/**
 * Executor Registry
 *
 * Manages registered executor instances per the executor contract v1 spec
 * (docs/contracts/executor.v1.md). Each executor registers with
 * `aiwg serve` via POST /api/v1/executors/register and then pushes
 * real-time events over WebSocket at /ws/executors/:executorId.
 *
 * This is the AIWG-side dispatch surface for the executor contract epic.
 * Executor implementations (sandbox adapter, local executor) are in sibling issues.
 *
 * @issue #1179
 * @see #1177 — executor-contract epic
 * @see #1178 — JSON Schema + conformance fixtures (schemas/executor-v1.json)
 * @see docs/contracts/executor.v1.md — authoritative prose spec
 */
import { EventEmitter } from 'events';
export declare function validateRegisterPayload(data: unknown): {
    valid: boolean;
    errors: string;
};
export declare function validateEventEnvelope(data: unknown): {
    valid: boolean;
    errors: string;
};
export declare function validateDispatchPayload(data: unknown): {
    valid: boolean;
    errors: string;
};
/** Transport endpoints as declared in the schema. */
export interface TransportEndpoints {
    rest: string;
    ws: string;
    grpc?: string;
}
/** One active mission tracked by aiwg serve. */
export interface MissionRecord {
    missionId: string;
    executorId: string;
    state: MissionState;
    createdAt: string;
    updatedAt: string;
    completedAt?: string;
    recentEvents: EventEnvelope[];
    ptySessionRef?: string;
    exitCode?: number;
    error?: string;
}
export type MissionState = 'queued' | 'assigned' | 'running' | 'paused' | 'hitl-required' | 'suspended' | 'done' | 'failed' | 'aborted';
export interface EventEnvelope {
    event: string;
    executor_id: string;
    mission_id?: string;
    ts: string;
    data?: Record<string, unknown>;
}
/** Per-executor registration record (in-memory). */
export interface ExecutorRegistration {
    /** Stable executor UUID — declared by the executor at registration time. */
    executorId: string;
    /** Optional default A2A sandbox instance id. May differ from executorId. */
    a2aInstanceId?: string;
    name: string;
    version: string;
    specVersion: string;
    transportEndpoints: TransportEndpoints;
    capabilities: string[];
    /** Bearer token issued at first registration; preserved across re-registers. */
    token: string;
    connected: boolean;
    lastEventTs?: string;
    registeredAt: string;
    disconnectedAt?: string;
    /** Non-terminal missions currently owned by this executor. */
    currentMissions: Set<string>;
    /** Live WS connection handle (set by serve.ts on WS upgrade). */
    wsConn?: WebSocketConn;
}
/** Minimal WS connection interface (duck-typed from the `ws` package). */
export interface WebSocketConn {
    readyState: number;
    send(data: string): void;
    close(code?: number, reason?: string): void;
}
/** Serializable executor summary (used in API responses). */
export interface ExecutorSummary {
    executor_id: string;
    a2a_instance_id?: string;
    name: string;
    version: string;
    spec_version: string;
    transport_endpoints: TransportEndpoints;
    capabilities: string[];
    connected: boolean;
    last_event_ts?: string;
    active_mission_count: number;
    registered_at: string;
    disconnected_at?: string;
}
/** Request body for POST /api/v1/executors/register (wire shape). */
export interface ExecutorRegisterRequest {
    executor_id: string;
    a2a_instance_id?: string;
    name: string;
    version: string;
    spec_version: string;
    transport_endpoints: TransportEndpoints;
    capabilities: string[];
}
/** Response body for 201 Created. */
export interface ExecutorRegisterResponse {
    executor_id: string;
    token: string;
    registered_at: string;
}
/** Filter criteria for executor selection (mirrors ExecutorFilter schema). */
export interface ExecutorFilter {
    /** Pin to specific executor. null = any. */
    executor_id?: string | null;
    /** Executor must advertise ALL listed capabilities. */
    capabilities?: string[];
}
/** Result of picking an executor via pickByFilter(). */
export interface ExecutorPickResult {
    executor: ExecutorRegistration;
    reason: string;
    rejected: Array<{
        executorId: string;
        reason: string;
    }>;
}
export declare function resolveExecutorIdentityStorePath(projectRootOverride?: string): string;
/**
 * ExecutorRegistry — state, auth, and identity store integration for
 * registered executor instances. Parallel to SandboxRegistry.
 *
 * Emits EventEmitter events:
 *   'executor:registered'   — { executorId, name }
 *   'executor:deregistered' — { executorId, reason }
 *   'mission:assigned'      — { missionId, executorId }
 *   'mission:state_change'  — { missionId, executorId, state, prevState }
 */
