// Responsibility: project one PaC status capture into explicit source-commit release evidence.

export interface PacDeliveryObserveInput {
  readonly status: Record<string, unknown>;
  readonly sourceCommit: string;
}

export interface PacDeliveryObserveSnapshotInput {
  readonly snapshot: Record<string, unknown>;
  readonly target: Record<string, unknown>;
  readonly consumer: Record<string, unknown>;
  readonly sourceCommit: string;
}

export function projectPacDeliveryObserveSnapshot(input: PacDeliveryObserveSnapshotInput): Record<string, unknown> {
  const rows = arrayRecords(input.snapshot.consumers);
  const consumerId = stringOrNull(input.consumer.id);
  const row = rows.find((item) => item.consumer === consumerId) ?? {};
  const observation = record(input.snapshot.observation);
  const artifactMode = "deferred-single-snapshot";
  return projectPacDeliveryObserve({
    sourceCommit: input.sourceCommit,
    status: {
      target: input.target,
      consumer: input.consumer,
      observation: {
        ...observation,
        ok: observation.ok === true && input.snapshot.ok === true,
      },
      readErrors: input.snapshot.readErrors ?? [],
      summary: {
        latestPipelineRun: row.latestPipelineRunSummary ?? {},
        pipelineRuns: row.pipelineRuns ?? [],
        artifact: { collector: { mode: artifactMode } },
        argo: row.argo ?? {},
        runtime: row.runtime ?? {},
      },
    },
  });
}

export function projectPacDeliveryObserve(input: PacDeliveryObserveInput): Record<string, unknown> {
  const summary = record(input.status.summary);
  const pipelineRuns = arrayRecords(summary.pipelineRuns);
  const latestPipeline = record(summary.latestPipelineRun);
  const pipeline = pipelineRuns.find((item) => item.sourceCommit === input.sourceCommit) ?? latestPipeline;
  const argo = record(summary.argo);
  const runtime = record(summary.runtime);
  const workloads = arrayRecords(runtime.workloads);
  const matchingWorkloads = workloads.filter((item) => item.sourceCommit === input.sourceCommit);
  const deliveryObservation = record(record(input.status.consumer).deliveryObservation);
  const configuredRuntimeEvidence = stringOrNull(deliveryObservation.runtimeEvidence);
  const runtimeEvidence = configuredRuntimeEvidence === "not-applicable" ? "not-applicable" : "required";
  const runtimeEvidenceRequired = runtimeEvidence === "required";
  const observationConfigPath = stringOrNull(deliveryObservation.configPath);
  const observationModeDefaulted = deliveryObservation.defaulted === true || configuredRuntimeEvidence === null;
  const pipelineSourceCommit = stringOrNull(pipeline.sourceCommit);
  const sourceMatched = pipelineSourceCommit === input.sourceCommit;
  const pipelineSucceeded = pipeline.status === "True";
  const runtimeReady = matchingWorkloads.length > 0 && matchingWorkloads.every(workloadReady);
  const argoReady = argo.sync === "Synced" && argo.health === "Healthy";
  const observationReady = record(input.status.observation).ok === true;
  const readErrors = arrayRecords(input.status.readErrors);
  const state = !observationReady || !sourceMatched || !pipelineSucceeded || (runtimeEvidenceRequired && matchingWorkloads.length === 0)
    ? "blocked"
    : (!runtimeEvidenceRequired || runtimeReady) && argoReady
      ? "complete"
      : "partial";
  const firstBreak = firstBreakFor({
    observationReady,
    sourceMatched,
    pipelineSucceeded,
    runtimeEvidenceRequired,
    matchingWorkloads,
    runtimeReady,
    argoReady,
    argo,
    readErrors,
  });

  const artifactMode = record(record(summary.artifact).collector).mode ?? null;
  const warnings = runtimeEvidence === "not-applicable"
    ? [{
      code: "runtime-evidence-not-applicable",
      phase: "runtime",
      blocking: false,
      mode: runtimeEvidence,
      configPath: observationConfigPath,
    }]
    : !observationModeDefaulted
      ? []
      : [{
        code: "runtime-evidence-mode-defaulted",
        phase: "runtime",
        blocking: false,
        mode: runtimeEvidence,
        configPath: observationConfigPath,
        reason: stringOrNull(deliveryObservation.fallbackReason),
      }];
  return {
    ok: state !== "blocked",
    status: state,
    action: "platform-infra-pipelines-as-code-delivery-observe",
    mutation: false,
    sourceCommit: input.sourceCommit,
    remoteCaptureCount: 1,
    target: input.status.target,
    consumer: input.status.consumer,
    observation: input.status.observation,
    readErrors,
    pipeline: {
      id: pipeline.name ?? null,
      status: pipeline.status ?? null,
      reason: pipeline.reason ?? null,
      sourceCommit: pipelineSourceCommit,
      sourceMatched,
      durationSeconds: pipeline.durationSeconds ?? null,
      selectedFrom: pipeline === latestPipeline ? "latest" : "bounded-status-history",
    },
    argo: {
      sync: argo.sync ?? null,
      health: argo.health ?? null,
      revision: argo.revision ?? null,
      targetRevision: argo.targetRevision ?? null,
      firstDegradedResource: argo.firstDegradedResource ?? null,
      firstCondition: argo.firstCondition ?? null,
    },
    runtime: {
      evidenceMode: runtimeEvidence,
      applicable: runtimeEvidenceRequired,
      workloadCount: workloads.length,
      matchingWorkloadCount: matchingWorkloads.length,
      ready: runtimeEvidenceRequired ? runtimeReady : null,
      workloads: matchingWorkloads.map((item) => ({
        deployment: item.deployment ?? null,
        namespace: item.namespace ?? null,
        readyReplicas: item.readyReplicas ?? null,
        replicas: item.replicas ?? null,
        sourceCommit: item.sourceCommit ?? null,
        digest: item.digest ?? null,
      })),
    },
    artifactEvidence: {
      mode: artifactMode,
      deferred: artifactMode === "taskrun-status-only" || artifactMode === "deferred-single-snapshot",
    },
    firstBreak,
    warnings,
    valuesPrinted: false,
  };
}

