/**
 * ADP PTO 同步 API client
 * 仅会议管理员（Administrator / MeetingManager）可访问
 */
import apiClient from '@/lib/api-client';

export interface AdpSyncTaskExecution {
  id: string;
  status: 'PENDING' | 'RUNNING' | 'SUCCESS' | 'FAILED' | 'TIMEOUT' | 'CANCELLED';
  startedAt: string;
  completedAt: string | null;
  duration: number | null;
  result: Record<string, unknown> | null;
  logs: string | null;
  error: string | null;
}

export interface AdpSyncTask {
  code: 'ADP_LINKER' | 'ADP_PTO_SYNC';
  name: string;
  status: 'ACTIVE' | 'PAUSED' | 'DISABLED';
  lastRunAt: string | null;
  lastStatus: string | null;
  totalRuns: number;
  successRuns: number;
  failedRuns: number;
  lastExecution: AdpSyncTaskExecution | null;
}

export interface AdpSyncStatus {
  tasks: AdpSyncTask[];
  isEnabled: boolean;
  configValidation: { ok: boolean; missing: string[] };
}

export interface AdpSyncResult {
  success: boolean;
  duration: number;
  errors: string[];
  logs?: string;
  recordsFetched?: number;
  recordsUpserted?: number;
  recordsDeleted?: number;
  recordsUnmatched?: number;
  extras?: Record<string, unknown>;
}

export interface AdpSyncTriggerAck {
  accepted: boolean;
  reason?: string;
  status: 'RUNNING';
}

export interface AdpPtoScheduleListItem {
  id: string;
  leaveDate: string;     // ISO date
  startTime: string;     // ISO datetime
  endTime: string;
  syncedAt: string;
  user: {
    id: string;
    displayName: string;
    email: string;
  };
}

export interface AdpPtoScheduleListResponse {
  items: AdpPtoScheduleListItem[];
  total: number;
  page: number;
  pageSize: number;
}

export interface AdpPtoScheduleQuery {
  startDate?: string;    // ISO date
  endDate?: string;
  userId?: string;
  departmentId?: string;
  q?: string;
  page?: number;
  pageSize?: number;
}

export async function getAdpSyncStatus(): Promise<AdpSyncStatus> {
  return apiClient.get('/adp-sync/status');
}

export async function triggerAdpLinker(dryRun = false): Promise<AdpSyncTriggerAck> {
  return apiClient.post('/adp-sync/linker/trigger', { dryRun });
}

export async function triggerAdpPtoSync(
  windowStartDays?: number,
  windowEndDays?: number,
): Promise<AdpSyncTriggerAck> {
  const body: Record<string, number> = {};
  if (windowStartDays !== undefined) body.windowStartDays = windowStartDays;
  if (windowEndDays !== undefined) body.windowEndDays = windowEndDays;
  return apiClient.post('/adp-sync/pto/trigger', body);
}

export async function listAdpPtoSchedules(
  query: AdpPtoScheduleQuery = {},
): Promise<AdpPtoScheduleListResponse> {
  return apiClient.get('/adp-sync/admin/pto-schedules', { params: query });
}

export async function applyMeetingPto(meetingId: string): Promise<{
  meetingId: string;
  marked: number;
  details: Array<{ userId: string; previousStatus: string; scheduleId: string }>;
}> {
  return apiClient.post(`/meeting-attendance/meetings/${meetingId}/apply-pto`);
}

// ----- 手动匹配 -----

export interface UnmatchedAdpEntry {
  aoid: string;
  email: string;
}

export async function listUnmatchedAdp(): Promise<{
  items: UnmatchedAdpEntry[];
  lastRunAt: string | null;
}> {
  return apiClient.get('/adp-sync/admin/unmatched-adp');
}

export interface UnlinkedUserCandidate {
  id: string;
  displayName: string;
  email: string;
}

export async function searchUnlinkedUsers(q: string): Promise<{ items: UnlinkedUserCandidate[] }> {
  return apiClient.get('/adp-sync/admin/users-search', { params: { q } });
}

export async function manualLinkAoid(
  aoid: string,
  userId: string,
): Promise<{ success: boolean; user: UnlinkedUserCandidate & { adpAoid: string; adpLinkedAt: string } }> {
  return apiClient.post('/adp-sync/admin/manual-link', { aoid, userId });
}
