import type { MarkdownTree } from '../app/utils/markdown'; import { expect, test } from 'bun:test'; import { splitParagraphBreaks } from '../app/utils/markdown'; test('paragraph splitting preserves nested formatting without mutating a cached parser tree', () => { const tree = { nodes: [ ['p', {}, 'before', ['br', {}], ['strong', {}, 'after']], ['blockquote', {}, 'one', ['br', {}], ['em', {}, 'two']], ] } as MarkdownTree; const original = structuredClone(tree); const result = splitParagraphBreaks(tree); expect(result.nodes).toEqual([ ['p', {}, 'before'], ['p', {}, ['strong', {}, 'after']], ['blockquote', {}, ['p', {}, 'one'], ['p', {}, ['em', {}, 'two']]], ]); expect(tree).toEqual(original); expect(splitParagraphBreaks(tree)).toEqual(result); }); test('br-free trees return by reference with no allocation', () => { const tree = { nodes: [ ['p', {}, 'plain ', ['strong', {}, 'text']], ['ul', {}, ['li', {}, 'one'], ['li', {}, 'two']], ] } as MarkdownTree; expect(splitParagraphBreaks(tree)).toBe(tree); }); test('single newlines still split into sibling paragraphs', () => { const tree = { nodes: [ ['p', {}, 'line one', ['br', {}], 'line two'], ] } as MarkdownTree; expect(splitParagraphBreaks(tree).nodes).toEqual([ ['p', {}, 'line one'], ['p', {}, 'line two'], ]); }); test('nested changes rebuild only the affected path', () => { const tree = { nodes: [ ['blockquote', {}, ['p', {}, 'kept']], ['p', {}, 'split', ['br', {}], 'me'], ] } as MarkdownTree; const result = splitParagraphBreaks(tree); expect(result).not.toBe(tree); expect(result.nodes[0]).toBe(tree.nodes[0]); expect(result.nodes).toEqual([ ['blockquote', {}, ['p', {}, 'kept']], ['p', {}, 'split'], ['p', {}, 'me'], ]); });