// ═══════════════════════════════════════════════════════════
// Feedback Zod Schemas — Runtime validation for CONTRACTS.md §3
// ═══════════════════════════════════════════════════════════

import { z } from "zod";

export const QualityDimensionSchema = z.enum([
  "code_quality", "design_aesthetics", "design_ux", "test_coverage",
  "documentation", "architecture", "error_handling", "performance",
  "security", "creativity", "completeness", "naming", "dx",
]);

export const PipelineStageSchema = z.enum([
  "intake", "scaffolding", "building", "testing",
  "review", "staging", "production", "published",
]);

export const DecisionFeedbackSchema = z.object({
  decision: z.enum(["approved", "rejected", "needs_work", "deferred", "skipped"]),
  reason: z.string().optional(),
  severity: z.enum(["minor", "moderate", "major", "critical"]).optional(),
  blockers: z.array(z.string()).optional(),
  suggestions: z.array(z.string()).optional(),
  tags: z.array(z.string()).optional(),
});

export const DimensionScoreSchema = z.object({
  dimension: QualityDimensionSchema,
  score: z.number().min(1).max(10),
  weight: z.number().optional(),
  comment: z.string().optional(),
});

export const FreeTextFeedbackSchema = z.object({
  liked: z.string().optional(),
  disliked: z.string().optional(),
  generalNotes: z.string().optional(),
});

export const ComparisonFeedbackSchema = z.object({
  preferred: z.enum(["A", "B", "neither", "both_good"]),
  reason: z.string().optional(),
  preferenceStrength: z.enum(["slight", "moderate", "strong", "overwhelming"]),
  winningFactors: z.array(z.string()).optional(),
  perDimension: z.array(z.object({
    dimension: QualityDimensionSchema,
    winner: z.enum(["A", "B", "tie"]),
  })).optional(),
  timeOnA_ms: z.number().optional(),
  timeOnB_ms: z.number().optional(),
});

export const AnnotationSchema = z.object({
  type: z.enum(["praise", "criticism", "question", "suggestion"]),
  target: z.object({
    file: z.string().optional(),
    lineStart: z.number().optional(),
    lineEnd: z.number().optional(),
    charStart: z.number().optional(),
    charEnd: z.number().optional(),
    selector: z.string().optional(),
    region: z.string().optional(),
  }),
  text: z.string(),
  severity: z.enum(["nit", "minor", "major", "critical"]).optional(),
  category: z.string().optional(),
});

export const ConfidenceFeedbackSchema = z.object({
  confidencePercent: z.number().min(0).max(100),
  zone: z.enum(["guess", "educated_guess", "confident", "certain"]),
  wouldDelegateToAI: z.boolean(),
  needsExpertReview: z.boolean(),
  lowConfidenceReason: z.string().optional(),
  isTrainingExample: z.boolean().optional(),
});

export const EstimationFeedbackSchema = z.object({
  estimate: z.union([z.number(), z.literal("unknown"), z.literal("break")]),
  context: z.string().optional(),
  hoveredValues: z.array(z.number()).optional(),
});

export const BatchDecisionSchema = z.object({
  itemId: z.string(),
  decision: z.enum(["approve", "reject", "love", "skip"]),
  timeMs: z.number(),
  flippedForDetails: z.boolean(),
});

export const TemperatureFeedbackSchema = z.object({
  temperature: z.number().min(0).max(100),
  zone: z.enum(["freezing", "cold", "lukewarm", "warm", "hot", "blazing"]),
  drivers: z.array(z.string()),
  dragJourney: z.array(z.number()),
});

export const ChecklistFeedbackSchema = z.object({
  checks: z.record(z.boolean()),
  notes: z.record(z.string()),
  checkOrder: z.array(z.string()),
  allClear: z.boolean(),
  completionRate: z.number().min(0).max(1),
});

