"use strict";
var __importDefault = (this && this.__importDefault) || function (mod) {
    return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const core_1 = require("@oclif/core");
const chalk_1 = __importDefault(require("chalk"));
const ora_1 = __importDefault(require("ora"));
const nest_app_1 = require("../../lib/nest-app");
const context_banner_1 = require("../../lib/context-banner");
const cli_observability_cluster_service_1 = require("../../services/cli-observability-cluster.service");
const config_storage_1 = require("../../lib/config-storage");
const prompts_1 = require("../../lib/prompts");
const vnet_provisioning_service_1 = require("../../lib/services/vnet-provisioning.service");
class EnvDestroy extends core_1.Command {
    async run() {
        const { flags } = await this.parse(EnvDestroy);
        (0, context_banner_1.printContextBanner)();
        let spinner = (0, ora_1.default)('Initializing...').start();
        try {
            // Bootstrap NestJS and get services
            const app = await (0, nest_app_1.getNestApp)();
            spinner.stop();
            console.log(chalk_1.default.red('\n⚠️  DESTROY Observability Cluster\n'));
            spinner = (0, ora_1.default)('Checking for cluster...').start();
            const observabilityService = app.get(cli_observability_cluster_service_1.CliObservabilityClusterService);
            // Find observability cluster
            const cluster = await observabilityService.getObservabilityCluster();
            if (!cluster) {
                spinner.fail('No observability cluster found');
                console.log(chalk_1.default.yellow('\n⚠️  No observability cluster exists.\n'));
                console.log(chalk_1.default.dim('Create one with:'));
                console.log(`   ${chalk_1.default.cyan('flui env create')}\n`);
                return;
            }
            spinner.succeed('Cluster found');
            // Display cluster info
            console.log(chalk_1.default.yellow('   Cluster to be deleted:\n'));
            console.log(`   ${chalk_1.default.bold('Name:')}       ${cluster.name}`);
            console.log(`   ${chalk_1.default.bold('ID:')}         ${cluster.id}`);
            console.log(`   ${chalk_1.default.bold('Status:')}     ${cluster.status}`);
            console.log(`   ${chalk_1.default.bold('Region:')}     ${cluster.region}`);
            console.log(`   ${chalk_1.default.bold('Nodes:')}      ${cluster.nodeCount}`);
            if (cluster.sharedStorageVolumeId) {
                console.log(`   ${chalk_1.default.bold('Shared storage:')} ${chalk_1.default.red(`${cluster.sharedStorageVolumeSizeGb ?? '?'} GB`)} (volume ${cluster.sharedStorageVolumeId} will be deleted)`);
            }
            console.log(chalk_1.default.red('\n   ⚠️  ALL DATA WILL BE PERMANENTLY LOST!'));
            console.log(chalk_1.default.dim('   Cluster compute, attached block volumes and shared NFS storage are deleted at the provider.'));
            console.log(chalk_1.default.dim('   Data survives destroy ONLY if covered by an active backup policy (S3-backed Velero / app backups).\n'));
            // Confirmation prompt: user must type the cluster name verbatim
            if (!flags.force) {
                console.log('');
                console.log(chalk_1.default.yellow(`   To confirm, type the cluster name exactly: ${chalk_1.default.bold(cluster.name)}`));
                const confirmed = await (0, prompts_1.confirmByTypingPrompt)(chalk_1.default.yellow('⚠️  Cluster name'), cluster.name);
                if (!confirmed) {
                    console.log(chalk_1.default.green('\n✅ Deletion cancelled (name did not match)\n'));
                    return;
                }
            }
            // Delete cluster (servers will be fully deleted before firewall cleanup)
            console.log('');
            spinner = (0, ora_1.default)({
                text: 'Deleting cluster resources...',
                color: 'yellow',
            }).start();
            try {
                await observabilityService.deleteObservabilityCluster();
                spinner.succeed('All cluster resources deleted successfully');
            }
            catch (error) {
                spinner.fail('Cluster deletion encountered an error');
                throw error;
            }
            // Clean up observability-cluster-registration from config.json
            spinner = (0, ora_1.default)('Cleaning up configuration...').start();
            try {
                const configStorage = new config_storage_1.ConfigStorage();
                const config = configStorage['readConfig']();
                if (config.credentials?.['observability-cluster-registration']) {
                    delete config.credentials['observability-cluster-registration'];
                    configStorage['writeConfig'](config);
                    spinner.succeed('Configuration cleaned up');
                }
                else {
                    spinner.info('No registration to clean up');
                }
            }
            catch (error) {
                spinner.warn(`Failed to clean up configuration: ${error.message}`);
                console.log(chalk_1.default.yellow('   This is not critical, continuing...'));
            }
            // Tear down environment VNet/Subnet (must run AFTER all servers are deleted —
            // Hetzner refuses to delete a network that still has attached servers).
            try {
                spinner = (0, ora_1.default)('Removing environment VNet...').start();
                const vnetService = app.get(vnet_provisioning_service_1.VnetProvisioningService);
                await vnetService.destroyEnvVnet();
                spinner.succeed('Environment VNet removed');
            }
            catch (error) {
                spinner.warn(`VNet teardown failed: ${error.message}`);
                console.log(chalk_1.default.yellow('   You may need to delete the VNet manually from the Hetzner console.'));
            }
            console.log(chalk_1.default.green('\n✅ Observability Cluster Deleted Successfully\n'));
            console.log(chalk_1.default.dim('   All cluster resources have been removed:'));
            console.log(chalk_1.default.dim('   • Servers (master and worker nodes)'));
            console.log(chalk_1.default.dim('   • Firewalls and security rules'));
            console.log(chalk_1.default.dim('   • Environment VNet/Subnet'));
            console.log(chalk_1.default.dim('   • SSH keys and bootstrap credentials'));
            console.log(chalk_1.default.dim('   • Local configuration\n'));
        }
        catch (error) {
            spinner.fail('Failed to destroy cluster');
            console.log(chalk_1.default.red('\n❌ Error:\n'));
            if (error instanceof Error) {
                console.log(`   ${error.message}`);
                if (error.message.includes('not found')) {
                    console.log(chalk_1.default.yellow('\n💡 Hint:'));
                    console.log(`   The cluster may have already been deleted.`);
                    console.log(`   Check with: ${chalk_1.default.cyan('flui env status')}\n`);
                }
            }
            else {
                console.log(`   ${String(error)}`);
            }
            this.exit(1);
        }
        finally {
            await (0, nest_app_1.closeNestApp)();
        }
    }
}
EnvDestroy.description = 'Permanently delete observability cluster (WARNING: All data will be lost!)';
EnvDestroy.examples = [
    '<%= config.bin %> <%= command.id %>',
    '<%= config.bin %> <%= command.id %> --force',
];
EnvDestroy.flags = {
    force: core_1.Flags.boolean({
        char: 'f',
        description: 'Skip confirmation prompt',
        default: false,
    }),
};
exports.default = EnvDestroy;
