<template>
    <div>
        <div class="grid-x">
            <div class="medium-7 cell"></div>
            <div class="medium-1 cell">
                <button type="button" class="button input-group" v-on:click='importchannel'>
                    <i class="fa fa-plus" aria-hidden="true"></i> Import
                </button>
            </div>
            <div class="medium-1 cell"></div>
            <div class="medium-1 cell">
                <button type="button" class="button input-group" v-on:click='exportchannel'>
                    <i class="fa fa-plus" aria-hidden="true"></i> Export
                </button>
            </div>
            <div class="medium-1 cell"></div>
            <div class="medium-1 cell">
                <button type="button" class="button input-group" v-on:click='Expanded = !Expanded'>
                    <i class="fa fa-plus" aria-hidden="true"></i> Add
                </button>
            </div>
        </div>

        <transition name="fade">
            <form v-cloak v-if="Expanded">
                <h2>Add new Channel</h2>
                <div class="grid-x">
                    <div class="medium-7 cell">
                        <p class="input-group">
                            <span class="input-group-label">Title</span>
                            <input class="input-group-field" type="text" placeholder="Youtube Channel Title" 
                            v-model="Title" readonly>
                        </p>
                        <p class="input-group">
                            <span class="input-group-label">Channel ID</span>
                            <input class="input-group-field" v-bind:class="{ error: !Valid }" type="text"
                                    placeholder="https://www.youtube.com/channel/UCJkMlOu7faDgqh4PfzbpLdg" 
                                    v-model="Channel_Identification_Box">
                        </p>
                        <p class="input-group">
                            <span class="input-group-label">Description</span>
                            <input class="input-group-field" placeholder="Description"
                                v-model="Description" readonly cols="15" rows="5"
                                type="text">
                        </p>
                        <button type="button"
                            class="button input-group" style="max-height:50px; max-width:100px; float: right;"
                            v-if="Valid" @click="Submit">Submit</button>
                    </div>
                    <div class="medium-2 cell"></div>
                    <div class="input-group medium-2 cell">
                        <img :src="Thumbnail"/>
                    </div>
                    <div class="medium-1 cell"></div>
                </div>
            </form>
        </transition>
    </div>
</template>

<script lang="ts">
import Vue from "vue";
import * as DumbYT from "../dumbyt";
import Axios from "axios";
import SA2,{ SweetAlertType } from "sweetalert2";
import * as _ from "lodash";
import Sweetalert2, {SweetAlertOptions} from "sweetalert2";

// Small wrapper to convert to and from channels and import/export possible channels.
class OutChannel {
    ID : string;
    Tags : Array<string>;
    Title: string;

    constructor(channel :DumbYT.Channel) {
        this.ID = channel.ID;
        this.Title = channel.Title;
        this.Tags = channel.User_Tags;
    }
};

async function Channel_Bulk_Add() : Promise<void> {
    // Ask user for the JSON file containing our channels.
    const {value: uploadedfile} = await SA2({
        title: 'Select image',
        input: 'file',
        inputAttributes: {
            'aria-label': 'Upload your profile picture'
        }
    });
    
    // Check that we got an input file.
    if (uploadedfile != null) {
        // Read our file.
        var reader = new FileReader();

        // Tell reader to run upload our channels when it got a file.
        reader.onload = async (e) => {
            // Send all requested channel updates to the server.
            const channels = JSON.parse(reader.result) as OutChannel[];
            const attempts = await Promise.all(channels.map(c => DumbYT.API.channel_modify(c.ID, DumbYT.API.Modification.Add)));

            // Get all the insertions which failed.
            const bad = attempts.filter((a: any): a is string => !!a).map(a => {return { 
                title: "Channel Add Fail!",
                text: "The channel has not been added due to the following: \n" + a,
                type: "error"} as SweetAlertOptions
            });
            
            // Make dialog boxes for them.
            await SA2.queue(bad);
        }

        // Give our uploader the data which was sent.
        reader.readAsText(uploadedfile)
    }
}

// Vue class for keeping state of the videos.
export default Vue.extend({
    data() {
        return {
            Title: "",
            Description: "",
            ID: "",
            Thumbnail: "",
            Valid: false,
            Expanded: false,
            Channel_Identification_Box : ""
        }
    },

    watch: {
        Channel_Identification_Box(newcontents: string) {
            this.GetChannelFromYT(newcontents);
        }
    },
    methods: {
        Submit() : void {
            DumbYT.API.channel_modify(this.ID, DumbYT.API.Modification.Add).then((resp) => {
                if (resp == null)
                    SA2(
                        "Channel Add Success!", 
                        "The channel has been added succesfully, video contents should be updated shortly.",
                        "success"
                    );
                else
                    SA2(
                        "Channel Add Fail!", 
                        "The channel has not been added due to the following: \n" + resp,
                        "error"
                    );
            });

            // Hide the bars and erase internal state.
            this.Expanded = false;
            this.clear();
        },

        // Clears the contents of the add channel field
        clear() : void {
            this.Title = "";
            this.Description = "";
            this.ID = "";
            this.Thumbnail = "";
            this.Valid = false;
            this.Channel_Identification_Box = "";
        },

        // Export the channels as a json file.
        exportchannel() : void {
            function download(filename: string, text: string) : void {
                var element = document.createElement('a');
                element.setAttribute('href', 'data:application/json;charset=utf-8,' + encodeURIComponent(text));
                element.setAttribute('download', filename);

                element.style.display = 'none';
                document.body.appendChild(element);

                element.click();

                document.body.removeChild(element);
            }

            // Get all the youtube channels.
            DumbYT.API.search_channels("").then(channels => 
                download("Channel_Export.json", 
                    JSON.stringify(channels.map(c => new OutChannel(c)))
                )
            );
        },

        // Import a channel list
        importchannel() : void {
            Channel_Bulk_Add();
        },

        GetChannelFromYT(Channel: string) : void {
            // Say it failed first so if we exit early then correctly marked fail.
            this.Valid = false;

            // Copy over to internal ID box.
            this.ID = Channel;

            // Remove any potential youtube URL from the field.
            const ytchurl = "https://www.youtube.com/channel/";
            if (this.ID.startsWith(ytchurl))
                this.ID = this.ID.replace(ytchurl, "");

            // Check if what remains looks like a youtube channel ID.
            if (this.ID.length != "UCyS4xQE6DK4_p3qXQwJQAyA".length){
                this.Title = "";
                this.Description = "";
                this.ID = "";
                this.Thumbnail = "";
                this.Valid = false;
            }

            // Get channel metadata.
            const API = 'https://www.googleapis.com/youtube/v3/channels?';
            const API_Parts = 'part=snippet%2CcontentDetails%2Cstatistics';
            const API_Key = '&key=AIzaSyCuIYkMc5SktlnXRXNaDf2ObX-fQvtWCnQ'
            const API_Search_ID = '&id=' + this.ID;
            Axios.get(API + API_Parts + API_Search_ID + API_Key).then((resp) => {
                this.Description = _.truncate(resp.data.items[0].snippet.description, {length: 70});
                this.Title = resp.data.items[0].snippet.title;
                this.Thumbnail = resp.data.items[0].snippet.thumbnails.high.url;
                this.Valid = true;
            })
            .catch(function (error) {
                console.log(error);
            });
        }
    }
});
</script>

<style>
.fade-enter-active {
    transition: opacity 0.75s;
}

.fade-leave-active {
    transition: opacity 0.25s;
}

.fade-enter, .fade-leave-to {
    opacity: 0;
}
</style>
