import { Component, Input, OnInit, inject, signal } from '@angular/core';
import { CommonModule } from '@angular/common';
import { MatCardModule } from '@angular/material/card';
import { MatTableModule } from '@angular/material/table';
import { MatButtonModule } from '@angular/material/button';
import { MatIconModule } from '@angular/material/icon';
import { MatMenuModule } from '@angular/material/menu';
import { MatProgressSpinnerModule } from '@angular/material/progress-spinner';
import { MatDialog, MatDialogModule } from '@angular/material/dialog';
import { EmptyStateComponent } from '../../../shared/components/empty-state/empty-state.component';
import { ConfirmDialogComponent } from '../../../shared/components/confirm-dialog/confirm-dialog.component';
import { VerificationBadgeComponent, VerificationStatus } from '../../../shared/components/verification-badge/verification-badge.component';
import { DocumentUploadComponent, DocumentUploadDialogData } from '../document-upload/document-upload.component';
import { DocumentService } from '../services/document.service';
import { NotificationService } from '../../../core/services/notification.service';
import { DocumentResponseDto } from '../../../api/models';

@Component({
  selector: 'app-document-list',
  standalone: true,
  imports: [
    CommonModule,
    MatCardModule,
    MatTableModule,
    MatButtonModule,
    MatIconModule,
    MatMenuModule,
    MatProgressSpinnerModule,
    MatDialogModule,
    EmptyStateComponent,
    VerificationBadgeComponent,
  ],
  template: `
    <div class="document-list">
      <div class="list-header">
        <h3>Documents</h3>
        @if (canUpload) {
          <button mat-raised-button color="primary" (click)="openUploadDialog()">
            <mat-icon>upload</mat-icon>
            Upload
          </button>
        }
      </div>

      @if (loading()) {
        <div class="loading-container">
          <mat-spinner diameter="32"></mat-spinner>
        </div>
      } @else if (documents().length === 0) {
        <app-empty-state
          icon="folder_open"
          title="No documents"
          message="No documents have been uploaded yet."
        >
          @if (canUpload) {
            <button mat-raised-button color="primary" (click)="openUploadDialog()">
              <mat-icon>upload</mat-icon>
              Upload Document
            </button>
          }
        </app-empty-state>
      } @else {
        <div class="documents-grid">
          @for (doc of documents(); track doc.id) {
            <mat-card class="document-card">
              <div class="doc-icon">
                <mat-icon>{{ getDocIcon(doc.originalFilename) }}</mat-icon>
              </div>
              <div class="doc-info">
                <span class="doc-name" [title]="doc.originalFilename">
                  {{ doc.originalFilename }}
                </span>
                <span class="doc-type">{{ formatDocType(doc.docType) }}</span>
                <div class="doc-meta-row">
                  <span class="doc-meta">Version {{ doc.currentVersion }}</span>
                  <app-verification-badge
                    [status]="getVerificationStatus(doc)"
                    [iconOnly]="true"
                  />
                </div>
              </div>
              <div class="doc-actions">
                <button mat-icon-button [matMenuTriggerFor]="docMenu">
                  <mat-icon>more_vert</mat-icon>
                </button>
                <mat-menu #docMenu="matMenu">
                  <button mat-menu-item (click)="downloadDocument(doc)">
                    <mat-icon>download</mat-icon>
                    <span>Download</span>
                  </button>
                  @if (canUpload) {
                    <button mat-menu-item (click)="deleteDocument(doc)">
                      <mat-icon color="warn">delete</mat-icon>
                      <span>Delete</span>
                    </button>
                  }
                </mat-menu>
              </div>
            </mat-card>
          }
        </div>
      }
    </div>
  `,
  styles: [
    `
      .document-list {
        margin-top: 16px;
      }

      .list-header {
        display: flex;
        justify-content: space-between;
        align-items: center;
        margin-bottom: 16px;

        h3 {
          margin: 0;
          font-size: 1.125rem;
          font-weight: 500;
        }
      }

      .loading-container {
        display: flex;
        justify-content: center;
        padding: 32px;
      }

      .documents-grid {
        display: grid;
        grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
        gap: 16px;
      }

      .document-card {
        padding: 16px;
        display: flex;
        align-items: center;
        gap: 12px;
      }

      .doc-icon {
        display: flex;
        align-items: center;
        justify-content: center;
        width: 48px;
        height: 48px;
        border-radius: 8px;
        background-color: #e3f2fd;

        mat-icon {
          font-size: 24px;
          width: 24px;
          height: 24px;
          color: #1976d2;
        }
      }

      .doc-info {
        flex: 1;
        min-width: 0;
        display: flex;
        flex-direction: column;
        gap: 2px;
      }

      .doc-name {
        font-weight: 500;
        white-space: nowrap;
        overflow: hidden;
        text-overflow: ellipsis;
      }

      .doc-type {
        font-size: 0.875rem;
        color: rgba(0, 0, 0, 0.54);
      }

      .doc-meta {
        font-size: 0.75rem;
        color: rgba(0, 0, 0, 0.38);
      }

      .doc-meta-row {
        display: flex;
        align-items: center;
        gap: 8px;
      }
    `,
  ],
})
export class DocumentListComponent implements OnInit {
  @Input({ required: true }) requestId!: string;
  @Input() canUpload = false;

