export interface ApiResponse<T> {
  code: number;
  message: string;
  data: T;
}

export interface PageResult<T> {
  items: T[];
  total: number;
  page: number;
  pageSize: number;
}

export interface AdminProfile {
  id: number;
  username: string;
  name: string;
  status: number;
  isSuperAdmin: boolean;
  mustChangePassword: boolean;
  permissions: string[];
}

export interface ManagedAdmin {
  id: number;
  username: string;
  name: string;
  status: number;
  isSuperAdmin: boolean;
  mustChangePassword: boolean;
  permissions: string[];
  lastLoginAt?: string | null;
  createdAt?: string | null;
}

export interface PermissionNode {
  code: string;
  name: string;
  superOnly?: boolean;
  children?: PermissionNode[];
}

export interface SsoClientItem {
  id: number;
  appId: string;
  name: string;
  redirectUris: string[];
  allowAutoRegister: boolean;
  defaultEntitlementPlanId?: number | null;
  defaultEntitlementPlanName?: string | null;
  status: number;
  identityCount: number;
  lastUsedAt?: string | null;
  createdAt: string;
  updatedAt: string;
  clientSecret?: string;
}

export interface SsoIdentityItem {
  id: number;
  clientId: number;
  clientName: string;
  appId: string;
  userId: number;
  userName: string;
  phone: string;
  externalUserId: string;
  displayNameSnapshot?: string | null;
  lastLoginAt?: string | null;
  createdAt: string;
}

export interface SsoAuditItem {
  id: number;
  appId?: string | null;
  clientName?: string | null;
  userId?: number | null;
  externalUserId?: string | null;
  action: string;
  status: string;
  errorMessage?: string | null;
  ip?: string | null;
  createdAt: string;
}

export interface DashboardStats {
  userCount: number;
  sessionCount: number;
  messageCount: number;
  aiRequestCount: number;
  knowledgeCount: number;
  inputToken: number;
  outputToken: number;
  totalToken: number;
  estimatedCost?: number | null;
  costCurrency?: string | null;
  costBreakdown: Array<{
    scene: string;
    modelName: string;
    requestCount: number;
    inputToken: number;
    outputToken: number;
    totalToken: number;
    estimatedCost: number;
    currency?: string | null;
  }>;
}

export type TrafficGrain = "minute" | "hour" | "day" | "week";

export interface PeakTrafficRow {
  period: string;
  periodLabel: string;
  requestCount: number;
  errorCount: number;
  errorRate: number;
  avgResponseMs: number;
}

export interface PeakTrafficResult {
  grain: TrafficGrain;
  peakPeriod?: string | null;
  peakRequests: number;
  totalRequests: number;
  rows: PeakTrafficRow[];
}

export interface PromptDetail {
  id: number | null;
  promptContent: string;
  changeType: "default" | "save" | "reset" | "restore";
  sourcePromptId?: number | null;
  updatedByName?: string | null;
  updatedAt?: string | null;
  charCount: number;
}

export interface PromptHistoryItem {
  id: number;
  preview: string;
  charCount: number;
  changeType: "save" | "reset" | "restore";
  sourcePromptId?: number | null;
  updatedByName: string;
  updatedAt: string;
  isCurrent: boolean;
}

export type ContentGenerationType = "help_card" | "share_draft";

export interface ContentGenerationVariable {
  name: string;
  label: string;
}

export interface ContentGenerationConfigDetail {
  id: number | null;
  configType: ContentGenerationType;
  label: string;
  templateContent: string;
  instructionContent: string;
  lockedFooter: string;
  variables: ContentGenerationVariable[];
  changeType: "default" | "save" | "reset" | "restore";
  sourceConfigId?: number | null;
  updatedByName: string;
  updatedAt?: string | null;
  templateCharCount: number;
  instructionCharCount: number;
}

