import { browser, expect } from '@wdio/globals';
import { exec } from '../helpers/execute.ts';

// Phase C — Tab-Based Feature Tests (C5-C9)
// Settings panel, project health, metrics tab, context tab, files tab.

// --- Helpers ---

/** Get all project box IDs currently rendered. */
async function getProjectIds(): Promise<string[]> {
  return exec(() => {
    const boxes = document.querySelectorAll('[data-testid="project-box"]');
    return Array.from(boxes).map(
      (b) => b.getAttribute('data-project-id') ?? '',
    ).filter(Boolean);
  });
}

/** Switch to a tab in a specific project box. */
async function switchProjectTab(projectId: string, tabIndex: number): Promise<void> {
  await exec((id, idx) => {
    const box = document.querySelector(`[data-project-id="${id}"]`);
    const tabs = box?.querySelectorAll('[data-testid="project-tabs"] .ptab');
    if (tabs && tabs[idx]) (tabs[idx] as HTMLElement).click();
  }, projectId, tabIndex);
  await browser.pause(300);
}

// --- Scenario C5: Settings Panel Sections ---

describe('Scenario C5 — Settings Panel Sections', () => {
  before(async () => {
    // Close sidebar panel if open
    const panel = await browser.$('.sidebar-panel');
    if (await panel.isDisplayed().catch(() => false)) {
      await exec(() => {
        const btn = document.querySelector('.panel-close');
        if (btn) (btn as HTMLElement).click();
      });
      await browser.pause(300);
    }

    // Open settings
    await exec(() => {
      const btn = document.querySelector('[data-testid="settings-btn"]');
      if (btn) (btn as HTMLElement).click();
    });
    await browser.pause(500);
  });

  it('should show Appearance section with theme dropdown', async () => {
    const hasTheme = await exec(() => {
      const panel = document.querySelector('.sidebar-panel .settings-panel');
      if (!panel) return false;
      const text = panel.textContent ?? '';
      return text.toLowerCase().includes('theme') || text.toLowerCase().includes('appearance');
    });
    expect(hasTheme).toBe(true);
  });

  it('should show font settings (UI font and Terminal font)', async () => {
    const hasFonts = await exec(() => {
      const panel = document.querySelector('.sidebar-panel .settings-panel');
      if (!panel) return false;
      const text = panel.textContent ?? '';
      return text.toLowerCase().includes('font');
    });
    expect(hasFonts).toBe(true);
  });

  it('should show default shell setting in Agents category', async () => {
    // Switch to Agents category which contains shell settings
    const hasShell = await exec(() => {
      // Check across all settings categories
      const panel = document.querySelector('.sidebar-panel .settings-panel');
      if (!panel) return false;
      const text = panel.textContent ?? '';
      return text.toLowerCase().includes('shell') || text.toLowerCase().includes('agent');
    });
    expect(hasShell).toBe(true);
  });

  it('should have theme dropdown with many themes', async () => {
    // Click the theme dropdown
    const opened = await exec(() => {
      const btn = document.querySelector('.appearance .custom-dropdown .dropdown-btn');
      if (btn) { (btn as HTMLElement).click(); return true; }
      return false;
    });

    if (opened) {
      await browser.pause(300);
      const optionCount = await exec(() => {
        return document.querySelectorAll('.dropdown-menu .dropdown-item').length;
      });
      expect(optionCount).toBeGreaterThanOrEqual(15);

      // Close dropdown
      await exec(() => {
        const btn = document.querySelector('.appearance .custom-dropdown .dropdown-btn');
        if (btn) (btn as HTMLElement).click();
      });
      await browser.pause(200);
    }
  });

  after(async () => {
    // Close settings
    await exec(() => {
      const btn = document.querySelector('.panel-close');
      if (btn) (btn as HTMLElement).click();
    });
    await browser.pause(300);
  });
});

// --- Scenario C6: Project Health Indicators ---