  private readonly documentService = inject(DocumentService);
  private readonly notification = inject(NotificationService);
  private readonly dialog = inject(MatDialog);

  readonly loading = signal(true);
  readonly documents = signal<DocumentResponseDto[]>([]);

  ngOnInit(): void {
    this.loadDocuments();
  }

  loadDocuments(): void {
    this.documentService.getDocuments(this.requestId).subscribe({
      next: (docs) => {
        this.documents.set(docs);
        this.loading.set(false);
      },
      error: () => {
        this.loading.set(false);
      },
    });
  }

  openUploadDialog(): void {
    const dialogRef = this.dialog.open(DocumentUploadComponent, {
      data: { requestId: this.requestId } as DocumentUploadDialogData,
      width: '500px',
    });

    dialogRef.afterClosed().subscribe((result) => {
      if (result) {
        this.loadDocuments();
      }
    });
  }

  downloadDocument(doc: DocumentResponseDto): void {
    this.documentService.getDownloadUrl(this.requestId, doc.id).subscribe({
      next: (response) => {
        window.open(response.url, '_blank');
      },
      error: () => {
        this.notification.error('Failed to get download URL');
      },
    });
  }

  deleteDocument(doc: DocumentResponseDto): void {
    const dialogRef = this.dialog.open(ConfirmDialogComponent, {
      data: {
        title: 'Delete Document',
        message: `Are you sure you want to delete "${doc.originalFilename}"?`,
        confirmText: 'Delete',
        confirmColor: 'warn',
      },
    });

    dialogRef.afterClosed().subscribe((confirmed) => {
      if (confirmed) {
        this.documentService.deleteDocument(this.requestId, doc.id).subscribe({
          next: () => {
            this.notification.success('Document deleted');
            this.loadDocuments();
          },
        });
      }
    });
  }

  getDocIcon(filename: string): string {
    const ext = filename.split('.').pop()?.toLowerCase();
    switch (ext) {
      case 'pdf':
        return 'picture_as_pdf';
      case 'jpg':
      case 'jpeg':
      case 'png':
      case 'gif':
        return 'image';
      case 'doc':
      case 'docx':
        return 'article';
      default:
        return 'description';
    }
  }

  formatDocType(type: string): string {
    return type.replace(/_/g, ' ').toLowerCase().replace(/^\w/, (c) => c.toUpperCase());
  }

  getVerificationStatus(doc: DocumentResponseDto): VerificationStatus {
    // Document has a hash means it's been recorded on blockchain
    if (doc.currentHash && doc.currentHash.length > 0) {
      return 'verified';
    }
    // If document is active but no hash, it's pending verification
    if (doc.isActive) {
      return 'pending';
    }
    return 'unverified';
  }
}
