"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.createCommandsSearchCommand = createCommandsSearchCommand;
const errors_1 = require("../../../lib/errors");
const output_1 = require("../../../lib/output");
async function createCommandsSearchCommand() {
    const { Command } = await import("commander");
    const command = new Command("search");
    command
        .description("Search authoritative command descriptors with bounded deterministic results.")
        .argument("[query]", "Command identity, intent, capability, family, authorization, or posture query.")
        .option("--max-results <count>", "Maximum results from 1 to 50.", "10")
        .option("--include-noncallable", "Include reserved, planned, deprecated, and runtime-ineligible descriptors as inspection-only matches.")
        .option("--input-json <json>", "Structured request object with query and optional maxResults/includeNoncallable.")
        .action((query, options, commandInstance) => {
        const format = (0, output_1.resolveOutputFormat)(commandInstance.optsWithGlobals?.().format);
        if (format === null)
            throw (0, errors_1.createUsageError)("Unsupported output format for commands search.");
        let normalized;
        let result;
        try {
            if (options.inputJson !== undefined) {
                if (query !== undefined || options.maxResults !== String(output_1.DEFAULT_COMMAND_SEARCH_LIMIT) || options.includeNoncallable === true) {
                    throw new Error("--input-json cannot be combined with query, --max-results, or --include-noncallable.");
                }
                const input = (0, output_1.parseStructuredCommandInput)(options.inputJson, ["query", "maxResults", "includeNoncallable"]);
                const structuredQuery = (0, output_1.requireString)(input.query, "query");
                const maxResults = (0, output_1.optionalBoundedInteger)(input.maxResults, "maxResults", output_1.DEFAULT_COMMAND_SEARCH_LIMIT, 1, output_1.MAX_COMMAND_SEARCH_LIMIT);
                normalized = normalizeSearchRequest(structuredQuery, maxResults, requireOptionalBoolean(input.includeNoncallable, "includeNoncallable"), "structured");
            }
            else {
                normalized = normalizeSearchRequest((0, output_1.requireString)(query, "query"), Number(options.maxResults), options.includeNoncallable === true, "shell");
            }
            const root = getRootCommand(commandInstance);
            const runtimeCommands = (0, output_1.collectCallableCommandEvidence)(root).map((entry) => entry.command);
            result = (0, output_1.searchCommandDescriptors)(output_1.COMMAND_DESCRIPTOR_REGISTRY, normalized.request.query, normalized.request.maxResults, { includeNonCallable: normalized.request.includeNoncallable, runtimeCommands });
        }
        catch (error) {
            throw (0, errors_1.createUsageError)(error instanceof Error ? error.message : "Invalid command search request.", [
                "Recovery: provide a non-empty query and --max-results from 1 to 50."
            ]);
        }
        (0, output_1.emitSuccess)({
            command: "commands search",
            format,
            data: { ...result, ...normalized },
            text: ({ data: projected }) => [
                `Command search: ${projected.query}`,
                ...projected.matches.map((entry) => `- ${entry.command}: ${entry.summary}`),
                (0, output_1.renderTerminalBoundary)({ kind: "read-only" })
            ].join("\n")
        });
    });
    return command;
}
function normalizeSearchRequest(query, maxResults, includeNoncallable, inputStyle) {
    if (!Number.isInteger(maxResults) || maxResults < 1 || maxResults > output_1.MAX_COMMAND_SEARCH_LIMIT) {
        throw new Error(`Command search limit must be an integer from 1 to ${output_1.MAX_COMMAND_SEARCH_LIMIT}.`);
    }
    const normalizedQuery = query.trim();
    return {
        request: Object.freeze({ query: normalizedQuery, maxResults, includeNoncallable }),
        requestArgv: Object.freeze([
            "day-shift", "commands", "search", normalizedQuery,
            ...(maxResults === output_1.DEFAULT_COMMAND_SEARCH_LIMIT ? [] : ["--max-results", String(maxResults)]),
            ...(includeNoncallable ? ["--include-noncallable"] : [])
        ]),
        inputStyle
    };
}
function requireOptionalBoolean(value, field) {
    if (value === undefined)
        return false;
    if (typeof value !== "boolean")
        throw new Error(`${field} must be a boolean.`);
    return value;
}
function getRootCommand(commandInstance) {
    let root = commandInstance;
    while (root.parent !== null && root.parent !== undefined)
        root = root.parent;
    return root;
}
