import { Component, OnInit, inject } from '@angular/core'
import { FormsModule, ReactiveFormsModule } from '@angular/forms'
import { NgbDropdownModule, NgbModal } from '@ng-bootstrap/ng-bootstrap'
import { NgxBootstrapIconsModule } from 'ngx-bootstrap-icons'
import { delay, takeUntil, tap } from 'rxjs'
import { Workflow } from 'src/app/data/workflow'
import { IfPermissionsDirective } from 'src/app/directives/if-permissions.directive'
import { PermissionsService } from 'src/app/services/permissions.service'
import { WorkflowService } from 'src/app/services/rest/workflow.service'
import { ToastService } from 'src/app/services/toast.service'
import { ConfirmDialogComponent } from '../../common/confirm-dialog/confirm-dialog.component'
import { EditDialogMode } from '../../common/edit-dialog/edit-dialog.component'
import {
  WORKFLOW_TYPE_OPTIONS,
  WorkflowEditDialogComponent,
} from '../../common/edit-dialog/workflow-edit-dialog/workflow-edit-dialog.component'
import { PageHeaderComponent } from '../../common/page-header/page-header.component'
import { LoadingComponentWithPermissions } from '../../loading-component/loading.component'

@Component({
  selector: 'pngx-workflows',
  templateUrl: './workflows.component.html',
  styleUrls: ['./workflows.component.scss'],
  imports: [
    PageHeaderComponent,
    IfPermissionsDirective,
    FormsModule,
    ReactiveFormsModule,
    NgbDropdownModule,
    NgxBootstrapIconsModule,
  ],
})
export class WorkflowsComponent
  extends LoadingComponentWithPermissions
  implements OnInit
{
  private workflowService = inject(WorkflowService)
  permissionsService = inject(PermissionsService)
  private modalService = inject(NgbModal)
  private toastService = inject(ToastService)

  public workflows: Workflow[] = []

  ngOnInit() {
    this.reload()
  }

  reload() {
    this.loading = true
    this.workflowService
      .listAll()
      .pipe(
        takeUntil(this.unsubscribeNotifier),
        tap((r) => (this.workflows = r.results)),
        delay(100)
      )
      .subscribe(() => {
        this.show = true
        this.loading = false
      })
  }

  getTypesList(template: Workflow): string {
    return template.triggers
      .map(
        (trigger) =>
          WORKFLOW_TYPE_OPTIONS.find((t) => t.id === trigger.type).name
      )
      .join(', ')
  }

  editWorkflow(workflow: Workflow, forceCreate: boolean = false) {
    const modal = this.modalService.open(WorkflowEditDialogComponent, {
      backdrop: 'static',
      size: 'xl',
    })
    modal.componentInstance.dialogMode =
      workflow && !forceCreate ? EditDialogMode.EDIT : EditDialogMode.CREATE
    if (workflow) {
      // quick "deep" clone so original doesn't get modified
      const clone = Object.assign({}, workflow)
      clone.actions = [...workflow.actions]
      clone.triggers = [...workflow.triggers]
      modal.componentInstance.object = clone
    }
    modal.componentInstance.succeeded
      .pipe(takeUntil(this.unsubscribeNotifier))
      .subscribe((newWorkflow) => {
        this.toastService.showInfo(
          $localize`Saved workflow "${newWorkflow.name}".`
        )
        this.workflowService.clearCache()
        this.reload()
      })
    modal.componentInstance.failed
      .pipe(takeUntil(this.unsubscribeNotifier))
      .subscribe((e) => {
        this.toastService.showError($localize`Error saving workflow.`, e)
      })
  }

  copyWorkflow(workflow: Workflow) {
    const clone = Object.assign({}, workflow)
    clone.id = null
    clone.name = `${workflow.name} (copy)`
    clone.actions = [
      ...workflow.actions.map((a) => {
        a.id = null
        if (a.webhook) {
          a.webhook.id = null
        }
        if (a.email) {
          a.email.id = null
        }
        return a
      }),
    ]
    clone.triggers = [
      ...workflow.triggers.map((t) => {
        t.id = null
        return t
      }),
    ]
    this.editWorkflow(clone, true)
  }

  deleteWorkflow(workflow: Workflow) {
    const modal = this.modalService.open(ConfirmDialogComponent, {
      backdrop: 'static',
    })
    modal.componentInstance.title = $localize`Confirm delete workflow`
    modal.componentInstance.messageBold = $localize`This operation will permanently delete this workflow.`
    modal.componentInstance.message = $localize`This operation cannot be undone.`
    modal.componentInstance.btnClass = 'btn-danger'
    modal.componentInstance.btnCaption = $localize`Proceed`
    modal.componentInstance.confirmClicked.subscribe(() => {
      modal.componentInstance.buttonsEnabled = false
      this.workflowService.delete(workflow).subscribe({
        next: () => {
          modal.close()
          this.toastService.showInfo(
            $localize`Deleted workflow "${workflow.name}".`
          )
          this.workflowService.clearCache()
          this.reload()
        },
        error: (e) => {
          this.toastService.showError(
            $localize`Error deleting workflow "${workflow.name}".`,
            e
          )
        },
      })
    })
  }

  toggleWorkflowEnabled(workflow: Workflow) {
    this.workflowService.patch(workflow).subscribe({
      next: () => {
        this.toastService.showInfo(
          workflow.enabled
            ? $localize`Enabled workflow "${workflow.name}"`
            : $localize`Disabled workflow "${workflow.name}"`
        )
        this.workflowService.clearCache()
        this.reload()
      },
      error: (e) => {
        this.toastService.showError(
          $localize`Error toggling workflow "${workflow.name}".`,
          e
        )
      },
    })
  }
}
