import { render, screen } from '@testing-library/react';
import AppIcon from './AppIcon';
import { APP_ICON_SIZE, APP_ICON_STROKE_WIDTH } from '../../config';
import { randomColor, randomText } from '@/utils';
import { DIRECTIONAL_ICONS, ICONS } from './config';

const ComponentToTest = AppIcon;

/**
 * Tests for <AppIcon/> component
 */
describe('<AppIcon/> component', () => {
  it('renders itself', () => {
    const testId = randomText(8);
    render(<ComponentToTest data-testid={testId} />);
    const svg = screen.getByTestId(testId);
    expect(svg).toBeDefined();
    expect(svg).toHaveAttribute('data-icon', 'default');
    // Lucide sizes off real width/height attributes — no 1em/fontSize indirection to work around.
    expect(svg).toHaveAttribute('height', String(APP_ICON_SIZE));
    expect(svg).toHaveAttribute('width', String(APP_ICON_SIZE));
    expect(svg).toHaveAttribute('stroke-width', String(APP_ICON_STROKE_WIDTH));
  });

  it('supports .color property', () => {
    const testId = randomText(8);
    const color = randomColor();
    render(<ComponentToTest data-testid={testId} color={color} />);
    const svg = screen.getByTestId(testId);
    expect(svg).toHaveAttribute('data-icon', 'default');
    expect(svg).toHaveStyle(`color: ${color}`);
    // The whole family is stroked, never filled — a `fill` would paint the glyph solid.
    expect(svg).toHaveAttribute('stroke', color);
    expect(svg).toHaveAttribute('fill', 'none');
  });

  it('supports .icon property', () => {
    // Verify that all icons are supported
    for (const icon of Object.keys(ICONS)) {
      const testId = randomText(8);
      render(<ComponentToTest data-testid={testId} icon={icon} />);
      const svg = screen.getByTestId(testId);
      expect(svg).toBeDefined();
      expect(svg).toHaveAttribute('data-icon', icon.toLowerCase());
    }
  });

  it('supports .size property', () => {
    const testId = randomText(8);
    const size = Math.floor(Math.random() * 128) + 1;
    render(<ComponentToTest data-testid={testId} size={size} />);
    const svg = screen.getByTestId(testId);
    expect(svg).toHaveAttribute('height', String(size));
    expect(svg).toHaveAttribute('width', String(size));
  });

  it('supports .title property', () => {
    const testId = randomText(8);
    const title = randomText(16);
    render(<ComponentToTest data-testid={testId} title={title} />);
    const svg = screen.getByTestId(testId);
    expect(svg).toBeDefined();
    expect(svg).toHaveAttribute('title', title);
  });

  it('marks only the registered directional icons for the RTL mirror', () => {
    for (const icon of Object.keys(ICONS) as Array<keyof typeof ICONS>) {
      const testId = randomText(8);
      render(<ComponentToTest data-testid={testId} icon={icon} />);
      const svg = screen.getByTestId(testId);
      // The single globals.css rule keys off this attribute — a name drifting out of
      // DIRECTIONAL_ICONS silently stops mirroring under RTL, which is invisible in review.
      expect(svg.hasAttribute('data-icon-directional')).toBe(DIRECTIONAL_ICONS.has(icon));
    }
  });
});
