| 1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889 |
- // @vitest-environment jsdom
- /** Code renderer registration lifetimes through the production document and Slot registries. */
- import { afterEach, describe, expect, it } from 'vitest'
- import { act } from '@testing-library/react'
- import { SlotTestRuntime } from '@deepseek-ai/dsh-client-test-runtime'
- import { LocaleRuntime } from '@deepseek-ai/dsh-client-locale/client'
- import { apply } from '../src/client/code/index.ts'
- import { CodeBody } from '../src/client/code/CodeBody.tsx'
- import { CODE_EXTENSIONS } from '../src/client/code/languages.ts'
- import { DocumentPreviewRegistry } from '../src/client/document/registry.ts'
- import { documentTabInfoFactory } from '../src/client/document/contract.ts'
- const ID = '@deepseek-ai/dsh-client-ui-sidebar-documentpreview/code'
- const SLOT = 'sidebar.right.tab.document'
- const plugin = { inject: ['slots', 'locale', 'documentPreviews'], apply }
- let runtime: SlotTestRuntime | undefined
- afterEach(async () => {
- await runtime?.dispose()
- runtime = undefined
- })
- async function boot() {
- const rt = await SlotTestRuntime.create()
- runtime = rt
- const locale = new LocaleRuntime(rt.ctx)
- rt.ctx.provide('locale', locale)
- rt.slots.installLocale(locale)
- const previews = new DocumentPreviewRegistry()
- rt.ctx.provide('documentPreviews', previews)
- const declare = () => rt.declare({
- [SLOT]: { kind: 'keyed', scope: 'session', inject: { hooks: { tabInfo: documentTabInfoFactory } } },
- })
- return { rt, locale, previews, declare }
- }
- describe('code renderer registration', () => {
- it('publishes builtin metadata before the document slot exists and waits to register its body', async () => {
- const h = await boot()
- await h.rt.mount(plugin)
- expect(h.previews.getSnapshot()).toHaveLength(1)
- expect(h.previews.getSnapshot()[0]).toMatchObject({ id: ID, extensions: CODE_EXTENSIONS, priority: 'builtin', loading: 'text-pages', wrap: true })
- expect(h.rt.slots.entries(SLOT)).toEqual([])
- await h.declare()
- const entries = h.rt.slots.entries(SLOT)
- expect(entries).toHaveLength(1)
- expect(entries[0]).toMatchObject({ options: { key: ID }, locale: 'sidebarCodePreview', component: CodeBody })
- expect(h.previews.candidates('notes.unknown')).toEqual([])
- })
- it('resolves localized names at read time and removes metadata, locale, and body on disposal', async () => {
- const h = await boot()
- await h.declare()
- const feature = await h.rt.mount(plugin)
- const definition = h.previews.getSnapshot()[0]
- await act(async () => { h.locale.setLocale('en') })
- expect(definition?.title()).toBe('Code')
- await act(async () => { h.locale.setLocale('zh') })
- expect(definition?.title()).toBe('代码')
- await feature.dispose()
- expect(h.previews.getSnapshot()).toEqual([])
- expect(h.rt.slots.entries(SLOT)).toEqual([])
- expect(h.locale.bind('sidebarCodePreview')('title')).toBe('title')
- })
- it('remounts the keyed body after the document owner redeclares its slot', async () => {
- const h = await boot()
- await h.declare()
- await h.rt.mount(plugin)
- await act(async () => { h.rt.root.release() })
- expect(h.rt.slots.entries(SLOT)).toEqual([])
- expect(h.previews.getSnapshot()).toHaveLength(1)
- await h.declare()
- expect(h.rt.slots.entries(SLOT)).toHaveLength(1)
- })
- it('keeps prior HTML and Markdown builtins ahead of their optional source renderer', async () => {
- const h = await boot()
- for (const extension of ['html', 'md']) {
- h.rt.ctx.effect(() => h.previews.register({
- id: `dedicated-${extension}`, extensions: [extension], priority: 'builtin',
- title: () => extension, loading: extension === 'html' ? 'bytes-complete' : 'text-pages',
- }))
- }
- await h.rt.mount(plugin)
- expect(h.previews.candidates('page.html').map(item => item.id)).toEqual(['dedicated-html', ID])
- expect(h.previews.candidates('README.md').map(item => item.id)).toEqual(['dedicated-md', ID])
- })
- })
|