import { V as ValidationError } from './errors-mje_cKOs.js';

/**
 * Dataset — versioned, sliceable, content-hashed scenario collection.
 *
 * Scenarios stop being ephemeral arrays and become first-class
 * artifacts. Every Dataset carries:
 *   - content hash (sha256 over canonicalized scenario array)
 *   - provenance (contributor, createdAt, sourceUrl)
 *   - split labels (train | dev | test | holdout)
 *   - difficulty tiers (easy | medium | hard | extreme)
 *   - tags (free-form, per-scenario)
 *
 * `Dataset.slice({ difficulty, split, holdout, seed })` returns a
 * deterministic, reproducible subset. Holdout slices are locked: you
 * can read them but `mutate` throws, which prevents "oh I'll just
 * tweak that one scenario" contamination drift.
 */
type DatasetSplit = 'train' | 'dev' | 'test' | 'holdout';
type DatasetDifficulty = 'easy' | 'medium' | 'hard' | 'extreme';
interface DatasetScenario {
    id: string;
    /** Arbitrary payload; the framework doesn't interpret it. */
    payload: unknown;
    split?: DatasetSplit;
    difficulty?: DatasetDifficulty;
    /** Canary token that MUST NOT round-trip through a correct agent output. */
    canary?: string;
    /**
     * Behavioral-canary forbidden pattern. A string OR a serialized regex
     * (`/.../flags`) that the agent under test MUST NOT emit. Used by
     * {@link import('./canary').checkBehavioralCanary | checkBehavioralCanary},
     * which inverts the contamination-style semantic: presence in the
     * agent output is a LEAK / failure, not a positive signal.
     *
     * Falls back to {@link canary} when omitted.
     */
    forbiddenPattern?: string;
    tags?: Record<string, string>;
}
interface DatasetProvenance {
    contributor?: string;
    createdAt: string;
    sourceUrl?: string;
    license?: string;
    description?: string;
    /** Monotonic human-readable version (e.g. "2026.04.20"). */
    version: string;
}
interface DatasetManifest {
    name: string;
    provenance: DatasetProvenance;
    /** sha256 hex over canonicalized scenarios. */
    contentHash: string;
    scenarioCount: number;
    splitCounts: Record<DatasetSplit, number>;
}
interface SliceOptions {
    split?: DatasetSplit;
    difficulty?: DatasetDifficulty;
    /** Number of scenarios (random sample, seeded). Omit to take all that match. */
    limit?: number;
    seed?: number;
    /** Predicate narrowing. Applied after split/difficulty filters. */
    filter?: (scenario: DatasetScenario) => boolean;
    /** If true, include scenarios marked as holdout. Default false. */
    includeHoldout?: boolean;
}

/** Locked holdouts — throws on mutate. Callers that need a mutable dataset fork it. */
declare class HoldoutLockedError extends ValidationError {
    constructor(datasetName: string);
}
declare class Dataset {
    readonly name: string;
    readonly provenance: DatasetProvenance;
    private scenarios;
    private locked;
    constructor(init: {
        name: string;
        provenance: DatasetProvenance;
        scenarios: DatasetScenario[];
        locked?: boolean;
    });
    /** All scenarios. Readonly — callers must go through `slice` or `clone`. */
    all(): readonly DatasetScenario[];
    get size(): number;
    /**
     * Deterministic sliced subset. Seed is REQUIRED when `limit` is set so
     * the same arguments always produce the same slice across machines.
     */
    slice(options?: SliceOptions): DatasetScenario[];
    /**
     * Assemble the manifest (name + provenance + content hash + counts).
     * Content hash is deterministic over canonicalized scenarios.
     */
    manifest(): Promise<DatasetManifest>;
    /** Fresh unlocked copy — for post-release forks when mutation is needed. */
    clone(overrides?: Partial<{
        name: string;
        version: string;
    }>): Dataset;
    lock(): void;
    add(scenario: DatasetScenario): void;
    remove(scenarioId: string): void;
    /**
     * Stable JSON-Lines serialization — deterministic byte-for-byte.
     * Write to disk for contamination-verifiable archives.
     */
    toJsonl(): string;
    static fromJsonl(jsonl: string, manifest: Omit<DatasetManifest, 'contentHash' | 'scenarioCount' | 'splitCounts'>): Dataset;
}
declare function hashScenarios(scenarios: DatasetScenario[]): Promise<string>;

export { type DatasetSplit as D, HoldoutLockedError as H, type SliceOptions as S, type DatasetScenario as a, Dataset as b, type DatasetManifest as c, type DatasetDifficulty as d, type DatasetProvenance as e, hashScenarios as h };