export interface ContentGenerationHistoryItem {
  id: number;
  configType: ContentGenerationType;
  preview: string;
  templateCharCount: number;
  instructionCharCount: number;
  changeType: "save" | "reset" | "restore";
  sourceConfigId?: number | null;
  updatedByName: string;
  updatedAt: string;
  isCurrent: boolean;
}

export interface AdminUser {
  id: number;
  phone: string;
  name: string;
  nickname?: string | null;
  registrationSource: "direct" | "sso" | string;
  registrationClientId?: number | null;
  status: number;
  dailyChatLimit: number;
  dailyChatUsed: number;
  expiredAt?: string | null;
  lastLoginAt?: string | null;
  createdAt?: string | null;
  entitlement?: UserEntitlementSummary | null;
}

export interface AdminUserDetail {
  user: AdminUser;
  metrics: AdminUserMetrics;
  growthProfile?: UserGrowthProfileRecord | null;
  recentTopics: TopicSessionRecord[];
  recentHelpCards: TeacherHelpCardRecord[];
  recentShareDrafts: ShareDraftRecord[];
  recentReports: PeriodicReportRecord[];
}

export interface AdminUserMetrics {
  totalSessions: number;
  totalMessages: number;
  totalTopics: number;
  monthTopics: number;
  recentActiveDays: number;
  lastMessageAt?: string | null;
  aiRequestCount: number;
  inputToken: number;
  outputToken: number;
  totalToken: number;
  estimatedCost: number;
  costCurrency: string;
  helpCardCount: number;
  shareDraftCount: number;
  isHighFrequency: boolean;
  isInactive: boolean;
}

export interface EntitlementPlan {
  id: number;
  name: string;
  planType: "basic" | "deep" | "addon";
  description?: string | null;
  validityDays?: number | null;
  monthlyTopicLimit?: number | null;
  enableGrowthProfile: boolean;
  enablePeriodicReports: boolean;
  allowHelpCard: boolean;
  allowShareDraft: boolean;
  deductQuota: boolean;
  status: number;
  sortOrder: number;
  createdAt?: string | null;
  updatedAt?: string | null;
}

export interface UserEntitlementSummary {
  planId?: number | null;
  name: string;
  planType: string;
  monthlyTopicLimit?: number | null;
  monthlyTopicUsed: number;
  monthlyTopicRemaining?: number | null;
  enableGrowthProfile: boolean;
  enablePeriodicReports: boolean;
  allowHelpCard: boolean;
  allowShareDraft: boolean;
  deductQuota: boolean;
  effectiveAt?: string | null;
  expiredAt?: string | null;
  source: string;
  lifecycleStatus: "active" | "long_term" | "expiring_7" | "expiring_30" | "expired_fallback" | "default" | "legacy" | string;
  daysUntilExpiry?: number | null;
  previousPlanName?: string | null;
  previousExpiredAt?: string | null;
}

export interface EntitlementBatchRenewResult {
  succeeded: Array<{ userId: number; name: string }>;
  failed: Array<{ userId: number; name?: string; reason: string }>;
  successCount: number;
  failureCount: number;
}

export interface UserImportFailure {
  row: number;
  phone: string;
  reason: string;
}

export interface UserImportResult {
  created: number;
  updated: number;
  failed: number;
  failures: UserImportFailure[];
}

export interface SystemConfigItem {
  id: number;
  configKey: string;
  configValue: string;
  description?: string | null;
  updatedAt?: string | null;
}

export interface KnowledgeItem {
  id: number;
  name: string;
  feishuSpaceId: string;
  feishuNodeId: string;
  status: number;
  remark?: string | null;
  sourceTitle?: string | null;
  knowledgeType: "course" | "qa" | "general" | "fixed";
  lifecycleStatus: "active" | "archived";
  sourceStatus: "normal" | "error";
  sourceError?: string | null;
  currentVersionId?: number | null;
  lastSyncedAt?: string | null;
  lastPublishedAt?: string | null;
  migrationStatus: string;
  createdAt?: string | null;
  updatedAt?: string | null;
}

