The four bugs found during the #293 HTML-emission inventory, fixed in the package:
1. Spoiler mark was silently lost in the raw-HTML path: inlineToHtml (columns /
spanned cells) had no `case "spoiler"`, so spoilered text there dropped the
mark on round-trip. Now emits `<span data-spoiler="true">` — the same form the
top-level serializer uses and exactly what the schema's Spoiler mark parses.
2. Link `title` was dropped in the raw-HTML path: inlineToHtml's link case
emitted `<a href>` without the title. The schema's link mark carries a
`title` global attr (DocmostAttributes), so a titled link inside a column now
round-trips via `<a href … title=…>`.
3. Serializer contract test: emoji/date/toc were flagged as possibly caseless
inline atoms. Verified they exist in NEITHER the package schema NOR
editor-ext, so no node handling is needed today. Added
serializer-contract.test.ts, which derives every node type from the live
schema (getSchema(docmostExtensions)) and asserts each has an explicit
serializer `case` — all 45 current node types are covered and present, and a
future node added without a case will fail this test loudly.
4. codeCombined dead code: `const codeCombined = false` was hardcoded, so every
`codeCombined ? <html> : <markdown>` ternary always took the markdown branch.
Removed the variable and the dead HTML-alternative branches (bold/italic/code/
link/strike). Pure cleanup — output is byte-identical (goldens + full suite
pass unchanged). The `hasCode` early-return (code excludes other marks) stays.
Tests: spoiler-inside-column and link-title-inside-column round-trips, the
serializer contract test + inline-atom non-empty behavioral checks.
package vitest: 657 passed; tsc clean. git-sync: 268 passed.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>