logicspike/docs

Blog Engine

`@vlozi/blog` Backlog

Last Updated: 2026-05-06 Status: Active

Lives between sdk-reference.md (ground-truth reference) and the forward-looking visions (integration-friction-vision.md, layouts-vision.md, hosted-blog-vision.md). A living queue of bugs/improvements from consumer-integration sessions — items too small for their own vision doc but worth tracking between releases.


1. What just shipped — 2.1.6 (queued, awaiting publish)

5 changesets accumulated; pnpm changeset version will consolidate into one 2.1.6 CHANGELOG entry on publish.

Bug Changeset Severity
Mermaid hydration broken in browsers (new Function shim) fix-mermaid-loader.md High (regression from 2.1.5)
YouTube watch-URL + narrow allowlist + phantom 16:9 wrapper fix-youtube-embed-handling.md High
<p> margin-top leaking into task lists / callouts / blockquotes fix-prose-margin-leak.md Medium (UX)
Syntax-highlight CSS without a tokenizer fix-syntax-highlighting-half-shipped.md Medium
6-pack: image hydration + transformHtml + controlled search + prefetch parity + skeletons + post.id removal six-pack-improvements.md Medium-Mixed

Tests at HEAD: SDK 394 / 394 ✅, blog-service 94 / 94 ✅. Types ✅. Build ✅.

When you're ready: pnpm changeset version && pnpm install && pnpm changeset publish. See "Publish flow" at the bottom of this doc.


2. Deferred — sized and ready to pull

Items that have been triaged and have a concrete plan but aren't slotted into a release yet. Each is a complete picture: scope + estimate + where to start.

Slottable into 2.1.7 (next patch / minor)

# Item Scope Estimate Source
B1 <BlogPostingJsonLd post={post} /> SEO helper Add to @vlozi/blog/next — a small JSX component that emits <script type="application/ld+json"> with the BlogPosting schema for the given post. Auto-derives URL, image, datePublished, etc. ~30 lines W2 (final review)
B2 Mermaid host-theme class observer Built-in mermaidTheme: "follow-html-class" mode that watches <html>'s dark class via MutationObserver and re-renders. Function form already covers this — this is ergonomics for the shadcn / next-themes audience. ~10 lines W6 (final review)
B3 Webhook helper for ISR revalidation import { handleWebhook } from "@vlozi/blog/next" — generic handler consumers mount at /api/vlozi-webhook to revalidate paths/tags on publish. ~20 lines W9 (final review)
B4 RSS Atom variant generateAtom({ client, ... }) mirroring the existing generateRSS. RSS already exists; Atom is a small variant. ~30 lines W5 follow-up (final review)
B5 Atomic copy button on <pre> blocks Auto-injected by <BlogContent> on hover, "Copied" feedback for 1.5s. Standard 2026 expectation in dev blogs. ~50 lines (DOM walk + Clipboard API + animation timing) Final review (Idea 4a, deferred earlier)

Slottable into 2.2.0 (layouts MVP — already planned)

# Item Scope Notes
B6 usePostHeadings(slug) for TOC Hook returns { id, level, text }[] derived from post body. Pairs naturally with layouts that have a sidebar. DX-E (final review). The body-headings derivation is parsing the same HTML the renderer already produced.
B7 All of layouts-vision.md Editorial + Minimal MVP, <VloziBlogSite> umbrella, token system, dashboard picker, telemetry. ~3.5 weeks per the layouts vision.

Substantial / own vision doc when prioritized

# Item Why it deserves its own doc
B8 Sanitizer DOMParser refactor Real perf + correctness improvement (~10× faster on long posts). But: DOMParser is browser-only; the sanitizer also runs server-side in <ServerBlogPost> (Workers + Node have no DOMParser). Needs threat-modeling, perf benchmark, and a parser choice (parse5 / linkedom / htmlparser2).
B9 Multi-provider embeds (Twitter / X, Vimeo, Spotify, Instagram, CodePen, Gist) Each provider is editor extension + renderer + sanitizer + test. Substantial work.
B10 Author pages — client.blog.authors.list/.get + usePostsByAuthor API surface extension; needs blog-service backend support first.
B11 Draft preview mode (?preview=true API token) Common headless-CMS pattern; needs preview-token API + dashboard preview link UI.
B12 All of hosted-blog-vision.md <tenant>.vlozi.app/blog + custom-domain CNAME via Cloudflare for SaaS.
B13 npx @vlozi/blog setup CLI Big lever for technical-customer onboarding.
B14 Content importers (Substack / Medium / WordPress / Ghost / Notion / dev.to / RSS / Markdown) Big lever for switching from competitors.

Testing infrastructure