export interface ModelItem {
  id: number;
  provider: string;
  displayName?: string | null;
  apiType: string;
  modelName: string;
  baseUrl?: string | null;
  apiUrl: string;
  apiKeyMasked: string;
  authType: string;
  apiVersion?: string | null;
  temperature?: number | null;
  topP?: number | null;
  topK?: number | null;
  presencePenalty?: number | null;
  frequencyPenalty?: number | null;
  maxToken?: number | null;
  contextWindow?: number | null;
  streamEnabled: number;
  responseFormat?: string | null;
  extraParams?: string | null;
  remark?: string | null;
  timeoutSecond: number;
  enabled: number;
  isDefault: number;
  inputPricePer1k?: number | null;
  outputPricePer1k?: number | null;
  currency: string;
  usageScenarios?: string | null;
  allowSummary: number;
  allowReport: number;
  allowFixedInfo: number;
  allowSimpleKnowledge: number;
  allowDeepChat: number;
}

export interface AgentGenerationConfig {
  temperature: number | null;
  topP: number | null;
  topK: number | null;
  presencePenalty: number | null;
  frequencyPenalty: number | null;
  maxToken: number;
  streamEnabled: number;
  reasoningVisible: number;
  responseDepth: number;
}

export interface AgentRuntimeConfig extends AgentGenerationConfig {
  modelId: number | null;
  modelName: string | null;
}

export interface AgentDebugResult {
  ok: boolean;
  message: string;
  answer: string;
  prompt: string;
  modelName?: string;
  retrieveCount?: number;
  knowledgeIds?: string;
  retrievalTrace?: Record<string, unknown>[];
  retrievalLogId?: number;
  routeReason?: string;
  questionType?: string;
}

export interface AgentDebugStreamComplete {
  message: string;
  modelName?: string;
  retrieveCount?: number;
  knowledgeIds?: string;
  retrievalTrace?: Record<string, unknown>[];
  retrievalLogId?: number;
  routeReason?: string;
  questionType?: string;
}

export interface KnowledgeVersion {
  id: number;
  knowledgeId: number;
  snapshotId: number;
  versionNo: number;
  status: string;
  qualityStatus: string;
  changeSummary?: Record<string, unknown> | null;
  qualityReport?: Record<string, unknown> | null;
  processingRuleVersion: string;
  generationModel?: string | null;
  createdAt: string;
  publishedAt?: string | null;
}

export interface KnowledgeManifest {
  id: number;
  versionId: number;
  purpose: string;
  applicableQuestions: string;
  inapplicableQuestions: string;
  coreTopics: string;
  entities?: string | null;
  boundaries?: string | null;
  changeLevel: string;
  confirmed: boolean;
}

export interface KnowledgeDetail {
  knowledge: KnowledgeItem;
  currentVersion?: KnowledgeVersion | null;
  manifest?: KnowledgeManifest | null;
}

export interface KnowledgeVersionContent {
  version: KnowledgeVersion;
  manifest?: KnowledgeManifest | null;
  sections: Array<{ id: number; sectionKey: string; title: string; content: string; sourceStart: number; sourceEnd: number; contentHash: string }>;
  cards: Array<Record<string, unknown>>;
}

export interface KnowledgeContentSearchItem {
  knowledgeId: number;
  knowledgeName: string;
  sourceTitle?: string | null;
  knowledgeType: "course" | "qa" | "general" | "fixed";
  knowledgeStatus: number;
  lifecycleStatus: "active" | "archived";
  sourceStatus: "normal" | "error";
  versionId: number;
  versionNo: number;
  publishedAt?: string | null;
  itemType: "section" | "card" | "chunk";
  itemTypes?: Array<"section" | "card" | "chunk">;
  itemId: number;
  sectionId: number;
  sectionKey: string;
  title: string;
  snippet: string;
  highlightTerms?: string[];
  matchedIn: Array<"title" | "content">;
  hasChunks: boolean;
  isCurrentVersion: boolean;
  canAgentUse: boolean;
}

