openpencil/tests/e2e/chat/composer.spec.ts
Danila Poyarkov b4e479d9d0
feat: persist AI conversations and add chat history (#661)
* feat: persist AI conversations and add chat history

Store transcripts and attachment previews in IndexedDB, separate conversation history from transport lifetime, and add document-aware switching with shared Storybook coverage. Preserve interrupted activity and guard stale writes and async switches.

* test: group chat history tests by domain

* feat: simplify chat history navigation and diagnostics

Use a compact header with searchable document-scoped history and a correctly anchored conversation menu. Move diagnostic copying into the menu with copy-result feedback, and separate Storybook fixtures from composition.

* fix: address chat history review findings

* test: cover harness shutdown and restored chat scrolling

* fix: preserve Portless proxy port in MCP routes

* docs: clarify UI animation conventions

* feat: configure reasoning display and animate disclosure

* fix: separate transcript following from reasoning disclosure

* fix: restore selected chat after document recovery

* refactor: separate chat history persistence and sessions

* style: format reasoning story imports
2026-09-08 11:19:07 +03:00

33 lines
1.3 KiB
TypeScript

import { expect, test } from '#tests/helpers/chat/fixture'
test('composer enables submission only for non-empty input', async ({ configuredChat: chat }) => {
await expect(chat.sendButton).toBeDisabled()
await chat.input.fill('Make a red rectangle')
await expect(chat.sendButton).toBeEnabled()
})
test('composer grows with multiline input', async ({ configuredChat: chat }) => {
await chat.input.fill('First line')
const initialHeight = (await chat.input.boundingBox())?.height ?? 0
await chat.input.fill(Array.from({ length: 8 }, (_, index) => `Line ${index + 1}`).join('\n'))
await expect
.poll(async () => (await chat.input.boundingBox())?.height ?? 0)
.toBeGreaterThan(initialHeight)
})
test('Shift+Enter inserts a line break without submitting', async ({ configuredChat: chat }) => {
await chat.input.fill('First line')
await chat.input.press('Shift+Enter')
await chat.input.type('Second line')
await expect(chat.input).toHaveValue('First line\nSecond line')
await expect(chat.page.getByText('First line', { exact: true })).toBeHidden()
})
test('Enter submits and clears input', async ({ configuredChat: chat }) => {
await chat.submit('Hello there')
await expect(chat.userMessage()).toHaveText('Hello there')
await expect(chat.input).toHaveValue('')
})