import { Injectable } from '@angular/core';
import { NanoService } from '../nano/nano.service';

export enum NanoActionQueueEvent {
  DELETE = 'delete',
  LIST_DIR = 'listDir',
  MAKE_DIR = 'makeDir',
  COPY = 'copy',
  MOVE = 'move',
}

export type NanoActionType = {
  resourceId;
  path: string;
  done: boolean;
  icon: string;
  error: boolean;
  event: NanoActionQueueEvent;
};

@Injectable({
  providedIn: 'root',
})
export class NanoActionQueueService {
  private actionList: NanoActionType[] = [];
  public static WAIT_BEFORE_ALERT = 5000; // wait before alert the user about the event progress is not done yet (in ms)

  public getActionList(): NanoActionType[] {
    return this.actionList;
  }

  constructor(private nanoService: NanoService) {}

  public delete(resourceId, path: string, successCallback?: Function, errorCallback?: Function) {
    let actionRef: NanoActionType = {
      resourceId,
      path,
      done: false,
      icon: 'folder-open',
      error: false,
      event: NanoActionQueueEvent.DELETE,
    };

    setTimeout(() => {
      if (!actionRef.done) {
        this.actionList.push(actionRef);
      }
    }, NanoActionQueueService.WAIT_BEFORE_ALERT);

    this.nanoService.delete(
      resourceId,
      path,
      (res) => {
        actionRef.done = true;
        successCallback && successCallback(res);
      },
      (err) => {
        actionRef.error = true;
        errorCallback && errorCallback(err);
      }
    );
  }

  public listDir(
    resourceId,
    path: string,
    successCallback?: Function,
    errorCallback?: Function,
    progressCallback?: Function
  ) {
    let actionRef: NanoActionType = {
      resourceId,
      path,
      done: false,
      icon: 'folder-plus',
      error: false,
      event: NanoActionQueueEvent.LIST_DIR,
    };

    setTimeout(() => {
      if (!actionRef.done) {
        this.actionList.push(actionRef);
      }
    }, NanoActionQueueService.WAIT_BEFORE_ALERT);

    this.nanoService.listDir(
      resourceId,
      path,
      (res) => {
        actionRef.done = true;
        successCallback && successCallback(res);
      },
      (err) => {
        actionRef.done = true;
        actionRef.error = true;
        errorCallback && errorCallback(err);
      },
      progressCallback
    );
  }

  public makeDir(resourceId, path: string, successCallback?: Function, errorCallback?: Function) {
    let actionRef: NanoActionType = {
      resourceId,
      path,
      done: false,
      icon: 'folder-plus',
      error: false,
      event: NanoActionQueueEvent.MAKE_DIR,
    };

    setTimeout(() => {
      if (!actionRef.done) {
        this.actionList.push(actionRef);
      }
    }, NanoActionQueueService.WAIT_BEFORE_ALERT);

    this.nanoService.makeDir(
      resourceId,
      path,
      (res) => {
        actionRef.done = true;
        successCallback && successCallback(res);
      },
      (err) => {
        actionRef.done = true;
        actionRef.error = true;
        errorCallback && errorCallback(err);
      }
    );
  }

  public copy(
    resourceId,
    pathFrom: string,
    pathTo: string,
    successCallback: Function = () => {},
    errorCallback?: Function
  ) {}

  public move(
    resourceId,
    pathFrom: string,
    pathTo: string,
    successCallback: Function = () => {},
    errorCallback?: Function
  ) {
    let actionRef: NanoActionType = {
      resourceId,
      path: pathFrom,
      done: false,
      icon: 'folder-plus',
      error: false,
      event: NanoActionQueueEvent.MOVE,
    };

    setTimeout(() => {
      if (!actionRef.done) {
        this.actionList.push(actionRef);
      }
    }, NanoActionQueueService.WAIT_BEFORE_ALERT);

    this.nanoService.moveFile(
      resourceId,
      pathFrom,
      pathTo,
      (res) => {
        actionRef.done = true;
        successCallback && successCallback(res);
      },
      (err) => {
        actionRef.done = true;
        actionRef.error = true;
        errorCallback && errorCallback(err);
      }
    );
  }
}
