import Foundation

/// Launch overrides that hand gate ownership to Nucleic for a *containerized* Codex run, so Codex's
/// own approval/review layer stops shadowing gates Nucleic already owns.
///
/// Codex ships a "guardian" review layer (`features.guardian_approval`, **stable and ON by default**
/// — validated against codex-cli 0.146.0) that assesses actions including `mcp_tool_call`, and can
/// deny one outright or demand a permission grant over `permissions/requestApproval`. Nucleic's own
/// MCP tools (`host_exec`, the VM tools, `linux_container`, …) are already gated by
/// `ApprovalCoordinator` and Nucleic's UI, so for them that layer is pure interference: it fails
/// closed under `codex exec --ask-for-approval never` (no channel can grant it), and the tool comes
/// back as a bare failed `mcp_tool_call` item — no result, no reason — which the model reports to the
/// user as not being "authorized". Turning it off makes Nucleic the single gate, matching how the
/// Claude backend runs. No permission is bypassed: every tool still passes Nucleic's own gate.
///
/// Deliberately scoped to containerized runs. On a *host* run Codex's native command/file approvals
/// are not interference — they are the seam Nucleic gates commands through (`interactiveApprovals`),
/// and the container is anyway the isolation boundary that makes trusting our own gate reasonable.
public enum CodexGateOwnership {
    /// The env var carrying the per-session MCP bearer token, so it stays out of any config file.
    public static let tokenEnvVar = "NUCLEIC_MCP_TOKEN"

    /// Codex has no literal "disabled" value for an MCP server's per-call timeout. Pin it to the
    /// signed 32-bit maximum (about 68 years), the same effectively-unbounded value Nucleic uses
    /// for Claude's `MCP_TOOL_TIMEOUT`. Nucleic-owned tools include human approvals and long-running
    /// host/VM/container commands; their lifetime is controlled by Nucleic and the user, not by the
    /// agent client's default timeout.
    public static let toolTimeoutSeconds = 2_147_483_647

    /// Global `codex` args (before the `exec`/`app-server` subcommand) that strip Codex's review
    /// layer for a containerized run. `-c features.<name>=<bool>` is Codex's documented feature
    /// override (the same thing `--disable <FEATURE>` writes).
    public static let launchArgs: [String] = ["-c", "features.guardian_approval=false"]

    /// Global `codex` args pointing Codex at Nucleic's per-container MCP endpoint: streamable HTTP
    /// over the in-guest control bridge, authenticated by the bearer token read from
    /// ``tokenEnvVar``, with the server's tools pre-approved.
    ///
    /// `default_tools_approval_mode` (`auto | prompt | writes | approve`) defaults to `auto`, which
    /// routes every call on this server back through the approval layer above — the second half of
    /// the same interference, and the half that survives even when the guardian is off. `approve`
    /// pre-approves the `nucleic` server specifically; nothing else is affected. `tool_timeout_sec`
    /// is effectively unbounded because these calls may legitimately wait on a person or a lengthy
    /// build; the tool implementations retain their own operation-specific bounds where needed.
    public static func nucleicMCPArgs(port: UInt16) -> [String] {
        [
            "-c", "mcp_servers.nucleic.url=\"http://127.0.0.1:\(port)/mcp\"",
            "-c", "mcp_servers.nucleic.bearer_token_env_var=\"\(tokenEnvVar)\"",
            "-c", "mcp_servers.nucleic.default_tools_approval_mode=\"approve\"",
            "-c", "mcp_servers.nucleic.tool_timeout_sec=\(toolTimeoutSeconds)",
        ]
    }
}
