import { describe, it, expect } from 'vitest';
import { Command } from 'commander';
import { registerQueueCommand } from './cli.js';

describe('registerQueueCommand', () => {
  function buildProgram(): Command {
    const program = new Command('mosaic');
    registerQueueCommand(program);
    return program;
  }

  it('registers a "queue" subcommand', () => {
    const program = buildProgram();
    const queueCmd = program.commands.find((c) => c.name() === 'queue');
    expect(queueCmd).toBeDefined();
  });

  it('queue has list, stats, pause, resume, jobs, drain subcommands', () => {
    const program = buildProgram();
    const queueCmd = program.commands.find((c) => c.name() === 'queue');
    expect(queueCmd).toBeDefined();

    const names = queueCmd!.commands.map((c) => c.name());
    expect(names).toContain('list');
    expect(names).toContain('stats');
    expect(names).toContain('pause');
    expect(names).toContain('resume');
    expect(names).toContain('jobs');
    expect(names).toContain('drain');
  });

  it('jobs subcommand has a "tail" subcommand', () => {
    const program = buildProgram();
    const queueCmd = program.commands.find((c) => c.name() === 'queue');
    const jobsCmd = queueCmd!.commands.find((c) => c.name() === 'jobs');
    expect(jobsCmd).toBeDefined();

    const tailCmd = jobsCmd!.commands.find((c) => c.name() === 'tail');
    expect(tailCmd).toBeDefined();
  });

  it('drain has a --yes option', () => {
    const program = buildProgram();
    const queueCmd = program.commands.find((c) => c.name() === 'queue');
    const drainCmd = queueCmd!.commands.find((c) => c.name() === 'drain');
    expect(drainCmd).toBeDefined();

    const optionNames = drainCmd!.options.map((o) => o.long);
    expect(optionNames).toContain('--yes');
  });

  it('stats accepts an optional [name] argument', () => {
    const program = buildProgram();
    const queueCmd = program.commands.find((c) => c.name() === 'queue');
    const statsCmd = queueCmd!.commands.find((c) => c.name() === 'stats');
    expect(statsCmd).toBeDefined();
    // Should not throw when called without argument
    const args = statsCmd!.registeredArguments;
    expect(args.length).toBe(1);
    expect(args[0]!.required).toBe(false);
  });
});