export interface KnowledgeSyncJob {
  id: number;
  knowledgeId: number;
  mode: string;
  status: string;
  stage: string;
  progress: number;
  sourceError?: string | null;
  resultSummary?: Record<string, unknown> | null;
  createdAt: string;
  finishedAt?: string | null;
}

export interface MigrationSummary {
  total: number;
  counts: Record<string, number>;
}

export interface KnowledgeBatchUpdateResult {
  total: number;
  success: number;
  failed: number;
  results: Array<{ knowledgeId: number; ok: boolean; error?: string }>;
}

export interface KnowledgeBatchSyncResult {
  total: number;
  success: number;
  failed: number;
  results: Array<{
    knowledgeId: number;
    name?: string;
    ok: boolean;
    status?: string;
    job?: KnowledgeSyncJob;
    error?: string;
  }>;
}

export interface RetrievalLogItem {
  id: number;
  sessionId?: number | null;
  question: string;
  knowledgeCalled: boolean;
  selectedKnowledgeIds?: string | null;
  queryTerms?: string[] | null;
  status: string;
  toolCostMs?: number | null;
  totalCostMs?: number | null;
  attentionCreated: boolean;
  createdAt: string;
}

export interface AttentionItem {
  id: number;
  sessionId: number;
  messageId: number;
  userId: number;
  triggerMessage: string;
  problemSummary: string;
  triggerReason: string;
  priority: string;
  status: string;
  handlerNote?: string | null;
  createdAt: string;
}

export interface ChatRecord {
  id: number;
  userId: number;
  userPhone: string;
  userName: string;
  sourceType: "direct" | "sso";
  sourceClientId?: number | null;
  sourceName: string;
  title: string;
  messageCount: number;
  lastMessageAt?: string | null;
  updatedAt: string;
}

export interface ChatMessageRecord {
  id: number;
  sessionId: number;
  topicSessionId?: number | null;
  userId: number;
  role: "user" | "assistant";
  content: string;
  messageStatus: string;
  tokenInput?: number | null;
  tokenOutput?: number | null;
  responseTimeMs?: number | null;
  modelId?: number | null;
  createdAt: string;
}

export interface AiLogRecord {
  id: number;
  sessionId?: number | null;
  messageId?: number | null;
  userId?: number | null;
  modelName?: string | null;
  knowledgeIds?: string | null;
  retrieveCount: number;
  retrievedChunks: RetrievedKnowledgeChunk[];
  inputToken?: number | null;
  outputToken?: number | null;
  totalToken?: number | null;
  costMs?: number | null;
  estimatedCost?: number | null;
  currency?: string | null;
  routeReason?: string | null;
  questionType?: string | null;
  knowledgeHit?: boolean;
  status: string;
  errorMessage?: string | null;
  prompt?: string | null;
  createdAt: string;
}

export interface RetrievedKnowledgeChunk {
  index: number;
  knowledgeId?: number | null;
  knowledgeName: string;
  title: string;
  content: string;
  sourceUrl?: string | null;
}

export interface ChatDetail {
  session: ChatRecord;
  messages: ChatMessageRecord[];
  messagesPage?: PageResult<ChatMessageRecord>;
  aiLogs: AiLogRecord[];
  topics?: TopicSessionRecord[];
  helpCards?: TeacherHelpCardRecord[];
  shareDrafts?: ShareDraftRecord[];
}

export interface TeacherHelpCardRecord {
  id: number;
  userId: number;
  topicSessionId: number;
  summaryId?: number | null;
  content: string;
  source: string;
  copied: boolean;
  copiedAt?: string | null;
  createdAt: string;
}

export interface ShareDraftRecord {
  id: number;
  userId: number;
  topicSessionId: number;
  summaryId?: number | null;
  content: string;
  source: string;
  copied: boolean;
  copiedAt?: string | null;
  createdAt: string;
}