export function renderPacDeliveryObserve(result: Record<string, unknown>): string[] {
  const target = record(result.target);
  const consumer = record(result.consumer);
  const pipeline = record(result.pipeline);
  const argo = record(result.argo);
  const runtime = record(result.runtime);
  const firstBreak = record(result.firstBreak);
  const workloads = arrayRecords(runtime.workloads);
  return [
    "PLATFORM-INFRA PIPELINES-AS-CODE DELIVERY OBSERVE",
    `TARGET  ${text(target.id)}  CONSUMER  ${text(consumer.id)}  STATUS  ${text(result.status)}  MUTATION  false`,
    `SOURCE  expected=${short(text(result.sourceCommit))} observed=${short(text(pipeline.sourceCommit))} matched=${String(pipeline.sourceMatched === true)}`,
    `PIPELINE  id=${text(pipeline.id)} status=${text(pipeline.status)} reason=${text(pipeline.reason)}`,
    `ARGO  sync=${text(argo.sync)} health=${text(argo.health)} revision=${short(text(argo.revision))}`,
    `RUNTIME  mode=${text(runtime.evidenceMode)} matching=${text(runtime.matchingWorkloadCount)}/${text(runtime.workloadCount)} ready=${runtime.applicable === true ? String(runtime.ready === true) : "n/a"}`,
    ...workloads.map((item) => `  ${text(item.namespace)}/${text(item.deployment)} ${text(item.readyReplicas)}/${text(item.replicas)} digest=${short(text(item.digest), 24)}`),
    `FIRST_BREAK  ${Object.keys(firstBreak).length === 0 ? "-" : `${text(firstBreak.code)} phase=${text(firstBreak.phase)}`}`,
    "REMOTE_CAPTURE_COUNT  1",
  ];
}

function firstBreakFor(input: {
  observationReady: boolean;
  sourceMatched: boolean;
  pipelineSucceeded: boolean;
  runtimeEvidenceRequired: boolean;
  matchingWorkloads: readonly Record<string, unknown>[];
  runtimeReady: boolean;
  argoReady: boolean;
  argo: Record<string, unknown>;
  readErrors: readonly Record<string, unknown>[];
}): Record<string, unknown> | null {
  if (!input.observationReady) {
    const readError = input.readErrors[0];
    return readError === undefined
      ? { code: "target-capture-failed", phase: "remote-read" }
      : {
        code: readError.code ?? "target-capture-failed",
        phase: readError.stage ?? "remote-read",
        exitCode: readError.exitCode ?? null,
      };
  }
  if (!input.sourceMatched) return { code: "pipeline-source-commit-mismatch", phase: "pipeline" };
  if (!input.pipelineSucceeded) return { code: "pipeline-not-succeeded", phase: "pipeline" };
  if (input.runtimeEvidenceRequired && input.matchingWorkloads.length === 0) return { code: "runtime-source-commit-not-observed", phase: "runtime" };
  if (input.runtimeEvidenceRequired && !input.runtimeReady) return { code: "runtime-workload-not-ready", phase: "runtime" };
  if (!input.argoReady) {
    return {
      code: "argo-not-ready",
      phase: "argo",
      resource: input.argo.firstDegradedResource ?? null,
      condition: input.argo.firstCondition ?? null,
    };
  }
  return null;
}

function workloadReady(value: Record<string, unknown>): boolean {
  return Number.isInteger(value.replicas)
    && Number(value.replicas) >= 0
    && Number.isInteger(value.readyReplicas)
    && Number(value.readyReplicas) >= Number(value.replicas);
}

function record(value: unknown): Record<string, unknown> {
  return typeof value === "object" && value !== null && !Array.isArray(value) ? value as Record<string, unknown> : {};
}

function arrayRecords(value: unknown): Record<string, unknown>[] {
  return Array.isArray(value) ? value.map(record) : [];
}

function stringOrNull(value: unknown): string | null {
  return typeof value === "string" && value.length > 0 ? value : null;
}

function text(value: unknown): string {
  return value === null || value === undefined || value === "" ? "-" : String(value);
}

function short(value: string, max = 16): string {
  return value.length <= max ? value : value.slice(0, max);
}