# Item Why
B15 End-to-end smoke test of <BlogContent> with a fixture post containing every documented feature The "half-shipped feature" pattern (mermaid CSS without runtime, syntax CSS without tokenizer, empty wrappers from sanitization) keeps recurring. A jsdom + Playwright integration test that renders a fixture post containing every documented feature and asserts the final DOM would catch all three. ~half-day to set up; permanent regression net.
B16 Set up vitest in apps/seller-dashboard The Phase 0 markdown-importer YouTube fix couldn't ship unit tests because seller-dashboard has no test runner. Same applies to any future seller-dashboard utility/component logic.
B17 Convert remaining *.stories.tsx Storybook fixtures off Tailwind Phase 2.1 (Tailwind decoupling) shipped for production components; some Storybook stories still reference Tailwind utility classes in user-demo wrappers. Storybook QA in CI breaks if Tailwind setup isn't there.

Cosmetic / pure docs

# Item Status
B18 Update books-vision.md with a layout-chrome integration note Light touch when books actually start.
B19 data-vlz-syntax="default" set even when no tokens exist Cosmetic only. After 2.1.6 syntax-highlighting fix, posts with code blocks DO have tokens; posts without are unaffected (CSS rules match nothing — zero perf cost). No-action.
B20 Cross-page cache verification The SDK's cache should already persist across navigations (module-singleton client). Reporter flagged it as a possible re-fetch issue. Worth a Storybook scenario verifying behavior, not a refactor.
B21 generateStaticParamsForPosts parallelization Currently paginates sequentially in 100-post batches. For blogs over ~1000 posts, build time scales linearly. Perf, not correctness.

3. Already shipped — clarifications for the consumer reporter

Items the reporter listed that were already in the SDK; worth flagging in the next round-trip so the wishlist focus stays on the real gaps.

Item Where it lives Note
Sitemap helper generateSitemap in @vlozi/blog feeds.ts:168. README documents it.
RSS feed builder generateRSS in @vlozi/blog feeds.ts:67. README documents it. Atom variant is on the queue (B4).
Reading-time fallback estimateReadingTime in client.ts client.ts:674. Runs automatically when post.readingTime is missing — consumer doesn't call it.

4. Not on the roadmap (forever)

Things explicitly out of scope. Worth listing so the answer to "could we add..." is consistent.

  • WYSIWYG layout editor — the layout system is opinionated by design. (Per layouts-vision.md §16.)
  • Drag-drop blog page builder — same.
  • AI-generated layouts from a screenshot — demo magic; unmaintainable.
  • User-contributed layouts as a free open-contribution surface — six layouts forever. (layouts-vision.md §16.)
  • Per-post layout overrides — confuses readers, breaks RSS, breaks OG cache.

5. Publish flow for queued 2.1.6

When you're ready to ship the queued patch:

# 1. Consume the 5 changesets → bumps package.json + apps/website to 2.1.6,
#    generates a single CHANGELOG entry combining all 5 fix descriptions
pnpm changeset version
 
# 2. Lockfile sync will FAIL until 2.1.6 is on npm — that's expected.
#    Skip this step now; run after publish.
 
# 3. Verify everything still passes
pnpm --filter @vlozi/blog test         # 394 expected
pnpm --filter blog-service test         # 94 expected
pnpm --filter @vlozi/blog check-types
pnpm --filter @vlozi/blog build
 
# 4. Commit the version bump + CHANGELOG (no lockfile yet)
git add packages/blog-sdk/package.json packages/blog-sdk/CHANGELOG.md \
        apps/website/package.json .changeset/
git commit -m "chore(blog-sdk): release 2.1.6"
git push
 
# 5. Publish to npm (requires `npm login` first)
pnpm changeset publish
# enter OTP if 2FA prompts
 
# 6. Sync lockfile now that 2.1.6 resolves from npm
pnpm install
git add pnpm-lock.yaml
git commit -m "chore: sync lockfile after @vlozi/blog 2.1.6 publish"
git push
 
# 7. Deploy blog-service Worker (the YouTube URL normalization +
#    syntax-highlighting tokenization changes ship as part of the
#    Worker deploy, NOT the npm publish)
pnpm --filter blog-service deploy

The blog-service Worker deploy is critical — without it, the YouTube URL normalization and server-side syntax tokenization don't take effect even though the SDK package ships.


6. How to maintain this doc

  • When a B-item gets prioritized, pull it out into a focused commit + changeset, then delete the row from this doc.
  • When a new bug/improvement comes in from a consumer integration, add it to the appropriate "Slottable" section.
  • When something gets large enough to need its own vision doc, move it to "Substantial / own vision doc."
  • When the queued 2.1.6 ships, this section becomes "What just shipped — 2.1.6 (live)" and a new "What just shipped — 2.1.7" section opens above it.

This doc should never grow indefinitely — items leave when shipped, when scope-rejected, or when promoted to vision docs.

Blog Engine