import {Component, OnDestroy, OnInit} from '@angular/core';
import {FormControl, FormGroup} from "@angular/forms";
import {ActivatedRoute, Params, Router} from "@angular/router";
import {BehaviorSubject, filter, Subscription, take} from "rxjs";
import {PersistentStore} from "../../shared/state/persistent/persistent-store.service";
import {MastodonApiAccountsService, MastodonApiAuthenticationService, MastodonApiListsService} from "projects/mastodon-api/src/public-api";
import {Instance} from "../../shared/state/persistent/state";

@Component({
    selector: 'app-authorize',
    templateUrl: './authorize.component.html',
    styleUrls: ['./authorize.component.scss']
})
export class AuthorizeComponent implements OnInit, OnDestroy {
    subscriptions: Subscription[] = [];
    currentInstance?: Instance;
    accessToken?: string;
    accountId?: string;
    isAuthorized: BehaviorSubject<boolean> = new BehaviorSubject<boolean>(false);
    authorizing: boolean = false;

    serverForm = new FormGroup({
        instance: new FormControl(''),
    });

    constructor(private mastodonApiAuthService: MastodonApiAuthenticationService,
                private store: PersistentStore,
                private mastodonApiAccountsService: MastodonApiAccountsService,
                private mastodonApiListsService: MastodonApiListsService,
                private router: Router,
                private route: ActivatedRoute,) {
        this.subscriptions.push(this.store
            .select('currentInstance')
            .subscribe((currentInstance) => {
                this.currentInstance = <Instance>currentInstance
                this.accessToken = this.currentInstance?.accessToken;
                this.accountId = this.currentInstance?.accountId;
                this.isAuthorized.next(!!(this.currentInstance && this.accessToken && this.accountId));
            }));
    }


    ngOnInit(): void {
        this.route.queryParams
            .pipe(
                filter((params: Params) => params['code']),
                take(1)
            )
            .subscribe(params => {
                if (this.currentInstance && !this.accessToken && params['code']) {
                    this.mastodonApiAuthService
                        .getAccessToken(this.currentInstance.instanceName, this.currentInstance.clientId, this.currentInstance.clientSecret, this.currentInstance.redirectUrl, params['code'])
                        .pipe(take(1))
                        .subscribe(accessToken => {
                            this.store.set(
                                'currentInstance',
                                {...this.currentInstance, 'accessToken': accessToken}
                            );
                            this.mastodonApiAuthService.verifyCredentials(this.currentInstance!.instanceName, accessToken)
                                .pipe(take(1))
                                .subscribe((accountId) => {
                                        this.store.set(
                                            'currentInstance',
                                            {...this.currentInstance, 'accountId': accountId}
                                        );
                                        this.router.navigate(['/sync']);
                                        this.isAuthorized.next(true);
                                    }
                                );
                        });
                }
            });
    }

    async registerApplication() {
        this.authorizing = true;
        this.subscriptions.push(this.store
            .select<Instance>('currentInstance')
            .subscribe((currentInstance) => {
                this.authorizing = false;
                let instanceName = this.serverForm.value.instance ?? '';
                if (instanceName === '') {
                    return;
                }
                if (currentInstance?.instanceName === instanceName) {
                    this.mastodonApiAuthService
                        .authorizeUser(currentInstance.instanceName, currentInstance.clientId, currentInstance.redirectUrl);
                    return;
                }

                // let redirectUrl = window.location.toString();
                let redirectUrl = window.location.protocol + '//' + window.location.host + window.location.pathname;
                this.authorizing = true;
                this.mastodonApiAuthService
                    .createApp(instanceName, 'Mastolists', redirectUrl, 'https://mastolists.novaloop.cloud')
                    .pipe(take(1))
                    .subscribe(res => {
                        this.authorizing = false;
                        this.store.set(
                            'currentInstance',
                            <Instance>{
                                id: res.id,
                                instanceName: instanceName,
                                appName: res.name,
                                website: res.website,
                                redirectUrl: res.redirectUri,
                                clientId: res.clientId,
                                clientSecret: res.clientSecret,
                            }
                        );
                        this.mastodonApiAuthService.authorizeUser(instanceName, res.clientId, res.redirectUri);
                    });
            }));
    }

    ngOnDestroy(): void {
        this.subscriptions.forEach(subscription => subscription.unsubscribe());
    }

}
