import { UseGuards } from '@nestjs/common';
import { AttendanceService } from './attendance.service';
import { AttendanceImportService } from './attendance-import.service';
import { OperationLogsService } from '../operation-logs/operation-logs.service';
import { AuthorizationService, CaslAction, SubjectName } from '../authorization';
import { JwtAuthGuard } from '../auth/guards/jwt-auth.guard';

/** Minimal request user shape for type safety */
export interface RequestUser {
  id: number;
  username: string;
  permissions: string[];
  isSuperAdmin: boolean;
  roles: string[];
}

/** SSE event shape for @Sse() decorator */
export interface SseEvent {
  data: string | Record<string, unknown>;
  id?: string;
  type?: string;
  retry?: number;
}

@UseGuards(JwtAuthGuard)
export abstract class AttendanceControllerBase {
  constructor(
    protected readonly service: AttendanceService,
    protected readonly importService: AttendanceImportService,
    protected readonly logService: OperationLogsService,
    protected readonly authz: AuthorizationService,
  ) {}

  protected getTodayDateOnly(): string {
    const today = new Date();
    const year = today.getFullYear();
    const month = String(today.getMonth() + 1).padStart(2, '0');
    const day = String(today.getDate()).padStart(2, '0');
    return `${year}-${month}-${day}`;
  }

  protected canManageAllAttendance(req: { user: RequestUser }): boolean {
    return (
      this.authz.can(req, CaslAction.Manage, SubjectName.Attendance) ||
      // Legacy: class:edit grants broad attendance access for teacher scoping
      this.authz.can(req, CaslAction.Update, SubjectName.Class)
    );
  }

  protected getAccessibleClassIds(req: { user: RequestUser }) {
    return this.service.getAccessibleClassIds(req.user.id, this.canManageAllAttendance(req));
  }

  protected assertClassAccess(req: { user: RequestUser }, classId: number) {
    return this.service.assertClassAccess(req.user.id, classId, this.canManageAllAttendance(req));
  }
}
