"use strict";
var __importDefault = (this && this.__importDefault) || function (mod) {
    return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.projectPlanningScaffoldRefinementFindings = projectPlanningScaffoldRefinementFindings;
exports.inspectPlanningChildScaffolds = inspectPlanningChildScaffolds;
exports.createPhaseAuthoringReadinessReceipt = createPhaseAuthoringReadinessReceipt;
exports.computePhaseAuthoringReadinessReceiptId = computePhaseAuthoringReadinessReceiptId;
exports.projectPlanningScaffoldEvidence = projectPlanningScaffoldEvidence;
exports.projectPlanningScaffoldContract = projectPlanningScaffoldContract;
exports.comparePlanningScaffoldProjections = comparePlanningScaffoldProjections;
exports.planningScaffoldProjectionRevision = planningScaffoldProjectionRevision;
exports.legacyPlanningScaffoldProjectionRevision = legacyPlanningScaffoldProjectionRevision;
exports.stampPlanningScaffoldProjectionRevision = stampPlanningScaffoldProjectionRevision;
exports.rebindPlanningScaffoldProjectionRevision = rebindPlanningScaffoldProjectionRevision;
exports.readPlanningScaffoldProjectionRevision = readPlanningScaffoldProjectionRevision;
exports.planningAuthoringSectionPolicies = planningAuthoringSectionPolicies;
exports.auditPlanningArtifactAuthoring = auditPlanningArtifactAuthoring;
exports.auditParentDecomposition = auditParentDecomposition;
exports.inspectParentDecomposition = inspectParentDecomposition;
exports.classifyScaffoldAdapterRequirement = classifyScaffoldAdapterRequirement;
exports.inspectProjectedTaskScaffoldEvidence = inspectProjectedTaskScaffoldEvidence;
exports.inspectOrderedTaskScaffoldDependencies = inspectOrderedTaskScaffoldDependencies;
exports.inspectChildScaffoldEvidence = inspectChildScaffoldEvidence;
exports.declaredPlanningChildSlugs = declaredPlanningChildSlugs;
exports.formatPlanningAuthoringIssues = formatPlanningAuthoringIssues;
exports.formatParentDecompositionIssues = formatParentDecompositionIssues;
const node_crypto_1 = require("node:crypto");
const node_fs_1 = __importDefault(require("node:fs"));
const node_path_1 = __importDefault(require("node:path"));
const planning_document_utils_1 = require("./planning-document-utils");
const verb_policy_1 = require("./verb-policy");
const workflow_provenance_1 = require("./workflow-provenance");
const scaffold_target_path_policy_1 = require("./scaffold-target-path-policy");
function projectPlanningScaffoldRefinementFindings(parentPath, evidence) {
    const childLabel = `${evidence.childKind[0].toUpperCase()}${evidence.childKind.slice(1)}`;
    return evidence.missingEvidence.map((kind) => ({
        code: (`PLANNING_SCAFFOLD_${kind.toUpperCase()}_EVIDENCE_MISSING`),
        message: `${childLabel} '${evidence.childSlug}' is missing ${kind} evidence required for an executable scaffold.`,
        severity: "error",
        path: parentPath,
        evidence: {
            category: "planning-review",
            details: {
                childKind: evidence.childKind,
                childSlug: evidence.childSlug,
                missingEvidenceKind: kind,
                requiresRefinement: true,
                noWriteRequired: true
            }
        }
    }));
}
function inspectPlanningChildScaffolds(options) {
    const evidence = options.declaredChildSlugs.map((childSlug) => inspectChildScaffoldEvidence({
        markdownText: options.markdownText,
        childKind: options.childKind,
        childSlug,
        declaredChildSlugs: options.declaredChildSlugs,
        runtimeEvidencePathPolicy: options.runtimeEvidencePathPolicy
    }));
    const findings = evidence.flatMap((entry) => projectPlanningScaffoldRefinementFindings(options.parentPath, entry));
    return {
        declaredChildSlugs: [...options.declaredChildSlugs],
        evidence,
        findings,
        complete: evidence.length > 0
            && evidence.every((entry) => entry.complete)
            && findings.length === 0
    };
}
function createPhaseAuthoringReadinessReceipt(options) {
    const nestedTaskCount = options.normalizedScaffoldEvidence.reduce((count, milestone) => count + milestone.taskIdentities.length, 0);
    const complete = options.blockerCount === 0
        && options.inspectionComplete
        && options.declaredMilestoneSlugs.length > 0
        && options.normalizedScaffoldEvidence.length === options.declaredMilestoneSlugs.length
        && options.contractImpactFingerprints.length === nestedTaskCount;
    const normalizedScaffoldEvidence = options.normalizedScaffoldEvidence.map((milestone) => ({
        milestoneSlug: milestone.milestoneSlug,
        scaffoldEvidence: normalizeChildScaffoldEvidence(milestone.scaffoldEvidence),
        criterionIds: [...milestone.criterionIds],
        taskIdentities: milestone.taskIdentities.map((task) => ({
            taskSlug: task.taskSlug,
            description: task.description,
            criterionIds: [...task.criterionIds],
            sharedCriterionIds: [...task.sharedCriterionIds],
            currentBehavior: task.currentBehavior,
            desiredBehavior: task.desiredBehavior,
            ownership: [...task.ownership],
            dependencies: [...task.dependencies],
            targetPaths: [...task.targetPaths],
            adapterPaths: [...task.adapterPaths],
            requiredAdapter: task.requiredAdapter,
            adapterRequirementReasons: [...task.adapterRequirementReasons],
            validationCommands: [...task.validationCommands],
            rollback: [...task.rollback],
            missingEvidence: [...task.missingEvidence],
            complete: task.complete
        }))
    }));
    const receiptWithoutId = {
        schemaVersion: 2,
        phaseOverviewPath: options.phaseOverviewPath,
        phaseRevision: options.phaseRevision,
        reviewedAt: options.reviewedAt,
        reviewMode: "readiness",
        blockerCount: options.blockerCount,
        complete,
        handoffReady: complete,
        declaredMilestoneSlugs: [...options.declaredMilestoneSlugs],
        criterionOwnership: normalizedScaffoldEvidence.map((milestone) => ({
            milestoneSlug: milestone.milestoneSlug,
            criterionIds: [...milestone.criterionIds],
            taskCriterionOwnership: milestone.taskIdentities.map((task) => ({
                taskSlug: task.taskSlug,
                criterionIds: [...task.criterionIds],
                sharedCriterionIds: [...task.sharedCriterionIds]
            }))
        })),
        nestedTaskIdentities: normalizedScaffoldEvidence.map((milestone) => ({
            milestoneSlug: milestone.milestoneSlug,
            taskSlugs: milestone.taskIdentities.map((task) => task.taskSlug)
        })),
        normalizedScaffoldEvidence,
        contractImpactFingerprints: options.contractImpactFingerprints
            .map((entry) => ({ ...entry }))
            .sort((left, right) => left.milestoneSlug.localeCompare(right.milestoneSlug)
            || left.taskSlug.localeCompare(right.taskSlug)),
        materializedScaffoldRevisions: options.materializedScaffoldRevisions
            .map((entry) => ({ ...entry }))
            .sort((left, right) => left.path.localeCompare(right.path)),
        authorizes: complete ? ["milestone-full-set-create"] : []
    };
    return {
        ...receiptWithoutId,
        receiptId: computePhaseAuthoringReadinessReceiptId(receiptWithoutId)
    };
}
function computePhaseAuthoringReadinessReceiptId(receipt) {
    const digest = (0, node_crypto_1.createHash)("sha256")
        .update(JSON.stringify(receipt))
        .digest("hex");
    return `phase-authoring-readiness-${digest.slice(0, 24)}`;
}
function projectPlanningScaffoldEvidence(evidence, projection) {
    const ownership = evidence.ownership.length > 0
        ? evidence.ownership
        : uniqueStrings(projection.ownership ?? []);
    const dependencies = evidence.dependencies.length > 0
        ? evidence.dependencies
        : uniqueStrings(projection.dependencies ?? []);
    const targetPaths = evidence.targetPaths.length > 0
        ? evidence.targetPaths
        : uniqueStrings(projection.targetPaths ?? []);
    const adapterPaths = evidence.adapterPaths.length > 0
        ? evidence.adapterPaths
        : uniqueStrings(projection.adapterPaths ?? []);
    const validationCommands = evidence.validationCommands.length > 0
        ? evidence.validationCommands
        : uniqueStrings(projection.validationCommands ?? []);
    const rollback = evidence.rollback.length > 0
        ? evidence.rollback
        : uniqueStrings(projection.rollback ?? []);
    const adapterClassification = classifyScaffoldAdapterRequirement({
        prose: [],
        targetPaths,
        explicitAdapterPaths: adapterPaths
    });
    const requiredAdapter = evidence.requiredAdapter || adapterClassification.required;
    const adapterRequirementReasons = uniqueAdapterRequirementReasons([
        ...evidence.adapterRequirementReasons,
        ...adapterClassification.reasons
    ]);
    const missingEvidence = [];
    if (ownership.length === 0)
        missingEvidence.push("ownership");
    if (dependencies.length === 0)
        missingEvidence.push("dependency");
    if (targetPaths.length === 0)
        missingEvidence.push("target");
    if (requiredAdapter && adapterPaths.length === 0)
        missingEvidence.push("adapter");
    if (validationCommands.length === 0)
        missingEvidence.push("validation");
    if (rollback.length === 0)
        missingEvidence.push("rollback");
    return {
        ...evidence,
        ownership,
        dependencies,
        targetPaths,
        adapterPaths,
        requiredAdapter,
        adapterRequirementReasons,
        validationCommands,
        rollback,
        missingEvidence,
        complete: missingEvidence.length === 0
    };
}
function projectPlanningScaffoldContract(markdownText, artifactKind, projectionReader = "current") {
    const readScopedLines = projectionReader === "day-shift-0.2.11"
        ? legacyScopedSectionLines
        : scopedSectionLines;
    const readSemanticValues = projectionReader === "day-shift-0.2.11"
        ? legacySemanticValues
        : semanticValues;
    const sections = markdownSections(markdownText);
    const childSection = artifactKind === "milestone" ? "Tasks" : null;
    const declaredChildSlugs = childSection === null
        ? []
        : declaredPlanningChildSlugs(markdownText, childSection);
    const nestedEvidence = declaredChildSlugs.map((childSlug) => {
        const lines = readScopedLines(sections, "Scaffold Evidence", childSlug);
        return {
            childSlug,
            criterionIds: readSemanticValues(lines, "criterion_ids"),
            sharedCriterionIds: readSemanticValues(lines, "shared_criterion_ids"),
            currentBehavior: readSemanticValues(lines, "current_behavior")[0] ?? null,
            desiredBehavior: readSemanticValues(lines, "desired_behavior")[0] ?? null,
            ownership: readSemanticValues(lines, "ownership"),
            dependencies: readSemanticValues(lines, "dependency"),
            targetPaths: readSemanticValues(lines, "target"),
            adapterPaths: readSemanticValues(lines, "adapter"),
            validationCommands: readSemanticValues(lines, "validation"),
            rollback: readSemanticValues(lines, "rollback")
        };
    });
    const targetPaths = normalizedSectionValues(sections, [
        "Implementation Target Paths",
        "Target Paths"
    ]);
    const runtimeCriterionIds = readSemanticValues(frontMatterNestedLines(markdownText, "runtime_acceptance"), "criterion_ids");
    const acceptanceCriteria = normalizedMarkdownListValues(sections.get("Acceptance Criteria"));
    const acceptanceCriterionIds = acceptanceCriteria.flatMap((value) => acceptanceCriterionIdsFromValue(value));
    const childSlugKey = artifactKind === "milestone" ? "milestone" : "task";
    return {
        artifactKind,
        childSlug: readTopLevelFrontMatter(markdownText).get(childSlugKey) ?? null,
        criterionIds: runtimeCriterionIds.length > 0
            ? runtimeCriterionIds
            : uniqueStrings(acceptanceCriterionIds),
        acceptanceCriteria,
        ownership: normalizedSectionValues(sections, ["Scope"]),
        dependencies: normalizedSectionValues(sections, ["Dependencies"]),
        targetPaths,
        adapterPaths: uniqueStrings([
            ...nestedEvidence.flatMap((entry) => entry.adapterPaths),
            ...targetPaths.filter(isLikelyAdapterPath)
        ]),
        validationCommands: normalizedSectionValues(sections, ["Validation Commands"]),
        rollback: normalizedSectionValues(sections, ["Rollback / Recovery", "Rollback"]),
        currentBehavior: normalizedSectionText(sections, "Current Behavior"),
        desiredBehavior: normalizedSectionText(sections, "Desired Behavior"),
        declaredChildCount: childSection === null
            ? null
            : declaredTargetCount(sections.get(childSection) ?? []),
        declaredChildSlugs,
        nestedEvidence
    };
}
function comparePlanningScaffoldProjections(expected, observed) {
    const drift = [];
    compareScalarField(drift, "artifactKind", expected.artifactKind, observed.artifactKind);
    compareScalarField(drift, "childSlug", expected.childSlug, observed.childSlug);
    compareArrayField(drift, "criterionIds", expected.criterionIds, observed.criterionIds);
    compareArrayField(drift, "acceptanceCriteria", expected.acceptanceCriteria, observed.acceptanceCriteria);
    comparePlanningScaffoldOwnership(drift, expected, observed);
    compareArrayField(drift, "dependencies", expected.dependencies, observed.dependencies);
    compareArrayField(drift, "targetPaths", expected.targetPaths, observed.targetPaths);
    const observedAdapterPaths = uniqueStrings([
        ...observed.adapterPaths,
        ...expected.adapterPaths.filter((adapterPath) => observed.targetPaths.includes(adapterPath))
    ]);
    compareArrayField(drift, "adapterPaths", expected.adapterPaths, observedAdapterPaths);
    compareArrayField(drift, "validationCommands", expected.validationCommands, observed.validationCommands);
    compareArrayField(drift, "rollback", expected.rollback, observed.rollback);
    compareScalarField(drift, "currentBehavior", expected.currentBehavior, observed.currentBehavior);
    compareScalarField(drift, "desiredBehavior", expected.desiredBehavior, observed.desiredBehavior);
    compareScalarField(drift, "declaredChildCount", expected.declaredChildCount, observed.declaredChildCount);
    compareArrayField(drift, "declaredChildSlugs", expected.declaredChildSlugs, observed.declaredChildSlugs);
    compareArrayField(drift, "nestedEvidence.childSlugs", expected.nestedEvidence.map((entry) => entry.childSlug), observed.nestedEvidence.map((entry) => entry.childSlug));
    const observedNested = new Map(observed.nestedEvidence.map((entry) => [entry.childSlug, entry]));
    for (const expectedEntry of expected.nestedEvidence) {
        const observedEntry = observedNested.get(expectedEntry.childSlug);
        if (observedEntry === undefined)
            continue;
        const prefix = `nestedEvidence.${expectedEntry.childSlug}`;
        compareArrayField(drift, `${prefix}.criterionIds`, expectedEntry.criterionIds, observedEntry.criterionIds);
        compareArrayField(drift, `${prefix}.sharedCriterionIds`, expectedEntry.sharedCriterionIds, observedEntry.sharedCriterionIds);
        compareScalarField(drift, `${prefix}.currentBehavior`, expectedEntry.currentBehavior, observedEntry.currentBehavior);
        compareScalarField(drift, `${prefix}.desiredBehavior`, expectedEntry.desiredBehavior, observedEntry.desiredBehavior);
        compareArrayField(drift, `${prefix}.ownership`, expectedEntry.ownership, observedEntry.ownership);
        compareArrayField(drift, `${prefix}.dependencies`, expectedEntry.dependencies, observedEntry.dependencies);
        compareArrayField(drift, `${prefix}.targetPaths`, expectedEntry.targetPaths, observedEntry.targetPaths);
        compareArrayField(drift, `${prefix}.adapterPaths`, expectedEntry.adapterPaths, observedEntry.adapterPaths);
        compareArrayField(drift, `${prefix}.validationCommands`, expectedEntry.validationCommands, observedEntry.validationCommands);
        compareArrayField(drift, `${prefix}.rollback`, expectedEntry.rollback, observedEntry.rollback);
    }
    return { expected, observed, drift, current: drift.length === 0 };
}
function comparePlanningScaffoldOwnership(drift, expected, observed) {
    if (expected.artifactKind !== "milestone" || observed.artifactKind !== "milestone") {
        compareArrayField(drift, "ownership", expected.ownership, observed.ownership);
        return;
    }
    const driftCount = drift.length;
    compareArrayField(drift, "ownership", expected.ownership.map(normalizeMilestoneScopeProjectionValue), observed.ownership.map(normalizeMilestoneScopeProjectionValue));
    if (drift.length === driftCount)
        return;
    const ownershipDrift = drift[drift.length - 1];
    ownershipDrift.expected = [...expected.ownership];
    ownershipDrift.observed = [...observed.ownership];
}
function normalizeMilestoneScopeProjectionValue(value) {
    return value
        .replace(/^(?:(?:Own the child-specific implementation boundary|Deliver the declared milestone outcome):\s*)+/u, "")
        .trim();
}
function planningScaffoldProjectionRevision(projection) {
    return `sha256:${(0, node_crypto_1.createHash)("sha256").update(JSON.stringify(projection)).digest("hex")}`;
}
/**
 * Reproduces the projection identity written before acceptance-criterion text
 * became part of the semantic scaffold contract. It is used only to prove an
 * older generated child is still byte-semantically untouched before recovery.
 */
function legacyPlanningScaffoldProjectionRevision(projection) {
    const legacyProjection = {
        artifactKind: projection.artifactKind,
        childSlug: projection.childSlug,
        criterionIds: projection.criterionIds,
        ownership: projection.ownership,
        dependencies: projection.dependencies,
        targetPaths: projection.targetPaths,
        adapterPaths: projection.adapterPaths,
        validationCommands: projection.validationCommands,
        rollback: projection.rollback,
        currentBehavior: projection.currentBehavior,
        desiredBehavior: projection.desiredBehavior,
        declaredChildCount: projection.declaredChildCount,
        declaredChildSlugs: projection.declaredChildSlugs,
        nestedEvidence: projection.nestedEvidence
    };
    return `sha256:${(0, node_crypto_1.createHash)("sha256").update(JSON.stringify(legacyProjection)).digest("hex")}`;
}
function stampPlanningScaffoldProjectionRevision(markdownText, artifactKind) {
    const revision = planningScaffoldProjectionRevision(projectPlanningScaffoldContract(markdownText, artifactKind));
    return rebindPlanningScaffoldProjectionRevision(markdownText, revision);
}
function rebindPlanningScaffoldProjectionRevision(markdownText, revision) {
    if (!/^sha256:[a-f0-9]{64}$/u.test(revision)) {
        throw new TypeError("A canonical scaffold projection revision is required.");
    }
    const lines = markdownText.split(/\r?\n/u);
    const existingIndex = lines.findIndex((line) => /^scaffold_projection_revision\s*:/u.test(line));
    if (existingIndex >= 0) {
        lines[existingIndex] = `scaffold_projection_revision: ${revision}`;
    }
    else {
        const artifactTypeIndex = lines.findIndex((line) => /^artifact_type\s*:/u.test(line));
        if (artifactTypeIndex < 0)
            return markdownText;
        lines.splice(artifactTypeIndex + 1, 0, `scaffold_projection_revision: ${revision}`);
    }
    const newline = markdownText.includes("\r\n") ? "\r\n" : "\n";
    return lines.join(newline);
}
function readPlanningScaffoldProjectionRevision(markdownText) {
    return readTopLevelFrontMatter(markdownText).get("scaffold_projection_revision") ?? null;
}
function normalizedSectionValues(sections, names) {
    return uniqueStrings(names.flatMap((name) => sections.get(name) ?? [])
        .map(normalizeProjectionValue)
        .filter((value) => value !== ""));
}
function normalizedMarkdownListValues(lines) {
    return uniqueStrings((0, planning_document_utils_1.parseMarkdownListItems)(lines)
        .map(normalizeProjectionValue)
        .filter((value) => value !== ""));
}
function normalizedSectionText(sections, name) {
    const values = (sections.get(name) ?? [])
        .map(normalizeProjectionValue)
        .filter((value) => value !== "");
    return values.length === 0 ? null : values.join(" ");
}
function normalizeProjectionValue(value) {
    return value.trim()
        .replace(/^```[A-Za-z0-9_-]*$/u, "")
        .replace(/^[-*+]\s+/u, "")
        .replace(/^\d+[.)]\s+/u, "")
        .replace(/^`(.+)`$/u, "$1")
        .replace(/^\[([^\]]+)\]\([^)]*\)$/u, "$1")
        .replace(/[ \t]+/gu, " ")
        .trim();
}
function declaredTargetCount(lines) {
    for (const line of lines) {
        const match = line.match(/Target\s+(?:phase|milestone|task)\s+count\s*:\s*(\d+)/iu);
        if (match !== null)
            return Number.parseInt(match[1], 10);
    }
    return null;
}
function acceptanceCriterionIdsFromValue(value) {
    return [...value.matchAll(/\b([A-Za-z0-9_-]+-AC-\d+)\b/gu)].map((match) => match[1]);
}
function isLikelyAdapterPath(value) {
    return !/^(?:tests|tests_v2)\//u.test(value)
        && /(?:^|\/)(?:cli|commands?)(?:\/|$)|command-capabilities|automation-protocol|(?:command|cli)[-_]?manifest/iu.test(value);
}
function compareScalarField(drift, field, expected, observed) {
    if (expected === observed)
        return;
    drift.push({
        field,
        kind: expected === null || expected === undefined
            ? "extra"
            : observed === null || observed === undefined
                ? "missing"
                : "changed",
        expected,
        observed
    });
}
function compareArrayField(drift, field, expected, observed) {
    if (expected.length === observed.length
        && expected.every((value, index) => value === observed[index]))
        return;
    const expectedSet = new Set(expected);
    const observedSet = new Set(observed);
    const sameMembers = expected.length === observed.length
        && expected.every((value) => observedSet.has(value))
        && observed.every((value) => expectedSet.has(value));
    const kind = sameMembers
        ? "reordered"
        : expected.every((value) => observedSet.has(value))
            ? "extra"
            : observed.every((value) => expectedSet.has(value))
                ? "missing"
                : "changed";
    drift.push({ field, kind, expected: [...expected], observed: [...observed] });
}
const SECTION_POLICIES = {
    slice_overview: [
        { sectionName: "Purpose", sectionType: "purpose", intentCategory: "prose" },
        { sectionName: "Desired Outcome", sectionType: "general", intentCategory: "runtime-behavior" },
        { sectionName: "Scope", sectionType: "scope", intentCategory: "prose" },
        { sectionName: "Phases", sectionType: "milestones", intentCategory: "runtime-behavior" }
    ],
    phase_overview: [
        { sectionName: "Purpose", sectionType: "purpose", intentCategory: "prose" },
        { sectionName: "Scope", sectionType: "scope", intentCategory: "prose" },
        { sectionName: "Milestones", sectionType: "milestones", intentCategory: "runtime-behavior" },
        { sectionName: "Acceptance Criteria", sectionType: "general", intentCategory: "runtime-behavior" }
    ],
    milestone_overview: [
        { sectionName: "Purpose", sectionType: "purpose", intentCategory: "prose" },
        { sectionName: "Scope", sectionType: "scope", intentCategory: "prose" },
        { sectionName: "Tasks", sectionType: "tasks", intentCategory: "runtime-behavior" },
        { sectionName: "Acceptance Criteria", sectionType: "general", intentCategory: "runtime-behavior" }
    ],
    task_definition: [
        { sectionName: "Objective", sectionType: "task-body", intentCategory: "runtime-behavior" },
        { sectionName: "Current Behavior", sectionType: "task-body", intentCategory: "prose" },
        { sectionName: "Desired Behavior", sectionType: "task-body", intentCategory: "runtime-behavior" },
        { sectionName: "Acceptance Criteria", sectionType: "task-body", intentCategory: "runtime-behavior" },
        { sectionName: "Constraints", sectionType: "task-body", intentCategory: "prose" },
        { sectionName: "Lifecycle / Closure Expectations", sectionType: "task-body", intentCategory: "evidence" }
    ],
    implementation_summary: [
        { sectionName: "Summary", sectionType: "general", intentCategory: "evidence" },
        { sectionName: "Acceptance Criteria Results", sectionType: "general", intentCategory: "evidence" }
    ],
    reconciliation: [
        { sectionName: "Milestone Intent", sectionType: "general", intentCategory: "review" },
        { sectionName: "Acceptance Criteria Review", sectionType: "general", intentCategory: "review" }
    ]
};
const DECOMPOSITION_BOUNDARY_PATTERNS = [
    /\bimplement(?:s|ed|ing|ation|ations)?\b/u,
    /\bdepend(?:s|ed|ing|ent|ents|ence|ences|ency|encies)?\b/u,
    /\bvalidat(?:e|es|ed|ing|ion|ions)\b/u,
    /\b(?:rollback(?:s)?|roll(?:s|ed|ing)?\s+back)\b/u,
    /\bown(?:s|ed|ing|er|ers|ership)?\b/u
];
function planningAuthoringSectionPolicies(artifactType) {
    return SECTION_POLICIES[artifactType];
}
function auditPlanningArtifactAuthoring(options) {
    const issues = [];
    const verbViolations = (0, verb_policy_1.auditDisallowedDefineUsage)({
        markdownText: options.markdownText,
        sectionPolicies: planningAuthoringSectionPolicies(options.artifactType)
    });
    issues.push(...verbViolations.map((violation) => planningVerbIssue(options, violation)));
    const frontMatter = readTopLevelFrontMatter(options.markdownText);
    const provenanceIssues = (0, workflow_provenance_1.inspectPlanningWorkflowProvenance)({
        artifactType: options.artifactType,
        workflowProvenance: frontMatter.get("workflow_provenance") ?? "",
        workflowCliCommand: frontMatter.get("workflow_cli_command") ?? "",
        workflowManualException: frontMatter.get("workflow_manual_exception") ?? "",
        allowLegacyManualAlias: options.allowLegacyManualAlias === true
    });
    issues.push(...provenanceIssues
        .filter((issue) => !(options.allowMissingProvenance === true && issue.code === "PLANNING_WORKFLOW_PROVENANCE_MISSING"))
        .map((issue) => planningProvenanceIssue(options, issue)));
    return issues;
}
function auditParentDecomposition(options) {
    return inspectParentDecomposition(options).issues;
}
function inspectParentDecomposition(options) {
    const label = `${options.childKind}`;
    const escapedLabel = escapeRegExp(label);
    const countMatch = options.markdownText.match(new RegExp(`Target\\s+${escapedLabel}\\s+count:\\s*(\\d+)`, "i"));
    const proseRationale = readProseDecompositionRationale(options.markdownText);
    const semantic = readSemanticDecompositionEvidence(options.markdownText, options.childKind);
    const targetCount = semantic.targetCount
        ?? (countMatch === null ? null : Number.parseInt(countMatch[1], 10));
    const rationale = semantic.rationale ?? proseRationale;
    const evidenceKinds = semantic.evidenceKinds.length > 0
        ? semantic.evidenceKinds
        : decompositionEvidenceKinds(rationale);
    const source = semantic.source !== "missing"
        ? semantic.source
        : rationale === null
            ? "missing"
            : "prose";
    const issues = [];
    if (targetCount === null) {
        issues.push({
            code: "PLANNING_DECOMPOSITION_TARGET_COUNT_MISSING",
            artifactPath: options.artifactPath,
            childKind: options.childKind,
            reason: `Parent must state 'Target ${label} count: N' before ${label} scaffolding.`
        });
    }
    if (rationale === null || isPlaceholderRationale(rationale)) {
        issues.push({
            code: "PLANNING_DECOMPOSITION_RATIONALE_MISSING",
            artifactPath: options.artifactPath,
            childKind: options.childKind,
            reason: `Parent must state an authored decomposition rationale before ${label} scaffolding.`
        });
    }
    if (targetCount !== null) {
        if (targetCount !== options.declaredChildSlugs.length) {
            issues.push({
                code: "PLANNING_DECOMPOSITION_COUNT_CONTRADICTION",
                artifactPath: options.artifactPath,
                childKind: options.childKind,
                reason: `Target ${label} count ${targetCount} contradicts ${options.declaredChildSlugs.length} declared ${label} slug${options.declaredChildSlugs.length === 1 ? "" : "s"}.`
            });
        }
    }
    if (rationale !== null && !isPlaceholderRationale(rationale)) {
        if (evidenceKinds.length === 0) {
            issues.push({
                code: "PLANNING_DECOMPOSITION_RATIONALE_PATTERN_DERIVED",
                artifactPath: options.artifactPath,
                childKind: options.childKind,
                reason: "Decomposition rationale must name a concrete implementation, dependency, validation, rollback, or ownership boundary; familiar counts, names, numbering, and ordering are not evidence."
            });
        }
    }
    return {
        evidence: {
            childKind: options.childKind,
            targetCount,
            rationale,
            evidenceKinds,
            source
        },
        issues
    };
}
function classifyScaffoldAdapterRequirement(options) {
    const explicitAdapterPaths = uniqueStrings(options.explicitAdapterPaths);
    const commandFacingTargetPaths = uniqueStrings(options.targetPaths.filter(isLikelyAdapterPath));
    const proseText = options.prose.join("\n");
    const commandFacingProse = [
        /\bcli\b/iu,
        /\bcommand(?:-|[ \t]+)line\b/iu,
        /\b(?:json|text)[ \t]+output\b/iu,
        /\badapter\b/iu,
        /\b(?:command|cli)[ \t-]+(?:descriptor|registration|registry|manifest|surface|entrypoint|handler)\b/iu,
        /\b(?:descriptor|registration|registry|manifest)[ \t-]+(?:for[ \t]+)?(?:the[ \t]+|a[ \t]+)?(?:command|cli)\b/iu,
        /\bregister(?:s|ed|ing)?[ \t]+(?:the[ \t]+|a[ \t]+)?(?:command|cli)\b/iu,
        /\bmanifest[ \t-]+(?:command|adapter|registration)\b/iu
    ].some((pattern) => pattern.test(proseText));
    const reasons = [];
    if (explicitAdapterPaths.length > 0)
        reasons.push("explicit-adapter-path");
    if (commandFacingTargetPaths.length > 0)
        reasons.push("command-facing-target-path");
    if (commandFacingProse)
        reasons.push("command-facing-prose");
    return {
        required: reasons.length > 0,
        reasons,
        adapterPaths: uniqueStrings([
            ...explicitAdapterPaths,
            ...commandFacingTargetPaths
        ])
    };
}
function inspectProjectedTaskScaffoldEvidence(options) {
    const adapterClassification = classifyScaffoldAdapterRequirement({
        prose: options.prose,
        targetPaths: options.targetPaths,
        explicitAdapterPaths: options.explicitAdapterPaths
    });
    const missingEvidence = [];
    if (options.ownership.length === 0)
        missingEvidence.push("ownership");
    if (options.dependencies.length === 0)
        missingEvidence.push("dependency");
    if (options.targetPaths.length === 0)
        missingEvidence.push("target");
    if (adapterClassification.required && adapterClassification.adapterPaths.length === 0) {
        missingEvidence.push("adapter");
    }
    if (options.validationCommands.length === 0)
        missingEvidence.push("validation");
    if (options.rollback.length === 0)
        missingEvidence.push("rollback");
    return {
        adapterPaths: adapterClassification.adapterPaths,
        requiredAdapter: adapterClassification.required,
        adapterRequirementReasons: adapterClassification.reasons,
        missingEvidence,
        complete: missingEvidence.length === 0
    };
}
function inspectOrderedTaskScaffoldDependencies(options) {
    const issues = [];
    const taskSequence = new Map(options.tasks.map((task, index) => [task.taskSlug, index + 1]));
    const normalizedTargets = new Map(options.tasks.map((task) => [
        task.taskSlug,
        uniqueStrings([
            ...task.targetPaths,
            ...(task.adapterPaths ?? [])
        ]).flatMap((targetPath) => {
            const normalized = normalizeScaffoldDependencyPath(targetPath);
            return normalized === null ? [] : [normalized];
        })
    ]));
    for (const [consumerIndex, task] of options.tasks.entries()) {
        const consumerSequence = consumerIndex + 1;
        for (const dependency of task.dependencies) {
            const dependencyPath = normalizeScaffoldDependencyPath(dependency);
            if (dependencyPath === null)
                continue;
            if (dependencyPath.startsWith(".day-shift/"))
                continue;
            const taskArtifactProducer = dependencyPath.match(/(?:^|\/)tasks\/([^/]+)\/(?:task-definition|implementation-summary)\.md$/u)?.[1];
            let producers = taskArtifactProducer === undefined
                ? options.tasks.filter((candidate) => normalizedTargets.get(candidate.taskSlug)?.includes(dependencyPath))
                : options.tasks.filter((candidate) => candidate.taskSlug === taskArtifactProducer);
            if (taskArtifactProducer === undefined) {
                const absoluteDependencyPath = node_path_1.default.resolve(options.repositoryRoot, dependencyPath);
                const relativeDependencyPath = node_path_1.default.relative(options.repositoryRoot, absoluteDependencyPath);
                if (relativeDependencyPath !== ""
                    && !relativeDependencyPath.startsWith(`..${node_path_1.default.sep}`)
                    && relativeDependencyPath !== ".."
                    && node_fs_1.default.existsSync(absoluteDependencyPath)) {
                    continue;
                }
            }
            producers = producers.filter((producer, index, all) => all.findIndex((candidate) => candidate.taskSlug === producer.taskSlug) === index);
            const producerTasks = producers.map((producer) => producer.taskSlug);
            const producerSequences = producerTasks.flatMap((producerTask) => {
                const sequence = taskSequence.get(producerTask);
                return sequence === undefined ? [] : [sequence];
            });
            const common = {
                consumerTask: task.taskSlug,
                dependencyPath,
                producerTasks,
                consumerSequence,
                producerSequences
            };
            if (producers.length === 0) {
                issues.push({
                    ...common,
                    code: "PLANNING_SCAFFOLD_DEPENDENCY_PRODUCER_MISSING",
                    message: `Task '${task.taskSlug}' depends on missing implementation artifact '${dependencyPath}', which is not produced by any declared sibling task.`
                });
                continue;
            }
            if (producers.length > 1) {
                issues.push({
                    ...common,
                    code: "PLANNING_SCAFFOLD_DEPENDENCY_PRODUCER_AMBIGUOUS",
                    message: `Task '${task.taskSlug}' depends on '${dependencyPath}', but sibling tasks ${producerTasks.map((entry) => `'${entry}'`).join(", ")} all claim that producer path.`
                });
                continue;
            }
            const producerSequence = producerSequences[0];
            if (producerSequence === consumerSequence) {
                issues.push({
                    ...common,
                    code: "PLANNING_SCAFFOLD_DEPENDENCY_SELF_REFERENCE",
                    message: `Task '${task.taskSlug}' depends on its own missing target '${dependencyPath}'.`
                });
                continue;
            }
            if (producerSequence > consumerSequence) {
                issues.push({
                    ...common,
                    code: "PLANNING_SCAFFOLD_DEPENDENCY_ORDER_INVALID",
                    message: `Task '${task.taskSlug}' depends on missing artifact '${dependencyPath}', but later sibling task '${producers[0].taskSlug}' is its declared producer.`
                });
            }
        }
    }
    return issues;
}
function inspectChildScaffoldEvidence(options) {
    const legacyUnscoped = options.compatibilityMode === "legacy-unscoped";
    const readScopedLines = legacyUnscoped
        ? legacyScopedSectionLines
        : scopedSectionLines;
    const readSemanticValues = legacyUnscoped
        ? legacySemanticValues
        : semanticValues;
    const sections = markdownSections(options.markdownText);
    const frontMatterEvidence = [
        ...frontMatterNestedLines(options.markdownText, "scaffold_evidence"),
        ...frontMatterNestedLines(options.markdownText, "scaffolding")
    ];
    const semanticChildKind = readSemanticValues(frontMatterEvidence, "child_kind")[0]
        ?? readSemanticValues(frontMatterEvidence, "child-kind")[0];
    const semanticChildSlug = readSemanticValues(frontMatterEvidence, "child_slug")[0]
        ?? readSemanticValues(frontMatterEvidence, "child-slug")[0];
    const matchingFrontMatterEvidence = (semanticChildKind === undefined || semanticChildKind === options.childKind)
        && (semanticChildSlug === undefined || semanticChildSlug === options.childSlug)
        ? frontMatterEvidence
        : [];
    const declarations = childDeclarationDescriptions(sections.get(childSectionName(options.childKind)) ?? []);
    const declaration = declarations.get(options.childSlug) ?? "";
    const scopedEvidence = [
        ...matchingFrontMatterEvidence,
        ...readScopedLines(sections, "Scaffold Evidence", options.childSlug),
        ...readScopedLines(sections, "Acceptance Criteria", options.childSlug)
    ];
    const globalAllowed = options.declaredChildSlugs.length === 1;
    const targetEvidence = [
        ...scopedEvidence,
        ...(globalAllowed
            ? [
                ...(sections.get("Implementation Target Paths") ?? []),
                ...(sections.get("Runtime Delta") ?? []),
                ...(sections.get("Scope") ?? [])
            ]
            : readScopedLines(sections, "Implementation Target Paths", options.childSlug))
    ];
    const validationEvidence = [
        ...scopedEvidence,
        ...(globalAllowed
            ? [
                ...(sections.get("Validation Commands") ?? []),
                ...(sections.get("Validation Focus") ?? []),
                ...(sections.get("Validation Strategy") ?? [])
            ]
            : [
                ...readScopedLines(sections, "Validation Commands", options.childSlug),
                ...readScopedLines(sections, "Validation Focus", options.childSlug),
                ...readScopedLines(sections, "Validation Strategy", options.childSlug)
            ])
    ];
    const dependencyEvidence = [
        ...scopedEvidence,
        ...(globalAllowed
            ? [...(sections.get("Dependencies") ?? [])]
            : readScopedLines(sections, "Dependencies", options.childSlug))
    ];
    const rollbackEvidence = [
        ...scopedEvidence,
        ...(globalAllowed
            ? [
                ...(sections.get("Rollback / Recovery") ?? []),
                ...(sections.get("Rollback") ?? [])
            ]
            : [
                ...readScopedLines(sections, "Rollback / Recovery", options.childSlug),
                ...readScopedLines(sections, "Rollback", options.childSlug)
            ])
    ];
    const semanticOwnership = readSemanticValues(scopedEvidence, "ownership");
    const ownership = uniqueStrings(semanticOwnership.length > 0 && !legacyUnscoped
        ? semanticOwnership
        : [
            ...semanticOwnership,
            ...(declaration === "" ? [] : [declaration])
        ]);
    const dependencies = uniqueStrings([
        ...readSemanticValues(dependencyEvidence, "dependency"),
        ...extractRepositoryPaths(dependencyEvidence.filter((line) => permitsSemanticEvidenceKind(line, ["dependency"]))).filter((entry) => entry.startsWith(".day-shift/"))
    ]);
    const targetPaths = uniqueStrings([
        ...readSemanticValues(targetEvidence, "target"),
        ...readSemanticValues(targetEvidence, "targets"),
        ...extractRepositoryPaths(targetEvidence.filter((line) => permitsSemanticEvidenceKind(line, ["target", "targets", "adapter"])))
    ]).filter((value) => (0, scaffold_target_path_policy_1.isPlanningScaffoldTargetPath)(value, options.runtimeEvidencePathPolicy));
    const validationCommands = uniqueStrings([
        ...readSemanticValues(validationEvidence, "validation"),
        ...extractExecutableCommands(validationEvidence)
    ]);
    const semanticRollback = readSemanticValues(rollbackEvidence, "rollback");
    const freeFormRollbackEvidence = legacyUnscoped
        ? rollbackEvidence
        : rollbackEvidence.filter((line) => !isSemanticEvidenceLine(line));
    const rollback = uniqueStrings([
        ...semanticRollback,
        ...normalizedEvidenceLines(freeFormRollbackEvidence)
            .filter((entry) => /\b(?:revert|restore|remove|rollback|roll back)\b/iu.test(entry))
    ]);
    const acceptanceText = scopedEvidence
        .filter((line) => {
        const normalized = line.trim().replace(/^-\s+/u, "");
        if (/^adapter\s*:/iu.test(normalized))
            return true;
        return !/^(?:target|targets|validation|dependency|rollback)\s*:/iu.test(normalized);
    })
        .join("\n");
    const explicitAdapterPaths = uniqueStrings(readSemanticValues(scopedEvidence, "adapter")).filter((value) => (0, scaffold_target_path_policy_1.isPlanningScaffoldTargetPath)(value, options.runtimeEvidencePathPolicy));
    const completeness = inspectProjectedTaskScaffoldEvidence({
        prose: [acceptanceText],
        ownership,
        dependencies,
        targetPaths,
        explicitAdapterPaths,
        validationCommands,
        rollback
    });
    return {
        childKind: options.childKind,
        childSlug: options.childSlug,
        ownership,
        dependencies,
        targetPaths,
        adapterPaths: completeness.adapterPaths,
        validationCommands,
        rollback,
        requiredAdapter: completeness.requiredAdapter,
        adapterRequirementReasons: completeness.adapterRequirementReasons,
        missingEvidence: completeness.missingEvidence,
        complete: completeness.complete
    };
}
function declaredPlanningChildSlugs(markdownText, sectionName) {
    const lines = markdownText.split(/\r?\n/);
    const sectionIndex = lines.findIndex((line) => line.trim() === `## ${sectionName}`);
    if (sectionIndex === -1) {
        return [];
    }
    const slugs = [];
    for (let index = sectionIndex + 1; index < lines.length; index += 1) {
        const line = lines[index].trim();
        if (line.startsWith("## ")) {
            break;
        }
        const declaration = (0, planning_document_utils_1.parseDeclaredChildSlugBullet)(line);
        if (declaration !== null) {
            slugs.push(declaration.slug);
        }
    }
    return slugs;
}
function formatPlanningAuthoringIssues(issues) {
    return issues.map((issue) => {
        const replacement = issue.suggestedVerb === "" ? "" : ` Suggested replacement: ${issue.suggestedVerb}.`;
        return `${issue.artifactPath} [${issue.sectionName}] ${issue.reason}${replacement}`;
    });
}
function formatParentDecompositionIssues(issues) {
    return issues.map((issue) => `${issue.artifactPath}: ${issue.reason}`);
}
function readSemanticDecompositionEvidence(markdownText, childKind) {
    const sections = markdownSections(markdownText);
    const markdownLines = sections.get("Decomposition Evidence") ?? [];
    const frontMatterLines = frontMatterNestedLines(markdownText, "decomposition");
    const selectedLines = frontMatterLines.length > 0 ? frontMatterLines : markdownLines;
    if (selectedLines.length === 0) {
        return { targetCount: null, rationale: null, evidenceKinds: [], source: "missing" };
    }
    const declaredKind = semanticValues(selectedLines, "child_kind")[0]
        ?? semanticValues(selectedLines, "child-kind")[0]
        ?? childKind;
    if (declaredKind !== childKind) {
        return { targetCount: null, rationale: null, evidenceKinds: [], source: "missing" };
    }
    const rawTargetCount = semanticValues(selectedLines, "target_count")[0]
        ?? semanticValues(selectedLines, "target-count")[0];
    const parsedTargetCount = rawTargetCount === undefined
        ? null
        : Number.parseInt(rawTargetCount, 10);
    const targetCount = parsedTargetCount !== null && Number.isInteger(parsedTargetCount)
        ? parsedTargetCount
        : null;
    const typed = ["ownership", "dependency", "validation", "rollback"]
        .flatMap((kind) => semanticValues(selectedLines, kind).length > 0 ? [kind] : []);
    const rationaleParts = typed.flatMap((kind) => semanticValues(selectedLines, kind).map((value) => `${kind}: ${value}`));
    return {
        targetCount,
        rationale: rationaleParts.length === 0 ? null : rationaleParts.join("; "),
        evidenceKinds: typed,
        source: frontMatterLines.length > 0 ? "semantic-metadata" : "normalized-markdown"
    };
}
function decompositionEvidenceKinds(rationale) {
    if (rationale === null)
        return [];
    const normalized = rationale.toLowerCase();
    const kinds = [];
    if (DECOMPOSITION_BOUNDARY_PATTERNS[0].test(normalized)
        || DECOMPOSITION_BOUNDARY_PATTERNS[4].test(normalized)) {
        kinds.push("ownership");
    }
    if (DECOMPOSITION_BOUNDARY_PATTERNS[1].test(normalized))
        kinds.push("dependency");
    if (DECOMPOSITION_BOUNDARY_PATTERNS[2].test(normalized))
        kinds.push("validation");
    if (DECOMPOSITION_BOUNDARY_PATTERNS[3].test(normalized))
        kinds.push("rollback");
    return kinds;
}
function readProseDecompositionRationale(markdownText) {
    const lines = markdownText.split(/\r?\n/u);
    for (let index = 0; index < lines.length; index += 1) {
        const match = lines[index].match(/Decomposition rationale:\s*(.*)$/iu);
        if (match === null)
            continue;
        const parts = match[1].trim() === "" ? [] : [match[1].trim()];
        for (let continuationIndex = index + 1; continuationIndex < lines.length; continuationIndex += 1) {
            const continuation = lines[continuationIndex].trim();
            if (continuation === ""
                || /^#{1,6}\s+/u.test(continuation)
                || /^[-*+]\s+/u.test(continuation)
                || /^Target\s+(?:phase|milestone|task)\s+count\s*:/iu.test(continuation)
                || /^Decomposition rationale\s*:/iu.test(continuation)) {
                break;
            }
            parts.push(continuation);
        }
        const rationale = parts.join(" ").trim();
        return rationale === "" ? null : rationale;
    }
    return null;
}
function markdownSections(markdownText) {
    const sections = new Map();
    let current = null;
    for (const line of markdownText.split(/\r?\n/)) {
        const heading = line.match(/^##\s+(.+?)\s*$/);
        if (heading !== null) {
            current = heading[1];
            sections.set(current, []);
            continue;
        }
        if (/^#\s/u.test(line)) {
            current = null;
            continue;
        }
        if (current !== null)
            sections.get(current)?.push(line);
    }
    return sections;
}
function frontMatterNestedLines(markdownText, key) {
    const lines = markdownText.split(/\r?\n/);
    if (lines[0] !== "---")
        return [];
    const closing = lines.findIndex((line, index) => index > 0 && line === "---");
    if (closing < 0)
        return [];
    const start = lines.findIndex((line, index) => index > 0 && index < closing && line === `${key}:`);
    if (start < 0)
        return [];
    const nested = [];
    for (let index = start + 1; index < closing; index += 1) {
        if (/^[^\s]/u.test(lines[index]))
            break;
        nested.push(lines[index].replace(/^\s{2}/u, ""));
    }
    return nested;
}
function childSectionName(childKind) {
    if (childKind === "phase")
        return "Phases";
    if (childKind === "milestone")
        return "Milestones";
    return "Tasks";
}
function childDeclarationDescriptions(lines) {
    const descriptions = new Map();
    for (const declaration of (0, planning_document_utils_1.parseDeclaredChildSlugBullets)(lines)) {
        descriptions.set(declaration.slug, declaration.description);
    }
    return descriptions;
}
function scopedSectionLines(sections, sectionName, childSlug) {
    const lines = sections.get(sectionName) ?? [];
    const scoped = [];
    let active = false;
    let scopeIndent = 0;
    for (const line of lines) {
        const normalized = line.trim();
        const scope = line.match(/^(\s*)-\s+(?:`([^`]+)`|\[([^\]]+)\])\s*:\s*(.*)$/u);
        if (scope !== null) {
            active = (scope[2] ?? scope[3]) === childSlug;
            scopeIndent = scope[1].length;
            if (active && scope[4] !== "")
                scoped.push(scope[4]);
            continue;
        }
        if (!active)
            continue;
        const semanticLine = line.match(/^(\s*)(?:-\s+)?[A-Za-z0-9_-]+\s*:/u);
        if (semanticLine !== null) {
            if (semanticLine[1].length === scopeIndent + 2) {
                scoped.push(normalized.replace(/^-\s+/u, ""));
            }
            continue;
        }
        if (normalized !== "" && line.length - line.trimStart().length <= scopeIndent) {
            active = false;
        }
    }
    return scoped;
}
/**
 * Reproduces the pre-scoped-evidence reader only for migration validation.
 * It intentionally admits nested semantic lines after a selected child and
 * must never be used as the current authoring contract.
 */
function legacyScopedSectionLines(sections, sectionName, childSlug) {
    const lines = sections.get(sectionName) ?? [];
    const scoped = [];
    let active = false;
    for (const line of lines) {
        const normalized = line.trim();
        const scope = normalized.match(/^-\s+(?:`([^`]+)`|\[([^\]]+)\])\s*:\s*(.*)$/u);
        if (scope !== null) {
            active = (scope[1] ?? scope[2]) === childSlug;
            if (active && scope[3] !== "")
                scoped.push(scope[3]);
            continue;
        }
        if (active && (/^\s{2,}-\s+/u.test(line) || /^\s{2,}[A-Za-z0-9_-]+:/u.test(line))) {
            scoped.push(normalized.replace(/^-\s+/u, ""));
            continue;
        }
        if (normalized !== "")
            active = false;
    }
    return scoped;
}
function semanticValues(lines, key) {
    const escaped = escapeRegExp(key);
    const values = [];
    const listValued = key === "criterion_ids" || key === "shared_criterion_ids";
    for (const line of lines) {
        const normalized = line.trim().replace(/^-\s+/u, "");
        const match = normalized.match(new RegExp(`^(?:\\[[^\\]]+\\]|\\x60[^\\x60]+\\x60\\s+)?${escaped}\\s*:\\s*(.+)$`, "iu"));
        if (match === null)
            continue;
        values.push(...(listValued ? match[1].split(/\s*[;,]\s*/u) : [match[1]])
            .map((entry) => entry.trim().replace(/^`|`$/gu, ""))
            .filter((entry) => entry !== ""));
    }
    return uniqueStrings(values);
}
function legacySemanticValues(lines, key) {
    const escaped = escapeRegExp(key);
    const values = [];
    for (const line of lines) {
        const normalized = line.trim().replace(/^-\s+/u, "");
        const match = normalized.match(new RegExp(`^(?:\\[[^\\]]+\\]|\\x60[^\\x60]+\\x60\\s+)?${escaped}\\s*:\\s*(.+)$`, "iu"));
        if (match === null)
            continue;
        values.push(...match[1]
            .split(/\s*[;,]\s*/u)
            .map((entry) => entry.trim().replace(/^`|`$/gu, ""))
            .filter((entry) => entry !== ""));
    }
    return uniqueStrings(values);
}
function isSemanticEvidenceLine(line, key) {
    const normalized = line.trim().replace(/^-\s+/u, "");
    const semanticKey = key === undefined ? "[A-Za-z0-9_-]+" : escapeRegExp(key);
    return new RegExp(`^(?:\\[[^\\]]+\\]|\\x60[^\\x60]+\\x60\\s+)?${semanticKey}\\s*:`, "iu").test(normalized);
}
function permitsSemanticEvidenceKind(line, allowedKeys) {
    const normalized = line.trim().replace(/^-\s+/u, "");
    const match = normalized.match(/^(?:\[[^\]]+\]|`[^`]+`\s+)?([A-Za-z0-9_-]+)\s*:/u);
    return match === null || allowedKeys.includes(match[1].toLowerCase());
}
function extractRepositoryPaths(lines) {
    return uniqueStrings(lines.flatMap((line) => (0, scaffold_target_path_policy_1.extractPlanningScaffoldRepositoryPaths)(line)));
}
function extractExecutableCommands(lines) {
    const commands = [];
    const prefix = "(?:pnpm|npm|npx|node|yarn|bun|cargo|go|python(?:3)?|pytest|tsc)";
    for (const line of lines) {
        const normalized = line.trim().replace(/^-\s+/u, "").replace(/^```[A-Za-z0-9_-]*$/u, "");
        if (normalized === "" || normalized === "```")
            continue;
        const direct = normalized.match(new RegExp(`^(${prefix}\\b.+)$`, "u"));
        if (direct !== null)
            commands.push(direct[1].replace(/`$/u, ""));
        for (const inline of normalized.matchAll(new RegExp(`\\x60(${prefix}\\b[^\\x60]+)\\x60`, "gu"))) {
            commands.push(inline[1].trim());
        }
    }
    return uniqueStrings(commands);
}
function normalizedEvidenceLines(lines) {
    return uniqueStrings(lines
        .map((line) => line.trim().replace(/^-\s+/u, ""))
        .filter((line) => line !== "" && line !== "```" && !line.startsWith("```")));
}
function normalizeScaffoldDependencyPath(value) {
    const candidate = value.trim().replace(/^`|`$/gu, "").replaceAll("\\", "/");
    if (candidate === ""
        || candidate.startsWith("/")
        || /\s/u.test(candidate)) {
        return null;
    }
    const normalized = node_path_1.default.posix.normalize(candidate).replace(/^\.\//u, "");
    if (normalized === ".." || normalized.startsWith("../"))
        return null;
    return normalized;
}
function normalizeChildScaffoldEvidence(evidence) {
    return {
        childKind: evidence.childKind,
        childSlug: evidence.childSlug,
        ownership: [...evidence.ownership],
        dependencies: [...evidence.dependencies],
        targetPaths: [...evidence.targetPaths],
        adapterPaths: [...evidence.adapterPaths],
        validationCommands: [...evidence.validationCommands],
        rollback: [...evidence.rollback],
        requiredAdapter: evidence.requiredAdapter,
        adapterRequirementReasons: [...evidence.adapterRequirementReasons],
        missingEvidence: [...evidence.missingEvidence],
        complete: evidence.complete
    };
}
function uniqueAdapterRequirementReasons(values) {
    return [...new Set(values)];
}
function uniqueStrings(values) {
    return [...new Set(values.map((value) => value.trim()).filter((value) => value !== ""))];
}
function planningVerbIssue(options, violation) {
    return {
        code: "PLANNING_AUTHORING_VERB_INVALID",
        artifactPath: options.artifactPath,
        artifactType: options.artifactType,
        sectionName: violation.sectionName,
        reason: `${violation.reason} Sentence: ${violation.sentence}`,
        suggestedVerb: violation.suggestedVerb
    };
}
function planningProvenanceIssue(options, issue) {
    return {
        code: issue.code,
        artifactPath: options.artifactPath,
        artifactType: options.artifactType,
        sectionName: "front matter",
        reason: issue.message,
        suggestedVerb: ""
    };
}
function readTopLevelFrontMatter(markdownText) {
    const fields = new Map();
    const lines = markdownText.split(/\r?\n/);
    if (lines[0] !== "---") {
        return fields;
    }
    for (let index = 1; index < lines.length; index += 1) {
        if (lines[index] === "---") {
            break;
        }
        const match = lines[index].match(/^([A-Za-z0-9_]+):\s*(.*)$/);
        if (match !== null) {
            fields.set(match[1], parseScalarValue(match[2]));
        }
    }
    return fields;
}
function parseScalarValue(value) {
    const trimmed = value.trim();
    if (trimmed.length >= 2 && ((trimmed.startsWith('"') && trimmed.endsWith('"')) || (trimmed.startsWith("'") && trimmed.endsWith("'")))) {
        return trimmed.slice(1, -1);
    }
    return trimmed;
}
function isPlaceholderRationale(value) {
    const normalized = value.trim().toLowerCase();
    return normalized === "" || normalized === "pending" || normalized.includes("to be planned") || normalized.includes("replace with");
}
function escapeRegExp(value) {
    return value.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
}
