import { Injectable } from '@angular/core';
import { OdataGridHelper } from '../_shared/utils/odata-grid-helper';
import { Observable } from 'rxjs';
import dayjs from 'dayjs';
import * as util from '../_shared/utils/util';
import { map } from 'rxjs/operators';
import { State } from '@progress/kendo-data-query';
import { GridDataResult } from '@progress/kendo-angular-grid';

export interface RequiredData {
  hasApprovalPermission: boolean;
  hasDistributePermission: boolean;
}

export interface InvoiceSelection {
  id: number;
}

@Injectable({
  providedIn: 'root'
})
export class InvoiceCrudeService extends OdataGridHelper {
  private baseUrl = `${window.location.origin}/api/InvoiceCrude`;

  constructor() {
    super()
  }

  getRequiredData(): Observable<RequiredData> {
    const url = `${this.baseUrl}/GetRequiredData`;
    return this.http.get<RequiredData>(url);
  }

  getInvoices(state: State, monthStart: Date, monthEnd: Date): Observable<GridDataResult> {
    const monthStartStr = dayjs(monthStart).format("YYYY-MM-DD");
    const monthEndStr = dayjs(monthEnd).format("YYYY-MM-DD");
    const extraParamsQueryStr = `&monthStart=${monthStartStr}&monthEnd=${monthEndStr}`;
    return this.fetch(`GetInvoiceCrudeGridItems`, state, extraParamsQueryStr, false);
  }

  approveInvoiceLines(invoicesToApprove: number[]): Observable<string> {
    const url = `${this.baseUrl}/ApproveInvoiceLines`;
    return this.http.put<string>(url, invoicesToApprove);
  }

  exportInvoicesXls(monthStart: Date, monthEnd: Date, state: State, fileNameOriginal: string) {
    const monthStartStr = dayjs(monthStart).format("YYYY-MM-DD");
    const monthEndStr = dayjs(monthEnd).format("YYYY-MM-DD");
    const isExportStr = true;
    const extraParamsQueryStr = `&monthStart=${monthStartStr}&monthEnd=${monthEndStr}&isExport=${isExportStr}`;
    return this.fetchExport(`GetInvoiceCrudeGridItems`, state, extraParamsQueryStr, fileNameOriginal);
  }

  downloadInvoice(invoiceNum: string, fileNameOriginal: string): Observable<{ fileBlob: Blob, fileName: string }> {
    const url = `${this.baseUrl}/DownloadInvoice?invoiceNum=${invoiceNum}`;
    return this.http.get(url, { observe: 'response', responseType: 'blob' }).pipe(
      map(result => {
        const fileBlob = result.body;
        const fileName: string = result.body.type === "text/plain" ? "Error.txt" : fileNameOriginal;
        return { fileBlob, fileName };
      })
    );
  }

  mergeFiles(invoiceSelections: InvoiceSelection[]): Observable<{ fileBlob: Blob; fileName: string }> {
    const url = `${this.baseUrl}/MergeFiles`;
    return util.downloadFileWithBody(this.http, url, invoiceSelections);
  }

}