describe('Scenario C6 — Project Health Indicators', () => {
  it('should show status dots on project headers', async () => {
    const hasDots = await exec(() => {
      const dots = document.querySelectorAll('.project-header .status-dot');
      return dots.length;
    });
    // At least one project should have a status dot
    expect(hasDots).toBeGreaterThanOrEqual(1);
  });

  it('should show idle status when no agents running', async () => {
    const ids = await getProjectIds();
    if (ids.length < 1) return;

    const dotColor = await exec((id) => {
      const box = document.querySelector(`[data-project-id="${id}"]`);
      const dot = box?.querySelector('.status-dot');
      if (!dot) return 'not-found';
      const style = window.getComputedStyle(dot);
      return style.backgroundColor || style.color || 'unknown';
    }, ids[0]);

    // Should have some color value (not 'not-found')
    expect(dotColor).not.toBe('not-found');
  });

  it('should show status bar agent counts', async () => {
    const counts = await exec(() => {
      const bar = document.querySelector('[data-testid="status-bar"]');
      if (!bar) return '';
      return bar.textContent ?? '';
    });
    // Should contain project count at minimum
    expect(counts).toMatch(/project|idle|running|stalled|\d/i);
  });
});

// --- Scenario C7: Metrics Tab ---

describe('Scenario C7 — Metrics Tab', () => {
  it('should show Metrics tab in project tab bar', async () => {
    const ids = await getProjectIds();
    if (ids.length < 1) return;

    const hasMetrics = await exec((id) => {
      const box = document.querySelector(`[data-project-id="${id}"]`);
      const tabs = box?.querySelectorAll('[data-testid="project-tabs"] .ptab');
      if (!tabs) return false;
      return Array.from(tabs).some(t => t.textContent?.trim().toLowerCase().includes('metric'));
    }, ids[0]);

    expect(hasMetrics).toBe(true);
  });

  it('should render Metrics panel content when tab clicked', async () => {
    const ids = await getProjectIds();
    if (ids.length < 1) return;
    const projectId = ids[0];

    // Find and click Metrics tab
    await exec((id) => {
      const box = document.querySelector(`[data-project-id="${id}"]`);
      const tabs = box?.querySelectorAll('[data-testid="project-tabs"] .ptab');
      if (!tabs) return;
      for (const tab of tabs) {
        if (tab.textContent?.trim().toLowerCase().includes('metric')) {
          (tab as HTMLElement).click();
          break;
        }
      }
    }, projectId);
    await browser.pause(500);

    const hasContent = await exec((id) => {
      const box = document.querySelector(`[data-project-id="${id}"]`);
      const panel = box?.querySelector('.metrics-panel, .metrics-tab');
      return panel !== null;
    }, projectId);

    expect(hasContent).toBe(true);

    // Switch back to Model tab
    await switchProjectTab(projectId, 0);
  });
});

// --- Scenario C8: Context Tab ---

describe('Scenario C8 — Context Tab Visualization', () => {
  it('should render Context tab with token meter', async () => {
    const ids = await getProjectIds();
    if (ids.length < 1) return;
    const projectId = ids[0];

    // Switch to Context tab (index 2)
    await switchProjectTab(projectId, 2);

    const hasContextUI = await exec((id) => {
      const box = document.querySelector(`[data-project-id="${id}"]`);
      const ctx = box?.querySelector('.context-tab, .context-stats, .token-meter, .stat-value');
      return ctx !== null;
    }, projectId);

    expect(hasContextUI).toBe(true);

    // Switch back to Model tab
    await switchProjectTab(projectId, 0);
  });
});

// --- Scenario C9: Files Tab with Editor ---

describe('Scenario C9 — Files Tab & Code Editor', () => {
  it('should render Files tab with directory tree', async () => {
    const ids = await getProjectIds();
    if (ids.length < 1) return;
    const projectId = ids[0];

    // Switch to Files tab (index 3)
    await switchProjectTab(projectId, 3);
    await browser.pause(500);

    const hasTree = await exec((id) => {
      const box = document.querySelector(`[data-project-id="${id}"]`);
      const tree = box?.querySelector('.file-tree, .directory-tree, .files-tab');
      return tree !== null;
    }, projectId);

    expect(hasTree).toBe(true);
  });

  it('should list files from the project directory', async () => {
    const ids = await getProjectIds();
    if (ids.length < 1) return;

    const fileNames = await exec((id) => {
      const box = document.querySelector(`[data-project-id="${id}"]`);
      const items = box?.querySelectorAll('.tree-name');
      return Array.from(items ?? []).map(el => el.textContent?.trim() ?? '');
    }, ids[0]);

    // Test project has README.md and hello.py
    const hasFiles = fileNames.some(f =>
      f.includes('README') || f.includes('hello') || f.includes('.py') || f.includes('.md'),
    );
    expect(hasFiles).toBe(true);

    // Switch back to Model tab
    await switchProjectTab(ids[0], 0);
  });
});