export declare class ExecutorRegistry extends EventEmitter {
    private executors;
    private missions;
    /** Persistent token store — executorId → identity record */
    private identityStore;
    constructor();
    /**
     * Register an executor. Validates payload against `register_payload` schema.
     * Returns 400-level error string on invalid payload.
     * On re-register with same executor_id: reclaims prior token (per ADR §9).
     */
    register(req: ExecutorRegisterRequest): ExecutorRegisterResponse | {
        error: string;
        status: 400;
    };
    /**
     * Deregister an executor by ID. Auth must be checked by the caller.
     * Emits 'executor:deregistered'.
     */
    deregister(executorId: string, reason?: 'graceful_shutdown' | 'operator_deleted' | 'timeout'): boolean;
    /**
     * Validate bearer token for an executor.
     */
    authenticate(executorId: string, token: string): boolean;
    /**
     * Mark the WS event stream as connected or disconnected.
     */
    setConnected(executorId: string, connected: boolean, wsConn?: WebSocketConn): void;
    /**
     * Push a message to the executor's live WS connection.
     * Returns true if sent, false if the executor has no open connection.
     */
    pushToExecutor(executorId: string, event: EventEnvelope): boolean;
    /**
     * Handle an inbound event from an executor WS connection.
     * Validates against event_envelope schema; updates mission state.
     */
    handleEvent(envelope: EventEnvelope): void;
    private appendMissionEvent;
    /**
     * Create a mission record and associate it with an executor.
     * Called by the dispatch route after forwarding succeeds.
     */
    assignMission(missionId: string, executorId: string): MissionRecord;
    /**
     * Mark a mission as failed (e.g. executor unreachable on forward).
     */
    failMission(missionId: string, error: string): void;
    /**
     * Get a mission record by ID.
     */
    getMission(missionId: string): MissionRecord | undefined;
    /**
     * Transition a mission to a requested operator state.
     * Returns false if the mission is in a terminal state or not found.
     */
    transitionMission(missionId: string, targetState: 'paused' | 'running' | 'aborted'): boolean;
    /**
     * List all executors as serializable summaries.
     */
    list(): ExecutorSummary[];
    /**
     * Get a single executor summary.
     */
    get(executorId: string): ExecutorSummary | undefined;
    /**
     * Get the raw registration record (internal use by dispatch).
     */
    getRegistration(executorId: string): ExecutorRegistration | undefined;
    /**
     * Pick the best executor matching the given filter.
     *
     * Default-selection policy (per ADR §3):
     *   1. Sandbox-first: prefer any executor with isolation:vm or isolation:container
     *   2. Local fallback: isolation:none or isolation:host
     *   3. 503 if no executor available
     *
     * `long_running: true` requires a 'resumable' capability.
     */
    pickByFilter(filter: ExecutorFilter, longRunning?: boolean): ExecutorPickResult | null;
    /** Total registered executor count. */
    get size(): number;
    /** Shut down — clear all state. */
    shutdown(): void;
}
export declare const executorRegistry: ExecutorRegistry;
//# sourceMappingURL=executor-registry.d.ts.map