export interface TopicSummaryRecord {
  id: number;
  topicSessionId: number;
  userId: number;
  schemaVersion: number;
  summary: string;
  currentFocus?: string | null;
  nextObservation?: string | null;
  modelName?: string | null;
  status: string;
  errorMessage?: string | null;
  attemptCount: number;
  maxAttempts: number;
  nextRunAt?: string | null;
  lastStartedAt?: string | null;
  finishedAt?: string | null;
  generatedAt: string;
}

export interface UserGrowthProfileRecord {
  id: number;
  userId: number;
  schemaVersion: number;
  reviewText: string;
  currentFocus?: string | null;
  sourceSummaryIds: number[];
  lastTopicSummaryId?: number | null;
  updatedBy: string;
  createdAt: string;
  updatedAt: string;
}

export interface PeriodicReportRecord {
  id: number;
  userId: number;
  schemaVersion: number;
  reportType: "weekly" | "monthly" | "stage" | string;
  reportTypeLabel: string;
  periodStart: string;
  periodEnd: string;
  title: string;
  content: string;
  sourceSummaryIds: number[];
  sourceTopicIds: number[];
  modelName?: string | null;
  status: "success" | "failed" | "empty" | string;
  errorMessage?: string | null;
  generatedBy: string;
  attemptCount: number;
  maxAttempts: number;
  nextRunAt?: string | null;
  lastStartedAt?: string | null;
  finishedAt?: string | null;
  generatedAt: string;
  createdAt: string;
  updatedAt: string;
}

export interface TopicSessionRecord {
  id: number;
  userId: number;
  chatSessionId: number;
  title: string;
  coreQuestion: string;
  status: string;
  messageCount: number;
  tokenInput: number;
  tokenOutput: number;
  quotaDeducted: boolean;
  startedAt: string;
  endedAt?: string | null;
  createdAt?: string | null;
  updatedAt?: string | null;
  summary?: TopicSummaryRecord | null;
  summaryAvailable?: boolean;
}

export interface QuestionInsightSummary {
  range: {
    dateFrom?: string | null;
    dateTo?: string | null;
    maxMessages: number;
  };
  summary: {
    scannedMessages: number;
    cleanedQuestions: number;
    filteredMessages: number;
    clusterCount: number;
    visibleClusterCount: number;
    minCount: number;
    cleanerVersion: string;
  };
  items: QuestionInsightCluster[];
  total: number;
  page: number;
  pageSize: number;
}

export interface QuestionInsightRefreshResult {
  processedMessages: number;
  acceptedQuestions: number;
  filteredMessages: number;
  concurrentSkips: number;
  hasMore: boolean;
  cleanerVersion: string;
}

export interface QuestionInsightCluster {
  rank: number;
  title: string;
  normalized: string;
  category: string;
  categoryLabel: string;
  count: number;
  userCount: number;
  sessionCount: number;
  aiRequestCount: number;
  noHitCount: number;
  failedCount: number;
  needsKnowledgeFollowUp: boolean;
  suggestedAction: string;
  firstSeenAt: string;
  lastSeenAt: string;
  topTerms: string[];
  variants: Array<{ text: string; count: number }>;
  samples: QuestionInsightSample[];
}

export interface QuestionInsightSample {
  messageId: number;
  sessionId: number;
  userId: number;
  userName: string;
  userPhone: string;
  raw: string;
  cleaned: string;
  createdAt: string;
}

export interface ChatRecordQuery {
  keyword?: string;
  userId?: number | null;
  status?: string;
  sourceType?: string;
  sourceClientId?: number | null;
  dateFrom?: string;
  dateTo?: string;
  page?: number;
  pageSize?: number;
}

export interface FeedbackItem {
  id: number;
  userId: number;
  userName: string;
  userPhone: string;
  messageId: number;
  messageContent: string;
  content: string;
  isRead: boolean;
  createdAt: string;
}

export interface FeedbackDetail extends FeedbackItem {
  sessionTitle: string;
  messages: Array<{ id: number; role: "user" | "assistant"; content: string; createdAt: string; isTarget: boolean }>;
}
