WorkBuddy review found 38 of 131 spec files failed at collection time (0 tests executed) — the '1015 passed' was a false green because vitest only counts 'Tests failed', not 'Test Files failed'. Root cause: dsh-client-ui-primitives@0.2.0-rc.2 declares dependencies:null but statically imports 23 external root packages. Our project declared only 18. Under pnpm strict layout, the missing 5 (dsh-client-store, dsh-util-code-language, dsh-util-workspace-path, diff, simple-icons) were unresolvable when Vite inlined the primitives package. Fixes: - Add 7 missing devDeps: dsh-client-store@0.2.0-rc.2, dsh-util-code-language@0.2.0-rc.2, dsh-util-workspace-path@0.2.0-rc.2, diff@9.0.0, simple-icons@16.35.0, zustand@5.0.15, immer@11.1.21 - vitest.config.ts: add transform plugin to strip sourceMappingURL comments from dsh-client-ui-primitives (upstream ships lib/index.js with trailing sourceMappingURL but package.json files excludes .map) - 5 spec files: add @vitest-environment jsdom directive (they import dsh-client-ui-primitives which calls window.addEventListener at module load; node environment lacks window) - Remove empty .map file hack from node_modules (ineffective + .gitignore blocks it from version control) Result: Test Files 131 passed (131), Tests 1367 passed | 9 skipped, EXIT=0. Verified: simple-icons 25 named exports all present. Typecheck + build pass.
74 lines
2.4 KiB
TypeScript
74 lines
2.4 KiB
TypeScript
// @vitest-environment jsdom
|
|
/**
|
|
* Markdown frontmatter preview regression (#251): a leading, closed YAML
|
|
* metadata block must not reach the shared MarkdownText parser, where its
|
|
* delimiters are otherwise interpreted as a thematic break and setext H2.
|
|
*/
|
|
import { afterEach, describe, expect, it } from 'vitest'
|
|
import { createElement } from 'react'
|
|
import { renderToString } from 'react-dom/server'
|
|
import './browser-globals.ts'
|
|
import { markdownPreviewSource } from '../src/client/markdown-frontmatter.ts'
|
|
import { TextEditor } from '../src/client/TextEditor.tsx'
|
|
import { createSidebarStore } from '../src/client/state.ts'
|
|
import { attachLocale } from '../src/client/locales.ts'
|
|
import type { FileViewerProps } from '../src/client/service.ts'
|
|
|
|
const FRONTMATTER = [
|
|
'---',
|
|
'name: example',
|
|
'description: hello',
|
|
'---',
|
|
'# Title',
|
|
'',
|
|
'Body',
|
|
].join('\n')
|
|
|
|
const CTX = {} as Parameters<typeof TextEditor>[0]['ctx']
|
|
|
|
function viewerProps(content: string): FileViewerProps {
|
|
return {
|
|
ctx: CTX,
|
|
store: createSidebarStore(),
|
|
scope: { sessionId: 's1', cwd: '/p' },
|
|
path: '/p/SKILL.md',
|
|
title: 'SKILL.md',
|
|
viewerId: 'markdown',
|
|
content,
|
|
}
|
|
}
|
|
|
|
afterEach(() => {
|
|
attachLocale(undefined)
|
|
})
|
|
|
|
describe('markdownPreviewSource', () => {
|
|
it('removes a closed YAML frontmatter block only from the preview source', () => {
|
|
expect(markdownPreviewSource(FRONTMATTER)).toBe('# Title\n\nBody')
|
|
})
|
|
|
|
it('supports CRLF without normalizing the body', () => {
|
|
expect(markdownPreviewSource('---\r\nname: example\r\n---\r\n# Title\r\nBody'))
|
|
.toBe('# Title\r\nBody')
|
|
})
|
|
|
|
it('leaves unclosed and non-leading delimiters unchanged', () => {
|
|
const unclosed = '---\nname: example\n# Title'
|
|
const nonLeading = '# Title\n\n---\nname: example\n---\n'
|
|
expect(markdownPreviewSource(unclosed)).toBe(unclosed)
|
|
expect(markdownPreviewSource(nonLeading)).toBe(nonLeading)
|
|
})
|
|
})
|
|
|
|
describe('TextEditor markdown frontmatter preview', () => {
|
|
it('renders the body without exposing YAML metadata as a heading', () => {
|
|
const html = renderToString(createElement(TextEditor, viewerProps(FRONTMATTER)))
|
|
expect(html).toContain('<h1')
|
|
expect(html).not.toContain('<h2')
|
|
expect(html).toContain('Title')
|
|
expect(html).toContain('Body')
|
|
expect(html).not.toContain('name: example')
|
|
expect(html).not.toContain('description: hello')
|
|
})
|
|
})
|