/**
 * CLI package sub-commands: install, remove, update, list.
 *
 * Self-contained — only called from main.ts when the first CLI arg
 * matches a package command name.
 */
import chalk from 'chalk';
import { DefaultPackageManager } from '../app/resources/package-manager.js';
import { SettingsManager } from '../app/settings-manager.js';
import { APP_NAME, getAgentDir } from '../config.js';
import { reportSettingsErrors } from './report-settings-errors.js';
function getPackageCommandUsage(command) {
    switch (command) {
        case 'install':
            return `${APP_NAME} install <source> [-l]`;
        case 'remove':
            return `${APP_NAME} remove <source> [-l]`;
        case 'update':
            return `${APP_NAME} update [source]`;
        case 'list':
            return `${APP_NAME} list`;
    }
}
function printPackageCommandHelp(command) {
    switch (command) {
        case 'install':
            console.log(`${chalk.bold('Usage:')}
  ${getPackageCommandUsage('install')}

Install a package and add it to settings.

Options:
  -l, --local    Install project-locally (.pi/settings.json)

Examples:
  ${APP_NAME} install npm:@foo/bar
  ${APP_NAME} install git:github.com/user/repo
  ${APP_NAME} install git:git@github.com:user/repo
  ${APP_NAME} install https://github.com/user/repo
  ${APP_NAME} install ssh://git@github.com/user/repo
  ${APP_NAME} install ./local/path
`);
            return;
        case 'remove':
            console.log(`${chalk.bold('Usage:')}
  ${getPackageCommandUsage('remove')}

Remove a package and its source from settings.

Options:
  -l, --local    Remove from project settings (.pi/settings.json)

Example:
  ${APP_NAME} remove npm:@foo/bar
`);
            return;
        case 'update':
            console.log(`${chalk.bold('Usage:')}
  ${getPackageCommandUsage('update')}

Update installed packages.
If <source> is provided, only that package is updated.
`);
            return;
        case 'list':
            console.log(`${chalk.bold('Usage:')}
  ${getPackageCommandUsage('list')}

List installed packages from user and project settings.
`);
            return;
    }
}
function parsePackageCommand(args) {
    const [command, ...rest] = args;
    if (command !== 'install' && command !== 'remove' && command !== 'update' && command !== 'list') {
        return undefined;
    }
    let local = false;
    let help = false;
    let invalidOption;
    let source;
    for (const arg of rest) {
        if (arg === '-h' || arg === '--help') {
            help = true;
            continue;
        }
        if (arg === '-l' || arg === '--local') {
            if (command === 'install' || command === 'remove') {
                local = true;
            }
            else {
                invalidOption = invalidOption ?? arg;
            }
            continue;
        }
        if (arg.startsWith('-')) {
            invalidOption = invalidOption ?? arg;
            continue;
        }
        if (!source) {
            source = arg;
        }
    }
    return { command, source, local, help, invalidOption };
}
export async function handlePackageCommand(args) {
    const options = parsePackageCommand(args);
    if (!options) {
        return false;
    }
    if (options.help) {
        printPackageCommandHelp(options.command);
        return true;
    }
    if (options.invalidOption) {
        console.error(chalk.red(`Unknown option ${options.invalidOption} for "${options.command}".`));
        console.error(chalk.dim(`Use "${APP_NAME} --help" or "${getPackageCommandUsage(options.command)}".`));
        process.exitCode = 1;
        return true;
    }
    const source = options.source;
    if ((options.command === 'install' || options.command === 'remove') && !source) {
        console.error(chalk.red(`Missing ${options.command} source.`));
        console.error(chalk.dim(`Usage: ${getPackageCommandUsage(options.command)}`));
        process.exitCode = 1;
        return true;
    }
    const cwd = process.cwd();
    const agentDir = getAgentDir();
    const settingsManager = SettingsManager.create(cwd, agentDir);
    reportSettingsErrors(settingsManager, 'package command');
    const packageManager = new DefaultPackageManager({ cwd, agentDir, settingsManager });
    packageManager.setProgressCallback((event) => {
        if (event.type === 'start') {
            process.stdout.write(chalk.dim(`${event.message}\n`));
        }
    });
    try {
        switch (options.command) {
            case 'install':
                await packageManager.install(source, { local: options.local });
                packageManager.addSourceToSettings(source, { local: options.local });
                console.log(chalk.green(`Installed ${source}`));
                return true;
            case 'remove': {
                await packageManager.remove(source, { local: options.local });
                const removed = packageManager.removeSourceFromSettings(source, { local: options.local });
                if (!removed) {
                    console.error(chalk.red(`No matching package found for ${source}`));
                    process.exitCode = 1;
                    return true;
                }
                console.log(chalk.green(`Removed ${source}`));
                return true;
            }
            case 'list': {
                const globalSettings = settingsManager.getGlobalSettings();
                const projectSettings = settingsManager.getProjectSettings();
                const globalPackages = globalSettings.packages ?? [];
                const projectPackages = projectSettings.packages ?? [];
                if (globalPackages.length === 0 && projectPackages.length === 0) {
                    console.log(chalk.dim('No packages installed.'));
                    return true;
                }
                const formatPackage = (pkg, scope) => {
                    const source = typeof pkg === 'string' ? pkg : pkg.source;
                    const filtered = typeof pkg === 'object';
                    const display = filtered ? `${source} (filtered)` : source;
                    console.log(`  ${display}`);
                    const path = packageManager.getInstalledPath(source, scope);
                    if (path) {
                        console.log(chalk.dim(`    ${path}`));
                    }
                };
                if (globalPackages.length > 0) {
                    console.log(chalk.bold('User packages:'));
                    for (const pkg of globalPackages) {
                        formatPackage(pkg, 'user');
                    }
                }
                if (projectPackages.length > 0) {
                    if (globalPackages.length > 0)
                        console.log();
                    console.log(chalk.bold('Project packages:'));
                    for (const pkg of projectPackages) {
                        formatPackage(pkg, 'project');
                    }
                }
                return true;
            }
            case 'update':
                await packageManager.update(source);
                if (source) {
                    console.log(chalk.green(`Updated ${source}`));
                }
                else {
                    console.log(chalk.green('Updated packages'));
                }
                return true;
        }
    }
    catch (error) {
        const message = error instanceof Error ? error.message : 'Unknown package command error';
        console.error(chalk.red(`Error: ${message}`));
        process.exitCode = 1;
        return true;
    }
}
//# sourceMappingURL=package-commands.js.map