import { describe, it, expect } from 'vitest'
import { readFileSync } from 'node:fs'
import { themeToCss } from './css'
import { makeValidPaletteSet } from './valid-theme.fixture'
import { defaultPaletteSet } from './resolve'

const baseCss = readFileSync(new URL('../base.css', import.meta.url), 'utf8')

describe('themeToCss', () => {
  const css = themeToCss(makeValidPaletteSet())

  it('emits palette-scoped explicit light + dark selector groups', () => {
    expect(css).toContain('[data-theme="fixture-theme"][data-palette="fixture-palette"][data-mode="light"]')
    expect(css).toContain('[data-theme="fixture-theme"][data-palette="fixture-palette"][data-mode="dark"]')
  })
  it('emits the system group with a prefers-color-scheme:dark block (anti-FOUC)', () => {
    expect(css).toContain('[data-theme="fixture-theme"][data-palette="fixture-palette"]:not([data-mode])')
    expect(css).toMatch(/@media\s*\(prefers-color-scheme:\s*dark\)/)
  })
  it('emits color custom props via the shared cssVarFor mapping', () => {
    expect(css).toContain('--mod-color-bg: #ffffff')        // light default
    expect(css).toContain('--mod-color-bg: #121212')        // dark
  })
  it('emits shape custom props', () => {
    expect(css).toContain('--mod-radius-sm: 0.125rem')
    expect(css).toContain('--mod-font-weight-bold: 700')
  })
  it('the system group default (un-wrapped) carries LIGHT props, the @media carries DARK', () => {
    const sysIdx = css.indexOf(':not([data-mode])')
    const mediaIdx = css.indexOf('@media', sysIdx)
    expect(sysIdx).toBeGreaterThan(-1)
    expect(mediaIdx).toBeGreaterThan(sysIdx)
    // light bg appears in the un-wrapped default block (before the @media)
    expect(css.slice(sysIdx, mediaIdx)).toContain('--mod-color-bg: #ffffff')
    // dark bg appears inside the @media block
    expect(css.slice(mediaIdx)).toContain('--mod-color-bg: #121212')
  })
})

describe('themeToCss with the shipped default palette', () => {
  const css = themeToCss(defaultPaletteSet)

  it('emits ramp alpha and contrast vars alongside semantic colors', () => {
    expect(css).toContain('--mod-accent-a1:')
    expect(css).toContain('--mod-accent-a12:')
    expect(css).toContain('--mod-accent-contrast:')
    expect(css).toContain('--mod-neutral-a1:')
    expect(css).toContain('--mod-neutral-contrast:')
  })

  it('emits color-scheme per mode', () => {
    expect(css).toContain('color-scheme: light;')
    expect(css).toContain('color-scheme: dark;')
  })
})

describe('base.css shipped defaults', () => {
  it('ships dark as the root default color-scheme and background', () => {
    expect(baseCss).toContain('color-scheme: dark;')
    expect(baseCss).toContain('--mod-color-bg: #111113;')
    expect(baseCss).toContain('--mod-color-fg: #edeef0;')
  })
})
