import { expect, test } from '@playwright/test'

test('pasting, connecting, and citing one patent screenshot completes the Scene 7 report lesson', async ({ page, request }) => {
  test.setTimeout(60_000)
  const pageErrors:Error[]=[]
  page.on('pageerror',error => pageErrors.push(error))
  let sceneSeven:{ id:string } | undefined
  await expect.poll(async () => {
    const levels=await (await request.get('/api/levels')).json() as { id:string }[]
    sceneSeven=levels.find(level => level.id.startsWith('barricelli-inventor-proof-case-'))
    return Boolean(sceneSeven)
  },{ timeout:20_000,message:'Scene 7 playable clone should be seeded' }).toBe(true)
  if (!sceneSeven) throw new Error('Scene 7 playable clone was not seeded')
  const sceneSevenId=sceneSeven.id

  await page.goto(`/level/${sceneSevenId}`)
  await page.waitForTimeout(250)
  if (pageErrors.length) throw new Error(`Scene 7 failed to render: ${pageErrors.map(error => error.message).join('; ')}`)
  await expect(page.getByRole('heading', { name:'The Barricelli Files' })).toBeVisible()
  await expect(page.locator('.brief-panel')).toBeVisible()
  await expect(page.locator('.brief-panel > p')).toContainText('Prove that Nils Aall Barricelli was an inventor')
  await expect(page.locator('.brief-goals')).toHaveCount(0)
  await page.getByRole('button', { name:'BEGIN INVESTIGATION',exact:true }).click()

  const uploadResponse = page.waitForResponse(response => response.request().method() === 'POST'
    && response.url().includes(`/api/levels/${sceneSevenId}/documents`) && response.status() === 201)
  await page.evaluate(async () => {
    const canvas = document.createElement('canvas')
    canvas.width = 1280
    canvas.height = 520
    const context = canvas.getContext('2d')!
    context.fillStyle = '#fff'
    context.fillRect(0, 0, canvas.width, canvas.height)
    context.fillStyle = '#111'
    context.font = 'bold 56px Arial, sans-serif'
    context.fillText('GB695913A', 70, 95)
    context.font = '48px Arial, sans-serif'
    context.fillText('Improved chest of drawers', 70, 175)
    context.font = '34px Arial, sans-serif'
    context.fillText('Inventor', 70, 280)
    context.font = 'bold 52px Arial, sans-serif'
    context.fillText('Nils Aall Barricelli', 70, 355)
    context.font = '30px Arial, sans-serif'
    context.fillText('Priority date 1951-05-31     Publication date 1953-08-19', 70, 445)
    const blob = await new Promise<Blob>((resolve, reject) => canvas.toBlob(value => value ? resolve(value) : reject(new Error('Could not render screenshot')), 'image/png'))
    const transfer = new DataTransfer()
    transfer.items.add(new File([blob], 'google-patents.png', { type:'image/png' }))
    window.dispatchEvent(new ClipboardEvent('paste', { clipboardData:transfer,bubbles:true,cancelable:true }))
  })
  const uploaded = await (await uploadResponse).json()
  expect(uploaded.analysis).toMatchObject({ extractionStatus:'succeeded',matchedFlags:['scene7.nils_inventor_proved'],
    goals:[expect.objectContaining({ key:'barricelli.inventor-proof',status:'complete',newlyCompleted:true })] })

  await expect(page.getByRole('dialog',{ name:'What kind of evidence is this?' })).toBeVisible()
  await page.getByRole('button',{ name:'Classify as Clip' }).click()
  await expect(page.locator('.source-file-widget')).toHaveCount(1)
  await expect(page.locator('.source-file-widget')).toHaveAttribute('data-capture-kind','clipping')
  await expect(page.locator('.source-file-widget > strong')).toHaveCount(0)
  await expect(page.locator('.clip-provenance')).toHaveText('ADD DATE + SOURCE')
  await expect(page.locator('.source-file-widget')).toHaveClass(/\barriving\b/)
  await expect(page.locator('.goal-complete-card')).toHaveCount(0)
  await expect(page.locator('.evidence-card.claim')).toContainText('Nils Aall Barricelli was an inventor')

  await page.locator('.source-file-widget').dblclick()
  await page.getByRole('button',{ name:'TYPE',exact:true }).click()
  await page.getByRole('menuitemradio',{ name:/Mugshot/ }).click()
  await expect(page.locator('.source-file-widget')).toHaveAttribute('data-capture-kind','photo')
  await page.getByRole('button',{ name:'TYPE',exact:true }).click()
  await page.getByRole('menuitemradio',{ name:/Clip/ }).click()
  await expect(page.locator('.source-file-widget')).toHaveAttribute('data-capture-kind','clipping')
  await page.getByRole('button',{ name:'FILE',exact:true }).click()
  await page.getByRole('menuitem',{ name:/INFO/ }).click()
  await expect(page.getByLabel('Board presentation')).toHaveValue('clipping')
  await expect(page.getByLabel('Document title')).toHaveValue('')
  await page.getByLabel('Published date').fill('1953-08-19')
  await expect(page.getByLabel('Published time')).toHaveValue('')
  await page.getByLabel('Source publication').fill('Google Patents · GB695913A')
  await page.getByLabel('Source URL').fill('https://patents.google.com/patent/GB695913A/en')
  await page.getByRole('button',{ name:'SAVE METADATA' }).click()
  await expect(page.locator('.file-editor')).toHaveCount(0)
  await expect(page.locator('.clip-provenance')).toHaveText('SOURCE RECORDED')
  await page.getByRole('button',{ name:'FILE',exact:true }).click()
  await page.getByRole('menuitem',{ name:/INFO/ }).click()
  await expect(page.getByLabel('Document title')).toHaveValue('Google Patents · GB695913A')
  await expect(page.getByLabel('Source publication')).toHaveValue('Google Patents · GB695913A')
  await page.getByRole('button',{ name:'Close file editor' }).click()
  await page.getByRole('button',{ name:'Close document',exact:true }).click()

  await page.locator('.evidence-card.claim').click()
  await page.getByRole('button',{ name:'Red thread' }).click()
  await page.locator('.source-file-widget').click()
  await expect(page.locator('.thread-editor')).toBeVisible()
  await expect(page.getByLabel('Thread tag')).toHaveValue('Proof that…')
  await page.getByLabel('Thread tag').fill('Proof that Nils Aall Barricelli is named as inventor on patent GB695913A.')
  await page.getByRole('button',{ name:'ADD TAG & TIGHTEN' }).click()

  await page.getByRole('button',{ name:'Report' }).click()
  await expect(page.locator('.case-report')).toBeVisible()
  await expect(page.locator('.report-claim')).toContainText('Nils Aall Barricelli was an inventor')
  await expect(page.locator('.report-evidence')).toContainText('Exhibit 1')
  await expect(page.locator('.report-evidence')).toContainText('Proof that Nils Aall Barricelli is named as inventor on patent GB695913A.')
  await expect(page.locator('.report-evidence')).toContainText('1953-08-19')
  await expect(page.locator('.report-evidence')).toContainText('Google Patents · GB695913A')
  await expect(page.locator('.report-evidence a')).toHaveAttribute('href','https://patents.google.com/patent/GB695913A/en')
  await page.getByRole('button',{ name:'SUBMIT CASE REPORT' }).click()
  await expect(page.locator('.report-verdict')).toContainText('Case report accepted')
  await expect(page.getByRole('button',{ name:/CLOSE CASE/ })).toBeVisible()

  const level = await (await request.get(`/api/levels/${sceneSevenId}`)).json()
  expect(level.goals).toEqual([expect.objectContaining({ key:'barricelli.inventor-proof',status:'complete',newlyCompleted:false })])
  const savedDocuments=level.exhibits.filter((exhibit: { type:string }) => exhibit.type === 'document')
  expect(savedDocuments).toEqual([
    expect.objectContaining({ title:'Google Patents · GB695913A',captureKind:'clipping',width:230,height:290 }),
  ])
  expect(savedDocuments[0].rotation).toBeGreaterThanOrEqual(-10)
  expect(savedDocuments[0].rotation).toBeLessThanOrEqual(10)
  expect(level.report).toMatchObject({ status:'accepted',investigatorName:'Player' })
})
