/**
 * wallet.ts — VigCoin wallet management for Vigthoria CLI.
 *
 *   vigthoria wallet balance          — show current balance
 *   vigthoria wallet history [--n 20] — recent transactions
 *   vigthoria wallet cloud-status     — show cloud access and model pricing
 */
import chalk from 'chalk';
import { Config } from '../utils/config.js';
import { Logger } from '../utils/logger.js';
export class WalletCommand {
    config;
    logger;
    constructor() {
        this.config = new Config();
        this.logger = new Logger();
    }
    register(program) {
        const wallet = program
            .command('wallet')
            .description('Inspect monetary Vigthoria Credits used for Cloud, API, Video, and other PAYG services');
        wallet
            .command('balance')
            .description('Show purchased and paid-subscription credit balances')
            .option('--json', 'Emit machine-readable JSON output', false)
            .action(async (options) => this.showBalance(options));
        wallet
            .command('history')
            .description('Show monetary wallet transactions')
            .option('-n, --n <count>', 'Maximum transactions to show', '20')
            .option('--json', 'Emit machine-readable JSON output', false)
            .action(async (options) => this.showHistory({
            n: Number(options.n || 20),
            json: options.json,
        }));
        wallet
            .command('cloud-status')
            .description('Show PAYG cloud eligibility and model pricing')
            .option('--json', 'Emit machine-readable JSON output', false)
            .action(async (options) => this.showCloudStatus(options));
        wallet.action(async () => this.showBalance());
    }
    getBaseUrl() {
        return String(this.config.get('apiUrl') || 'https://coder.vigthoria.io').replace(/\/$/, '');
    }
    getToken() {
        return this.config.get('authToken') || null;
    }
    getRefreshToken() {
        return this.config.get('refreshToken') || null;
    }
    async refreshAccessToken() {
        const refreshToken = this.getRefreshToken();
        if (!refreshToken)
            return false;
        try {
            const response = await fetch(`${this.getBaseUrl()}/api/token/refresh`, {
                method: 'POST',
                headers: { 'Content-Type': 'application/json' },
                body: JSON.stringify({ refresh_token: refreshToken }),
            });
            if (!response.ok)
                return false;
            const payload = await response.json();
            const nextToken = payload.token || payload.access_token;
            if (!nextToken)
                return false;
            this.config.set('authToken', nextToken);
            if (payload.refresh_token) {
                this.config.set('refreshToken', payload.refresh_token);
            }
            return true;
        }
        catch {
            return false;
        }
    }
    async parseResponseBody(resp) {
        const raw = await resp.text();
        if (!raw.trim())
            return {};
        try {
            return JSON.parse(raw);
        }
        catch {
            return { error: raw.slice(0, 240) };
        }
    }
    async apiFetch(path) {
        const url = `${this.getBaseUrl()}${path}`;
        const runRequest = async (token) => fetch(url, {
            headers: {
                Authorization: `Bearer ${token}`,
                Cookie: `vigthoria-auth-token=${token}`,
            },
        });
        let token = this.getToken();
        if (!token)
            throw new Error('Not authenticated. Run: vigthoria login');
        let resp = await runRequest(token);
        if (resp.status === 401 || resp.status === 403) {
            const refreshed = await this.refreshAccessToken();
            if (refreshed) {
                token = this.getToken();
                if (token) {
                    resp = await runRequest(token);
                }
            }
        }
        const body = await this.parseResponseBody(resp);
        if (!resp.ok) {
            const err = body.error
                || body.message
                || `HTTP ${resp.status}`;
            throw new Error(err);
        }
        return body;
    }
    async showBalance(opts = {}) {
        try {
            const data = await this.apiFetch('/api/user/vigcoin/balance');
            if (opts.json) {
                console.log(JSON.stringify(data, null, 2));
                return;
            }
            console.log('');
            console.log(chalk.bold.cyan('  Vigthoria PAYG Wallet'));
            console.log(chalk.gray('  ─────────────────────────────'));
            console.log(`  PAYG balance:          ${chalk.bold.yellow(data.balance.toLocaleString())} credits`);
            const purchased = Number(data.purchasedBalance || 0);
            const subscription = Number(data.subscriptionBalance || 0);
            console.log(`  Purchased:             ${chalk.green(purchased.toLocaleString())} credits`);
            console.log(`  Paid subscription:     ${chalk.cyan(subscription.toLocaleString())} credits`);
            console.log(`  Lifetime funded:       ${chalk.green(data.lifetimeEarned.toLocaleString())} credits`);
            console.log(`  Lifetime PAYG spend:   ${chalk.red(data.lifetimeSpent.toLocaleString())} credits`);
            if (data.lastUpdated) {
                console.log(`  Last updated:    ${chalk.gray(new Date(data.lastUpdated).toLocaleString())}`);
            }
            console.log('');
            console.log(chalk.gray('  Music Points and other promotional rewards are product-only and are not included.'));
            console.log(chalk.gray('  Top up monetary credits at: https://hub.vigthoria.io/credits'));
            console.log('');
        }
        catch (err) {
            this.logger.error(err.message);
            process.exit(1);
        }
    }
    async showHistory(opts = {}) {
        const limit = Math.max(1, Math.min(100, opts.n || 20));
        try {
            const data = await this.apiFetch(`/api/user/vigcoin/transactions?limit=${limit}`);
            if (opts.json) {
                console.log(JSON.stringify(data, null, 2));
                return;
            }
            const txs = data.transactions || [];
            console.log('');
            console.log(chalk.bold.cyan(`  VigCoin Transaction History (last ${txs.length})`));
            console.log(chalk.gray('  ──────────────────────────────────────────────────────────'));
            if (txs.length === 0) {
                console.log(chalk.gray('  No transactions found.'));
            }
            else {
                for (const tx of txs) {
                    const sign = tx.amount >= 0 ? chalk.green(`+${tx.amount}`) : chalk.red(String(tx.amount));
                    const date = new Date(tx.created_at).toLocaleString();
                    const desc = tx.description || tx.action || tx.type;
                    console.log(`  ${chalk.gray(date)}  ${sign.padStart(8)} ⓥ  ${chalk.gray(`→`)} ${chalk.yellow(tx.balance_after)} ⓥ  ${desc}`);
                }
            }
            console.log('');
        }
        catch (err) {
            this.logger.error(err.message);
            process.exit(1);
        }
    }
    async showCloudStatus(opts = {}) {
        try {
            const data = await this.apiFetch('/api/user/cloud-access/status');
            if (opts.json) {
                console.log(JSON.stringify(data, null, 2));
                return;
            }
            console.log('');
            console.log(chalk.bold.cyan('  Cloud Access Status'));
            console.log(chalk.gray('  ─────────────────────────────'));
            if (data.isMasterAdmin) {
                console.log(`  Access: ${chalk.bold.green('Master Admin — unlimited cloud access')}`);
            }
            else if (data.cloudAccessAllowed) {
                console.log(`  Access: ${chalk.yellow('Pay as you go — explicit selection and wallet credits required')}`);
                console.log(`  Balance: ${chalk.bold.yellow(Number(data.balance || 0).toLocaleString())} ⓥ`);
                if (data.hasGrant) {
                    console.log(chalk.gray('  Model grant: active (billing still applies)'));
                }
            }
            else {
                console.log(`  Access: ${chalk.red('Unavailable for this account')}`);
            }
            console.log('');
            if (data.cloudModels) {
                console.log(chalk.bold('  Cloud Model Pricing'));
                console.log(chalk.gray('  ─────────────────────────────'));
                for (const [alias, cost] of Object.entries(data.cloudModels)) {
                    const displayName = alias.replace('vigthoria-cloud-', '').replace(/\b\w/g, c => c.toUpperCase());
                    console.log(`  ${chalk.cyan(`vigthoria-cloud-${displayName.toLowerCase()}`).padEnd(36)}  ${chalk.yellow(String(cost))} credits minimum reserve, then token-priced`);
                }
                console.log('');
                console.log(chalk.gray('  Use --model vigthoria-cloud-fast|balanced|code|power|maximum in vigthoria chat'));
            }
            console.log('');
        }
        catch (err) {
            this.logger.error(err.message);
            process.exit(1);
        }
    }
}
