"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.createCommandsManifestCommand = createCommandsManifestCommand;
const errors_1 = require("../../../lib/errors");
const output_1 = require("../../../lib/output");
async function createCommandsManifestCommand() {
    const { Command } = await import('commander');
    const command = new Command('manifest');
    command
        .description('Generate native tool descriptors from the authoritative command registry.')
        .argument('[command...]', 'Optional exact command path for a single-tool manifest.')
        .option('--include-noncallable', 'Include inspection-only metadata for descriptors outside the executable intersection.')
        .option('--input-json <json>', 'Structured request object with optional command/includeNoncallable fields.')
        .action((segments, options, commandInstance) => {
        const format = (0, output_1.resolveOutputFormat)(commandInstance.optsWithGlobals?.().format);
        if (format === null)
            throw (0, errors_1.createUsageError)('Unsupported output format for commands manifest.');
        let normalized;
        try {
            if (options.inputJson !== undefined) {
                if (segments.length > 0 || options.includeNoncallable === true) {
                    throw new Error('--input-json cannot be combined with command arguments or --include-noncallable.');
                }
                const input = (0, output_1.parseStructuredCommandInput)(options.inputJson, ['command', 'includeNoncallable']);
                normalized = normalizeManifestRequest((0, output_1.requireStringArray)(input.command, 'command', false), requireOptionalBoolean(input.includeNoncallable, 'includeNoncallable'), 'structured');
            }
            else {
                normalized = normalizeManifestRequest((0, output_1.requireStringArray)(segments, 'command', false), options.includeNoncallable === true, 'shell');
            }
        }
        catch (error) {
            throw (0, errors_1.createUsageError)(error instanceof Error ? error.message : 'Invalid commands manifest request.');
        }
        const commandName = normalized.request.command.join(' ');
        let registry = output_1.COMMAND_DESCRIPTOR_REGISTRY;
        if (commandName.length > 0) {
            const descriptor = (0, output_1.getRegisteredCommandDescriptor)(commandName);
            if (descriptor === null) {
                throw (0, errors_1.createUsageError)(`Unknown command descriptor '${commandName}'.`, [
                    `Recovery: run day-shift commands search ${JSON.stringify(commandName)} --format json.`,
                ]);
            }
            registry = [descriptor];
        }
        const runtimeCommands = (0, output_1.collectCallableCommandEvidence)(getRootCommand(commandInstance)).map((entry) => entry.command);
        const manifest = (0, output_1.createNativeToolManifest)(registry, {
            runtimeCommands,
            includeNonCallable: normalized.request.includeNoncallable || commandName.length > 0,
        });
        (0, output_1.emitSuccess)({
            command: 'commands manifest',
            format,
            data: { ...manifest, ...normalized },
            text: ({ data: projected }) => [
                `Native tool manifest: ${projected.tools.length} tool(s)`,
                ...projected.tools.map((tool) => `- ${tool.name}: ${tool.description}`),
                ...projected.inspectedNonCallable.map((descriptor) => `- ${descriptor.command}: ${descriptor.availability} (inspection only)`),
                (0, output_1.renderTerminalBoundary)({ kind: 'read-only' }),
            ].join('\n'),
        });
    });
    return command;
}
function normalizeManifestRequest(command, includeNoncallable, inputStyle) {
    const segments = Object.freeze([...command]);
    return {
        request: Object.freeze({ command: segments, includeNoncallable }),
        requestArgv: Object.freeze([
            'day-shift',
            'commands',
            'manifest',
            ...segments,
            ...(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;
}
