import { Inject } from "@angular/core";
import { AuthService } from '../auth/auth.service';
import { HttpHeaders, HttpParams, HttpClient } from '@angular/common/http';
import * as signalR from "@aspnet/signalr";
import { Observable, BehaviorSubject } from "rxjs";
import { Store, select, UPDATE } from '../../../@ngrx/store';
import { UPDATEE } from "../baseclass/UnifiedNotificationReducer";
import { UnifiedNotificationObject } from "../interface/UnifiedNotificationObject";
import { RequireInteractiveControl } from "../interface/Interactive Component/RequireInteractiveControl";
import { WebNotificationService } from '../auth/webNotification.service';

interface AppStateUnot {
    unot: NotificationMod;
}

export class NotificationMod {
    totalcount: number;
    instance: NotificationFigure[];
}


export class NotificationFigure {
    statusName: string;
    instanceCount: number;
}

export class UnifiedNotificationService {
    connection: signalR.HubConnection;
    unot$: Observable<NotificationMod>;
    public notificationModSub: BehaviorSubject<NotificationMod>;
    totalcount: number;
    totalcount$: Observable<number>;
    notificationMod: NotificationMod;
    statustypecount: number;
    currentstatustypecount: number;
    constructor(private authService: AuthService,
        public http: HttpClient,
        @Inject('syncserviceurl') public syncserviceUrl: string,
        private store: Store<AppStateUnot>) {
        this.unot$ = store.pipe(select('unot'));
        this.connection = new signalR.HubConnectionBuilder()
            .withUrl(syncserviceUrl + "NotificationHub",
                {
                    accessTokenFactory: () =>
                        this.authService.getAccessToken()
                })
            .build();

        this.connection.start().then(() => {
            console.log('Hub connection started');
        }).catch(err => {
        });

        this.connection.on("IstatusNotification", data => {
            let status: string = data;
            // alert(status);
            this.UpdateCount(status);
        });

        this.notificationModSub = new BehaviorSubject(<NotificationMod>{});
    }

    public InitiateCount(statuslist: string[]) {
        this.currentstatustypecount = 0;
        this.statustypecount = statuslist.length;
        this.totalcount = 0;
        if (statuslist.length == 0) {
            let unotres = <NotificationMod>{};
            unotres.totalcount = 0;

            this.notificationModSub.next(unotres);
            this.store.dispatch({ type: UPDATEE, value: unotres });
        }
        else {
            for (let x in statuslist) {
                this.UpdateCount(statuslist[x]);
            }
        }
    }


    public UpdateCount(status: string) {

        this.StatusCount(status).subscribe(s => {

            this.unot$.subscribe(unotres => {

                if (unotres == null) {
                    unotres = <NotificationMod>{};
                }
                if (unotres.instance != null) {
                }
                else {
                    unotres.instance = [];
                }
                var item = unotres.instance.find(x => x.statusName == status);
                if (item == null) {

                    var newitem: NotificationFigure = { instanceCount: s, statusName: status };
                    this.totalcount += s;
                    unotres.totalcount = this.totalcount;
                    if (unotres.totalcount > 99) { unotres.totalcount = 99; }
                    unotres.instance.push(newitem);
                }
                else {
                    var newitem: NotificationFigure = { instanceCount: s, statusName: status };
                    unotres.instance.splice(unotres.instance.findIndex(s => s.statusName == status), 1);
                    unotres.instance.push(newitem);
                    var countnew: number = 0;
                    for (let x in unotres.instance) {
                        countnew += unotres.instance[x].instanceCount;
                    }
                    this.totalcount = countnew;
                    unotres.totalcount = this.totalcount;
                    if (unotres.totalcount > 99) { unotres.totalcount = 99; }
                    // unotres.instance.push(newitem);
                }
                this.currentstatustypecount += 1;
                unotres.instance = unotres.instance.sort(
                    (n1, n2) => {
                        return n2.instanceCount - n1.instanceCount;
                    });

                this.notificationModSub.next(unotres);
                this.store.dispatch({ type: UPDATEE, value: unotres });


            }
            );

        }
        );
    }

    public StatusCount(status: string): Observable<number> {
        var optionss = {
            headers: new HttpHeaders({ 'Content-Type': 'application/json', 'Authorization': this.authService.getAuthorizationHeaderValue() }),
            params: new HttpParams()
        };

        return this.http.get<any>(this.syncserviceUrl + "api/Notification/GetUnifiedNotificationCount?status=" + status,
            optionss);
    }

    public GetNotificationList(status: string): Observable<UnifiedNotificationObjectClass[]> {
        var optionss = {
            headers: new HttpHeaders({ 'Content-Type': 'application/json', 'Authorization': this.authService.getAuthorizationHeaderValue() }),
            params: new HttpParams()
        };

        return this.http.get<UnifiedNotificationObjectClass[]>(this.syncserviceUrl + "api/Notification/GetUnifiedNotificationObjects?status=" + status,
            optionss);
    }

    public GetAllUnifiedNotificationList(): Observable<UnifiedNotificationObjectClass[]> {
        var optionss = {
            headers: new HttpHeaders({ 'Content-Type': 'application/json', 'Authorization': this.authService.getAuthorizationHeaderValue() }),
            params: new HttpParams()
        };

        return this.http.get<UnifiedNotificationObjectClass[]>(this.syncserviceUrl + "api/Notification/GetAllUnifiedNotificationList",
            optionss);
    }

    public GetStatusList() {
        var optionss = {
            headers: new HttpHeaders({ 'Content-Type': 'application/json', 'Authorization': this.authService.getAuthorizationHeaderValue() }),
            params: new HttpParams()
        };

        return this.http.get<string[]>(this.syncserviceUrl + "api/Notification/GetUnifiedNotificationStatus",
            optionss);
    }

    public GetUnifiedNotificationCountByModule(modulename: string): Observable<number> {
        var optionss = {
            headers: new HttpHeaders({ 'Content-Type': 'application/json', 'Authorization': this.authService.getAuthorizationHeaderValue() }),
            params: new HttpParams()
        };

        return this.http.get<any>(this.syncserviceUrl + "api/Notification/GetUnifiedNotificationCountByModule?modulename=" + modulename,
            optionss);
    }
}

export class UnifiedNotificationObjectClass implements UnifiedNotificationObject, RequireInteractiveControl {

    id: string;
    isLocked: boolean;
    applicationName: string;
    objectName: string;
    docName: string;
    objectType: string;
    objectId: string;
    description: string;
    requiredClaim: string;
    urlLink: string;
    status: string;



}

export class UnifiedOcNotificationObjectClass extends UnifiedNotificationObjectClass {

    oclist: string[]



}