export const RankingFeedbackSchema = z.object({
  finalRanking: z.array(z.string()),
  rankingChanges: z.number(),
  lockedItems: z.array(z.string()),
  expandedItems: z.array(z.string()),
  perItemNotes: z.record(z.string()).optional(),
});

export const RetrospectiveNoteSchema = z.object({
  text: z.string(),
  priority: z.enum(["urgent", "important", "idea"]).optional(),
});

export const RetrospectiveFeedbackSchema = z.object({
  start: z.array(RetrospectiveNoteSchema),
  stop: z.array(RetrospectiveNoteSchema),
  continue_: z.array(RetrospectiveNoteSchema),
});

export const FeedbackPayloadSchema = z.object({
  decision: DecisionFeedbackSchema.optional(),
  scores: z.array(DimensionScoreSchema).optional(),
  freeText: FreeTextFeedbackSchema.optional(),
  comparison: ComparisonFeedbackSchema.optional(),
  annotations: z.array(AnnotationSchema).optional(),
  confidence: ConfidenceFeedbackSchema.optional(),
  estimation: EstimationFeedbackSchema.optional(),
  batchDecisions: z.array(BatchDecisionSchema).optional(),
  retrospective: RetrospectiveFeedbackSchema.optional(),
  ranking: RankingFeedbackSchema.optional(),
  checklist: ChecklistFeedbackSchema.optional(),
  temperature: TemperatureFeedbackSchema.optional(),
  custom: z.record(z.unknown()).optional(),
});

export const ModalMetricsSchema = z.object({
  timeToFirstInteractionMs: z.number(),
  timeToDecisionMs: z.number(),
  fieldsModified: z.array(z.string()),
  scrollDepth: z.number().optional(),
  revisits: z.number(),
  totalInteractions: z.number(),
  viewportSize: z.object({ width: z.number(), height: z.number() }),
  deviceType: z.enum(["desktop", "mobile"]),
  hoverJourney: z.array(z.object({ target: z.string(), durationMs: z.number() })).optional(),
  hesitationPoints: z.array(z.object({ target: z.string(), durationMs: z.number() })).optional(),
});

export const WorkProductRefSchema = z.object({
  type: z.enum(["mcp_server", "code_module", "design", "test_suite", "documentation", "pipeline_config"]),
  id: z.string(),
  version: z.string(),
  path: z.string().optional(),
  summary: z.string(),
  bubaConfidence: z.number().min(0).max(1),
  bubaScorePrediction: z.number().optional(),
  generationContext: z.object({
    promptHash: z.string(),
    memorySnapshot: z.array(z.string()),
    modelUsed: z.string(),
    generationTimeMs: z.number(),
    iterationCount: z.number(),
  }),
});

export const EnrichedMetaSchema = z.object({
  timeOfDay: z.enum(["morning", "afternoon", "evening", "night"]),
  dayOfWeek: z.string(),
  sessionFatigue: z.number(),
  concurrentModals: z.number(),
  extractedThemes: z.array(z.string()).optional(),
  sentiment: z.number().optional(),
  actionableItems: z.array(z.string()).optional(),
  predictionDelta: z.number().optional(),
});

export const ModalResponseSchema = z.object({
  type: z.literal("factory_modal_response"),
  modalType: z.string(),
  modalVersion: z.string(),
  pipelineId: z.string(),
  itemId: z.string(),
  sessionId: z.string(),
  timestamp: z.string(),
  responseTimeMs: z.number(),
  feedback: FeedbackPayloadSchema,
  meta: ModalMetricsSchema,
});

export const FeedbackEventSchema = z.object({
  id: z.string(),
  timestamp: z.string(),
  sessionId: z.string(),
  modalType: z.string(),
  modalVersion: z.string(),
  workProduct: WorkProductRefSchema,
  pipelineId: z.string().nullable(),
  pipelineStage: PipelineStageSchema.nullable(),
  mcpServerType: z.string().optional(),
  feedback: FeedbackPayloadSchema,
  meta: ModalMetricsSchema.merge(EnrichedMetaSchema),
});
