import { describe, it, expect } from 'vitest'
import { computeProjection, defaultProjectionYears, type ProjectionYearInput } from '../projection'

describe('defaultProjectionYears', () => {
  it('creates n editable years from the start year with zero volume (V11 manual mode)', () => {
    const years = defaultProjectionYears(2026, 5)
    expect(years).toHaveLength(5)
    expect(years[0]).toEqual({ year: 2026, volume: 0, included: true })
    expect(years[4].year).toBe(2030)
  })
})

describe('computeProjection', () => {
  const years: ProjectionYearInput[] = [
    { year: 2026, volume: 10000, included: true },
    { year: 2027, volume: 20000, included: true },
    { year: 2028, volume: 30000, included: false }, // excluded → ignored
  ]

  it('computes gross = Δ/unit × included volume (V11 projTotals)', () => {
    const p = computeProjection(years, 1.23, 0)
    expect(p.totals.vol).toBe(30000)
    expect(p.totals.gross).toBeCloseTo(36900)
    expect(p.totals.remaining).toBeCloseTo(36900)
    expect(p.totals.nYears).toBe(2)
  })

  it('applies the defend quota only to cost increases', () => {
    const up = computeProjection(years, 1.23, 0.4)
    expect(up.totals.defended).toBeCloseTo(36900 * 0.4)
    expect(up.totals.remaining).toBeCloseTo(36900 * 0.6)

    // savings (negative delta) are never "defended away" (V11: gross>0 guard)
    const down = computeProjection(years, -0.5, 0.4)
    expect(down.totals.defended).toBe(0)
    expect(down.totals.remaining).toBeCloseTo(-15000)
  })

  it('produces per-year rows with cumulative remaining for the chart', () => {
    const p = computeProjection(years, 1.0, 0.5)
    expect(p.perYear).toHaveLength(3)
    expect(p.perYear[0]).toMatchObject({ year: 2026, remaining: 5000, cumRemaining: 5000 })
    expect(p.perYear[1]).toMatchObject({ year: 2027, remaining: 10000, cumRemaining: 15000 })
    // excluded year contributes nothing but keeps its place
    expect(p.perYear[2]).toMatchObject({ year: 2028, gross: 0, remaining: 0, cumRemaining: 15000 })
  })
})
