Skip to content
Mark Scherer edited this page Oct 1, 2026 · 60 revisions

Version Map

Canonical version + release-status table for every taggable repo in the markup-carve org.

For the dependency side - who pins whom, and whether that pin is a release - see Dependency Map, which is generated from the manifests by node tools/dependency-map.mjs in the carve repo. This page stays hand-written: the narrative, the release gotchas and the why are the part no generator should own.

Versioning policy

  • Every repo is versioned independently with SemVer. A bug fix on one repo ships as a patch (x.y.Z) on that repo only - no org-wide bump required. The 2026-08-10 coordinated release, for example, is spec 0.1.2, JS 0.1.3, Rust 0.1.2, and PHP 0.1.4.
  • The core four move in lockstep for minor/major only: the spec (carve) and the three engines (carve-js, carve-rs, carve-php) share a normative grammar.ebnf + corpus snapshot. When that snapshot version changes (e.g. 0.1 -> 0.2), all four tag the new minor together. Patches within a minor are still per-repo.
  • Satellites (bindings, editors, integrations) track the core feature set but version on their own cadence - they may patch or add features between core minors.
  • Pre-1.0: breaking changes may land in a minor (0.x) per SemVer's 0.x clause. 1.0 is targeted once the spec is declared stable (see carve#65).

Git tag naming

Bare SemVer tags are preferred (0.1.4). Use a v prefix only when the release system used by that repository requires it; an existing v-tag history alone is not a reason to introduce the prefix in a new repository. Pass the manifest/changelog version as a bare SemVer value (0.1.4); when a release system requires a prefixed Git tag, pass that tag separately (--tag v0.1.4) to scripts/pre-tag-check.sh.

Surveyed 2026-09-23 across the 47 active, non-fork repositories that have tags:

Convention Count Repositories
Bare SemVer (0.1.4) 34 carve, carve-js, carve-rs, carve-php, tree-sitter-carve, pandoc-carve, intellij-carve, homebrew-carve, sublime-carve, sublime-carve-lsp, emacs-carve, vim-carve, helix-carve, obsidian-carve, symfony-carve, laravel-carve, tempest-carve, shopware-carve, wp-carve, carve-php-media-embed, carve-php-chat, carve-components, carve-mcp, carve-css, carve-skill, rouge-carve, highlightjs-carve, astro-carve, docusaurus-carve, eleventy-carve, mkdocs-carve, zensical-carve, vite-plugin-carve, webpack-loader-carve
v-prefixed SemVer (v0.1.4) 13 carve-grammars, carve-lsp, vscode-carve, carve-rb, carve-py, carve-go, carve-wasm, carve-press, pdf-to-carve, zed-carve, carve-hexapdf, jekyll-carve, hugo-carve

For a repository with no tags yet, default to bare SemVer and make its tag-trigger workflow, release documentation, and pre-tag check agree. Use the v form only if its release tooling requires that form. Preparing a draft release does not authorize creating either tag.

Legend - Published: ✅ live on registry · ◑ partly (git tag + GitHub release done, registry publish pending) · ⬚ unpublished · 🔒 registry-name blocked · n/a no registry (git tag is the artifact).

Core (lockstep on the normative snapshot)

Repo Package / Registry Lang Current Pub Notes
carve - (spec + docs; normative grammar+corpus) EBNF/MD 0.1.6 n/a Released 2026-09-19 at 5863d1d8; release page published 2026-09-22. The headline is file inclusion and transclusion, PART 9 §19: the reserved {{ }} directive with a resolver contract, cycle guard, containment root, work bounds and dependency reporting (#291), with the resolver-call bound and the five include obligations normative and an include-security conformance suite behind them. BREAKING: a substitution carries its halves as old and new arrays of inline nodes, replacing the oldText / newText strings (#2094). Also a host-resolver contract mapping mentions and tags to link destinations, a version 2 importer-fidelity schema, text/x-carve as the clipboard type (#2050), and inline, unclosed-code-run, link-destination, writing and layout rulings throughout. No registry: the GitHub tag is the artifact.
carve-js npm @markup-carve/carve TS 0.1.7 ✅ Released; npm @markup-carve/carve 0.1.7 is live. BREAKING: migration reports move to schema version 2 - carried becomes preserved, normalized marks semantics-preserving rewrites, and an empty diagnostics array no longer means verified fidelity (#1671, #1673). BREAKING: a substitution carries old / new inline arrays in place of the string fields (#1827). renderCarve now throws SourceUnspellableError for shapes no parse builds rather than writing something different: an empty code span its run cannot end, a same-kind span with no braced span between the levels, a mention or tag glued to a word or carrying attributes or a name the grammar rejects, and an all-blank table row. The Markdown target's emphasis and strike spelling changed across many shapes; rendered bytes change, what a reader gets back does not.
carve-rs crates.io carve-lang (bin stays carve) Rust 0.1.6 ✅ Released; crates.io carve-lang 0.1.6 is live. Adds repeatable --extension registry keys, tabs and citation modes, section-wrapper opt-out and source-line annotations to the CLI; authoritative mention and tag resolver callbacks on Options; a defaulted unresolved_id on IncludeResolver so a host watches the file the author meant rather than the directive's spelling; the include dependency list on carve --json; and from_prosemirror_with_report, which returns dropped and degraded maps for what an editor payload lost on the way back.
carve-php Packagist markup-carve/carve-php PHP 0.1.9 ✅ Released. Adds ProseMirrorToCarve::degradedAttributes(), a second report channel for what a conversion carried in a lesser form (#2175): a mention whose display label differs from the id, a non-text label, or a name the grammar rejects is degraded rather than dropped, keyed as carve-rs and carve-grammars write it. Fixes a mention or tag carrying no name at all, which used to reach the writer and get the whole document refused, and makes a caption's # placeholder literal inside inline markup (#2181, carve#2112).

Spec pin: all four engines now pin spec 1cbd2c3, which is ahead of the 0.1.6 tag.

Bindings (track core feature set, own cadence)

Repo Package / Registry Lang Current Pub Notes
carve-py PyPI carve-lang PyO3 v0.1.5 ✅ Released 2026-09-23; PyPI carve-lang 0.1.5 is live. The engine now comes from the published carve-lang 0.1.6 crate on crates.io instead of a carve-rs git revision, so building the sdist no longer fetches from GitHub (#75). The engine code is the same carve-rs 0.1.6 the previous release pinned by revision. Note the distribution name: querying carve-py on PyPI answers about an unrelated project.
carve-rb RubyGems carve-lang magnus v0.1.5 ✅ Released 2026-09-23; RubyGems carve-lang 0.1.5 is live. Same move as carve-py: the engine comes from the published carve-lang 0.1.6 crate rather than a git revision, so gem install carve-lang no longer fetches from GitHub while it compiles the extension (#136).
carve-go pkg.go.dev/github.com/markup-carve/carve-go Go v0.1.3 ✅ Released. Adds RenderWithIncludes, which expands {{ path }} directives against a caller-supplied containment root and returns the output, the per-directive warnings and the dependency list a host watches for rebuilds (#64); every other entry point still leaves directives literal. Engine rebuilt from carve-rs 2e9c43f2 to released 0.1.6 (d7837249), which changed 41 of 1695 corpus documents, all from wrong to right.
carve-wasm npm @markup-carve/carve-wasm Rust→wasm v0.1.4 ✅ Released; npm @markup-carve/carve-wasm 0.1.4 is live. Adds astJsonToMarkdown, astJsonToPlainText and astJsonToAnsi, which render an AST-JSON document straight to those targets with the same options object and hook behavior as the source-taking entry points, alongside version 2 importer-fidelity reports for HTML and Markdown and additive migrateDjot / migrateBbcode entry points.

Libraries

Repo Package / Registry Lang Current Pub Notes
carve-grammars npm @markup-carve/carve-grammars Prism/hljs/TextMate/Tiptap v0.1.9 ✅ Released; npm 0.1.9 is live. Breaking: a carveSubstitution node carries old / new inline arrays in place of the oldText / newText strings, matching the spec schema (carve#2095, #466). Adds the reserved include directive scoped BY PART on all three surfaces - the path as a link scope, the selector as a section entity, each option as a parameter plus value - where it used to shred into the constructs its own selector is spelled with, so {{ ch.crv #intro }} colored #intro as a hashtag (#403). Also configurable frontmatter quick fields and reusable language-diff presentation helpers.
carve-components npm @markup-carve/carve-components React/Vue 0.1.1 ✅ Released 2026-09-23; npm 0.1.1 is live. Bundles carve-js 0.1.7, where 0.1.0 bundled 0.1.4 (#15). The build compiles the engine into dist/, so rendered output follows it.
carve-lsp npm @markup-carve/carve-lsp TS v0.1.7 ✅ Released; npm 0.1.7 is live. Adds include selections: a @lines range or a named section on an include directive is diagnosed, navigable and completable, and go to definition lands on the selected part rather than the top of the file (#186). A crossref whose target an included file supplies resolves, because it is answered from the merged document rather than from each child's source (#226), and an include warning raised inside a child is located there with relatedInformation pointing at the real position (#204, #228).
carve-mcp npm @markup-carve/carve-mcp TS/Rust 0.1.5 ✅ Released; npm 0.1.5 is live. Adds opt-in review, convert, structure and workspace tool profiles that cut MCP schema context while keeping all the default, a review-first semantic edit planner that combines up to 100 non-overlapping AST edits into one explained, reversible, stale-guarded patch without writing, and carve_diagnose_and_fix, which previews diagnostics and applies only explicitly selected safe fixes.
carve-php-media-embed Packagist markup-carve/carve-php-media-embed PHP 0.1.3 ✅ Released 2026-08-10 at 0b813161; Packagist resolves that exact commit. Requires carve-php ^0.1.4 and uses the tagged ^0.6 code-sniffer toolchain.
carve-hexapdf RubyGems carve-hexapdf Ruby v0.1.2 ✅ Released; RubyGems carve-hexapdf 0.1.2 is live. Fixes a substitution vanishing from the page: the inline renderer dispatched on critic_substitute and read new_text, while the engine publishes substitution with inline old / new halves (carve-js#1827), so the arm never fired and the fallback rendered nothing. Both halves now reach the page, struck for the replaced run and underlined for the replacement.
rouge-carve RubyGems rouge-carve Ruby 0.1.1 ✅ Released 2026-09-23; RubyGems rouge-carve 0.1.1 is live. Lexes the reserved include directive BY PART - the path as Name.Namespace, the selector as Name.Label, each option as Name.Attribute plus value - where it used to shred into the constructs its own selector is spelled with, so #intro in a path was colored as a hashtag. Rouge does not take new languages into core, so this ships as a plug-in; it publishes over OIDC trusted publishing because the account requires MFA on API pushes.
highlightjs-carve npm highlightjs-carve JS 0.1.1 ✅ Released; npm 0.1.1 is live. Vendors the Carve definition from carve-grammars 0.1.9 instead of 0.1.5 (#6, #9), which brings the emphasis, underline, strong, highlight and strike runs scoping their content correctly along with the include-directive scoping.
carve-css npm @markup-carve/carve-css CSS 0.1.2 ✅ Released 2026-10-01 at 118e708; npm 0.1.2 is live with SLSA provenance. Tab and code-group panels render again: every panel was display: none in every mode, including the default css one, because the rule keyed on an adjacency the engine never emits (all radios and labels come first, then the panels; order: -1 only makes them look interleaved). Panels now pair positionally across the sibling combinator, so :has() appears in no selector and its browser floor is gone. Also fixes two forced-colors contrast bugs (--carve-ink-inverse unmapped left a badge near 1.5:1), block image display and spacing, a highlight's nested ink and fill, and styles mark, pre.diff, .line-block, .hardbreaks and .references. The coverage gate now drives the 2203-case spec corpus across four configurations instead of two fixtures, and refuses to run without a corpus rather than reporting success over what it never rendered.
reveal-carve npm @markup-carve/reveal-carve CSS/JS 0.1.0 ✅ Released; npm 0.1.0 is live. A reveal.js theme and plugin for Carve decks. Its theme.css is the only stylesheet in the org that covered all three Carve render modes correctly, and it did so before carve-css did - worth reading before anyone re-solves tab panels elsewhere. A highlight now carries the theme's own ink through --carve-highlight-background and --carve-highlight-ink rather than the browser's mark color, at 11.79:1 light and 8.79:1 dark against a 7:1 bar chosen for projection, and a nested link, insert or cut inside it inherits that ink (#6). main has no required status checks, so --auto merges immediately rather than on green.
carve-latex npm @markup-carve/carve-latex TS 0.1.0 ✅ First release; npm 0.1.0 is live, verified from the published tarball. Carve to LaTeX and PDF publishing, with citations on by default.
carve-pdf (shell CLI; install from repo) Shell untagged ⬚ crv2pdf.sh - Carve to PDF via headless Chrome (CDP), also emitting standalone HTML, Markdown and text. Vendors carve-css's token/core/extension layers ahead of its PDF-specific overrides, retaining standalone operation without npm: wrap.py inlines the four files, and nothing in the repo runs npm, so the copy is correct rather than drift. Resynced 2026-10-01 to carve-css 4a5d692 with a zero local delta - all 99 lines it was behind were upstream changes it had simply missed, including one hunk that looked local and was an upstream cherry-pick. Before that resync its extensions.css was byte-identical to pre-fix upstream, so it carried the invisible-panel bug, and themes/base.css happened to mask it with its own display: block. No manifest, tag or registry yet.
pandoc-carve npm @markup-carve/pandoc-carve TS 0.1.5 ✅ Released; npm 0.1.5 is live. Breaking: CLI --diagnostics output moves from a JSON array to the version 2 report envelope, and conversion result types gain required report, fidelity and confidence fields, with shared preserved / normalized / degraded / dropped fidelity plus per-diagnostic confidence. Legacy warnings and diagnostics library result fields remain available.
pdf-to-carve PyPI pdf-to-carve Python v0.1.4 ✅ Released; PyPI pdf-to-carve is live. Adds an offline, side-by-side PDF/block correction workspace with page-aware navigation, undo, browser-local autosave and resume, corrected JSON download and compact regression-fixture export. Browser editing stays local, and an exported document must pass the strict --from-json validator before serialization.
carve-skill (Claude Code skill; install from repo) Markdown 0.1.2 n/a Agent-authoring skill: SKILL.md + references/ (syntax card, Markdown/Djot trap list, carve lint loop). Sources content from the spec submodule with a drift-guard test and a round-trip lint of examples/showcase.crv. Installed from the repo; the tag is the artifact.

Editors

Repo Marketplace Current Pub Notes
intellij-carve JetBrains 0.1.10 ✅ Released; JetBrains Marketplace serves 0.1.10 (plugin id 32204), verified 2026-10-01. Its vendored carve-css layers were refreshed from 0.1.0 to published 0.1.1 and now carry an UPSTREAM record (version, commit, SHA-256 per layer) with a two-part staleness guard: an offline test that the bytes match the record, and a CI step that asks npm and fails when npm has moved past it. The guard went red on its first run, which is the only reason to trust it. contrast.css is still deliberately unvendored: 0.1.1's forced-colors block maps --carve-accent to LinkText while leaving --carve-ink-inverse a hex, putting a callout badge near 1.5:1, which is worse than letting the user agent pick both sides. carve-css 0.1.2 fixes that pair, so the guard will prompt the refresh (#226).
vscode-carve VS Code Marketplace + Open VSX v0.1.7 ✅ Released 2026-09-22; tag v0.1.7 pushed, the Build and publish extension job succeeded and the GitHub release is published. The preview presents {.diff} on a language fence, marking added and removed lines on top of the language highlighting (#216), and the language server gains include selections through carve-lsp 0.1.7 (#268). The extension now bundles released carve-js 0.1.7 and carve-lsp 0.1.7, one engine copy between them, instead of an unreleased carve-js revision (#267, #268). Both listings serve 0.1.7, verified 2026-09-23 by direct query. The long-standing note that Open VSX returned 404 for this extension no longer holds.
tree-sitter-carve npm + crates.io + PyPI 0.1.6 ✅ Released 2026-09-22; live on npm, crates.io and PyPI, all three verified by direct query. Breaking: link_label is a leaf node with no attribute field and no inline children, because a reference label is a character run, and the anonymous "/*" token is gone in favor of the scanner deciding a bold-italic opener. Large inline-delimiter, attribute, comment, code-span, reference-definition, table, list and block-quote correctness wave; lone-\r divergences fall from 36 to 1. Adds a dedicated include_directive node with named parts and ships tree-sitter-carve.wasm as a release artifact (#420). Its tag had to be moved once: the first 0.1.6 run failed on a Windows MSVC _Static_assert incompatibility, fixed in #449 before re-tagging.
zed-carve Zed extensions v0.1.3 ◑ Pins the tree-sitter-carve 0.1.6 tag commit. The original registry submission zed-industries/extensions#6830 merged 2026-08-11 and Zed currently lists 0.1.1; zed-industries/extensions#7709 is open to move it to v0.1.3.
helix-carve (config repo) 0.1.4 n/a Moved its grammar pin to the tree-sitter-carve 0.1.6 tag commit. The tag is the artifact.
vim-carve (git plugin) 0.1.4 n/a Moved its grammar pin to the tree-sitter-carve 0.1.6 tag commit. Installable directly by tag.
emacs-carve MELPA 0.1.4 ◑ Released 2026-09-23. Include directives are fontified by part - target, section selector, option names and values (#34) - an include directive closes at the first }} outside a quoted run and a quoted option value is read as one value (#36, #38), and bare emphasis steps over link destinations and autolinks (#40). No carve-mode entry exists in MELPA or MELPA Stable, so repository submission remains. The repo carries no CHANGELOG; the release body is the record.
sublime-carve-lsp Package Control 0.1.2 ◑ Released 2026-09-23. Bundles carve-lsp 0.1.7, five releases on from the 0.1.2 this package shipped before: include resolution (definition, completion and diagnostics on a {{ path }} directive, a @lines range and a named section), crossrefs resolving across an include, workspace intelligence, pull diagnostics, colon-fence tooling and safe fixes. The engine underneath moves from carve-js 0.1.3 to 0.1.7.
sublime-carve Package Control 0.1.6 ◑ Released 2026-09-23. Include directives are highlighted by part, a quoted option value may hold a }} pair, and the directive closes at the first pair outside a quoted run (#39, #41, #45, #47). An unterminated {{ no longer opens an attribute block that cost every line below it its inline highlighting (#43), and a bare *, /, _, ~ or = inside a link destination, title or autolink no longer opens or closes an emphasis run (#49). Package Control indexes from tags; the repo carries no CHANGELOG, so the release body is the record.
obsidian-carve Obsidian community plugins 0.1.1 ◑ Expands {{ path }} include directives in the reading view, on by default, through the same extension pipeline as any other document, with relative links in an included file resolving against that file's folder (#20, #22, #30). Adds opening the file an include names by ctrl/cmd-click, and export or copy of a document with every include expanded, or of a bundle folder holding the document and every file it includes (#23).

Integrations

Repo Package / Registry Current Pub Notes
wp-carve WP.org slug carve-markup 0.1.7 ✅ Released 2026-10-01 at 44dc1e8; WordPress.org serves 0.1.7. Sixteen user-facing changes, of which the changelog originally described three - see the release-notes gotcha below. A {.diff} fence now gets highlighting and diff rows together and keeps its wash in dark mode; an img fence's sanitized SVG survives wp_kses (its data: URI is masked across the sanitizer rather than added to the protocol allowlist); ::: toc renders its list instead of an empty box; mentions actually turn off when the setting is off, including on the public comment-preview endpoint; a block image renders as a block; the toolbar toggles an inline mark instead of doubling it and places the caret by document offset on both source editors; the preview registers the same content extensions as the front end; the render cache signature carries the engine version; and a highlight keeps its own ink, which computed 1.01:1 on a dark theme. Bundles carve-php 0.1.10 and carve-grammars v0.1.11.
shopware-carve GH release ZIP 0.1.4 ✅ Released. Gated file includes: an administrator sets an absolute includeRoot, empty by default, which keeps every include directive literal everywhere. With a root configured, carve:render and the Carve CMS element expand includes, and on the CMS surface the editor needs the carve.include_expand privilege on top of CMS editing rights. Product, category and manufacturer fields stay literal whoever wrote them. This project does not publish through the Shopware Store.
laravel-carve Packagist markup-carve/laravel-carve 0.1.6 ✅ Released. Adds opt-in file-backed include rendering: an absolute include_root plus Carve::toHtmlFile() and Carve::toHtmlFileWithReport(). Blade directives and the string methods still never read files. A cached file render is served only while every recorded dependency still hashes the same, and logged warnings omit resolver details (#25).
symfony-carve Packagist markup-carve/symfony-carve 0.1.5 ✅ Released. Adds opt-in file-backed rendering: an absolute include_root plus CarveRenderer::renderFile() and renderFileWithReport(). The Twig filters and render() still take anonymous strings and never read files. A report carries the resolved and attempted include targets so an application can key its own cache on them, and warnings reaching the logger omit resolver details (#13).
tempest-carve Packagist markup-carve/tempest-carve 0.1.0 ✅ First release. Carve rendering for Tempest applications: a safe-by-default x-carve view component, a discoverable singleton CarveRenderer service, Tempest-native configuration with named profiles and extension registration, an optional content-hash rendering cache through Tempest Cache, and rendering diagnostics, profile violations and bounded loss reports.
vite-plugin-carve npm @markup-carve/vite-plugin-carve 0.1.1 ✅ Released 2026-09-23; npm 0.1.1 is live. {{ path }} directives in imported .crv documents now expand, resolved relative to the document and contained to Vite's project root. includes: false leaves them literal and includeRoot sets an absolute containment root (#18).
astro-carve npm @markup-carve/astro-carve 0.1.1 ✅ Released 2026-09-23; npm 0.1.1 is live. Include directives in .crv imports now expand, contained to Astro's project root by default, and included files are watched in dev. includes: false leaves them literal and includeRoot sets an absolute containment root (#15).
eleventy-carve npm @markup-carve/eleventy-carve 0.1.1 ✅ Released 2026-09-23; npm 0.1.1 is live. {{ path }} directives in file-backed templates now expand, resolved relative to the template and contained to its directory by default, and included files join Eleventy's watch targets (#16).
docusaurus-carve npm @markup-carve/docusaurus-carve 0.1.1 ✅ Released 2026-09-23; npm 0.1.1 is live. {{ path }} directives now expand, resolved relative to each document and contained to the docs directory (#8, #10). Requires @markup-carve/carve ^0.1.7, the first release carrying contained include expansion (#12).
webpack-loader-carve npm @markup-carve/webpack-loader 0.1.1 ✅ Released 2026-09-23; npm 0.1.1 is live. {{ path }} directives now expand, resolved relative to the importing .crv file and contained to webpack's rootContext, and included files are registered as webpack dependencies (#8). Requires @markup-carve/carve ^0.1.7 (#10). Note the package name is @markup-carve/webpack-loader, not the repo name.
carve-wysiwyg npm @markup-carve/carve-wysiwyg (private) 0.1.0 ⬚ Tiptap editor. Consumes published @markup-carve/carve-grammars. No tag.
carve-press npm @markup-carve/carve-press v0.1.3 ✅ Tagged 2026-09-21; npm @markup-carve/carve-press 0.1.3 went live 2026-09-23. A {.diff} attribute on a language-tagged fence renders its +, - and space markers as diff-marker spans and marks changed lines diff add or diff remove while the code keeps its language highlighting (#39). This release sat half-done for two days: tag, GitHub release and CHANGELOG all looked complete while npm still served 0.1.2, because the publish job was parked on the release environment approval gate. See the gate gotcha below.
carve-php-chat Packagist markup-carve/carve-php-chat 0.1.1 ✅ Released. Requires carve-php ^0.1.9, up from ^0.1.2, for the SubstitutionHalf node (#7). Fixes a substitution rendering both halves as inline content rather than flattened text: {~/old/~>*new*~} used to lose its emphasis and its strong on every flavor.
hugo-carve pkg.go.dev v0.1.1 ✅ Released 2026-09-23; the Go proxy serves v0.1.0 and v0.1.1. --includes expands {{ path }} directives from disk, contained to --include-root (default: the content directory), off by default, and --deps FILE writes what each page read so a build knows when to run again (#27, #30). Wraps carve-go as a preprocessor, because Hugo has no markup-plugin API. It has no tag-triggered workflow at all, so nothing publishes and nothing flips its release; the tag is the artifact and the release page needs flipping by hand.
mkdocs-carve PyPI mkdocs-carve 0.1.1 ✅ Released 2026-09-23; PyPI mkdocs-carve 0.1.1 is live. Expands {{ path }} includes for file-backed pages, contained to a root, through new includes and include_root config keys, off by default. Needs carve-lang 0.1.4 or newer, above the declared floor: includes: true on an older engine is a configuration error rather than a silent no-op (#17).
zensical-carve PyPI zensical-carve 0.1.1 ✅ Released 2026-09-23; PyPI zensical-carve 0.1.1 is live. Expands {{ path }} includes on whole pages, contained to a root, through new includes and include-root settings and their CLI equivalents, off by default. A ```carve fence has no file of its own, so it keeps the directive literal and says so once per build (#13).
jekyll-carve RubyGems jekyll-carve v0.1.2 ✅ Released 2026-09-23; RubyGems jekyll-carve 0.1.2 is live. Expands {{ path }} includes for file-backed pages, contained to a root, through new carve.includes and carve.include_root settings, off by default; a conversion with no page behind it stays literal. Every resolved target is registered with Jekyll's regeneration path. Needs carve-lang 0.1.4; on an older engine it raises an ArgumentError naming the installed version instead of a NoMethodError.

Distribution

Repo Channel Current Pub Notes
homebrew-carve Homebrew tap markup-carve/carve 0.1.0 ✅ Initial tap release published 2026-08-27 at bc006197. Installs the carve-rs binaries for macOS and Linux; the upstream release workflow generates and pushes the formula after publishing its platform assets. The formula passed the tap's eight-job macOS/Linux CI matrix, including the post-merge run.

Not tagged / released

  • carve-okf (Open Knowledge Format export) has a prepared 0.1.0 draft and no tag. A first-ever release, deserving a deliberate decision rather than a batch tag. (carve-latex was in this bullet and is released - npm 0.1.0 is live.)
  • carve-pdf (shell CLI) and carve-wysiwyg (private Tiptap editor) have no tag and no manifest release path.
  • carve-bench (internal benchmarks), awesome-carve (curated link list), symfony-carve-demo, laravel-carve-demo, tempest-carve-demo, zensical-carve-demo (demo apps) and .github (org meta) do not cut releases.

Registry name collisions

The bare name carve is taken on three registries. The distribution name differs from the import/require/binary name, which stays carve everywhere.

Registry carve Our dist name Import / binary name
npm (scope avoids it) @markup-carve/carve carve
crates.io ❌ taken (unrelated carve 0.0.1) carve-lang bin carve
PyPI ❌ taken (unrelated nested-data package) carve-lang import carve
RubyGems ❌ taken (unrelated gem) carve-lang require "carve"

Alternatives checked and free on PyPI+RubyGems (2026-06-27): markup-carve, carve-markup, carvelang. carve-lang was chosen for cross-registry consistency.

Special cases (release gotchas)

Hard-won during the first publishes. Read before tagging anything.

npm scoping and naming

  • Everything JS publishes under @markup-carve/*. The one historical exception, unscoped carve-grammars, was renamed to @markup-carve/carve-grammars in 0.1.2 (2026-07-14). tree-sitter-carve stays unscoped on purpose - that is the tree-sitter convention.
  • Renaming a published package is a three-repo move: rename + publishConfig.access: public in the package, then fix every consumer that pins it (dep key and import specifiers - a github:/file: dep key must match the package's own name), then tag. Consumers pinned by github: break the moment the rename hits the package's main, so merge in that order.
  • OIDC Trusted Publishing cannot bootstrap a brand-new scoped package. The first npm publish of a name that does not yet exist fails with 404 PUT .../@markup-carve/<pkg> under OIDC. Use a classic NPM_TOKEN for the first publish (granular token, read+write on the @markup-carve scope, repo secret, NODE_AUTH_TOKEN). A granular token can only be scoped to the scope, not to a not-yet-existing package name.
  • npm write ops mask auth failures as 404. npm deprecate without a session returns 404 Not Found - PUT ... even though the package exists; logged in but without 2FA it returns the accurate 403 ... Two-factor authentication or granular access token with bypass 2fa enabled is required. Pass --otp=<code> (or use a bypass-2FA granular token).
  • Deprecating the old unscoped carve-grammars is still OPEN (blocked on the 2FA step above): npm deprecate carve-grammars "Renamed to @markup-carve/carve-grammars" --otp=<code>.

crates.io

  • Trusted Publishing cannot bootstrap a brand-new crate (same wall as npm) - the trusted publisher is configured on the crate's crates.io Settings, which does not exist until the crate does. First publish uses a CARGO_REGISTRY_TOKEN (or a manual local cargo publish); afterward configure Trusted Publishing so future tags publish tokenlessly. carve-rs release.yml uses the token when the secret is set and falls back to OIDC otherwise.
  • A manual local cargo publish does NOT run the release workflow (which triggers on a tag), so it leaves the GitHub release a draft and creates no tag - both must then be done by hand. Prefer the tag path so crates.io + the GitHub release happen together.
  • The tests/spec submodule is not needed to publish. Cargo.toml include whitelists only src + meta and there is no build.rs, so the corpus never ships and cargo publish builds without it; it is only for cargo test.

GitHub releases

  • A --draft release stays invisible until someone publishes it - even when the tag and the registry publish already happened. carve-js 0.1.0 was tagged, npm-published, and still showed no release for hours because the draft was never flipped; carve-rs 0.1.0 sat the same way (draft + no tag) after its manual cargo publish until the draft was flipped. Check gh release list for Draft after any release round.

  • Publishing an old draft may not promote it to GitHub Latest. On 2026-08-10, JS 0.1.3 and Rust 0.1.2 published and reached their registries while GitHub still labelled the preceding releases Latest. Verify gh api repos/markup-carve/REPO/releases/latest --jq .tag_name; if needed, PATCH the new release with make_latest: "true".

  • PUBLISH THE DRAFT; do not push the tag yourself. Publishing a draft creates its tag from target_commitish, and that tag creation fires the on: push: tags: workflow, so ONE action does the whole release. Measured on carve-grammars across four releases - the workflow starts 1 to 6 seconds after the release's published_at, never before it:

    tag published workflow started
    v0.1.6 23:42:26Z 23:42:32Z
    v0.1.5 01:23:49Z 01:23:50Z
    v0.1.4 16:38:45Z 16:38:47Z
    v0.1.3 15:21:02Z 15:21:04Z

    The tag-first path is two actions that must BOTH happen, and the second one is the one people forget - which is exactly the "draft stays invisible" bullet above, hit twice on carve-js 0.1.0 and carve-rs 0.1.0. Publishing the draft cannot leave a draft behind, because the draft IS the trigger. Prefer it wherever a repo's release workflow is tag-triggered.

  • Do not read a green release run as "the registry has it". Verify the registry's own metadata, which is what an install resolves: for npm, curl -s https://registry.npmjs.org/@scope%2Fname | jq '.["dist-tags"].latest' rather than the GitHub UI or the run's exit status.

  • The tag drives the deploy, so the notes must exist before/at tag time.

  • Never gh release delete mid-flow. Fix and re-run (gh run rerun <id>). A re-run replays the workflow as of the tagged commit - if the fix landed after the tag, move the tag (git push origin :refs/tags/X.Y.Z, re-tag on updated main, push).

  • Tag prefix is per-repo - ALWAYS read the target repo's release.yml on.push.tags glob before tagging. The org is inconsistent: carve-js matches bare [0-9]+.[0-9]+.[0-9]+ (tag 0.1.1, no v), while carve-lsp matches v[0-9]+.[0-9]+.[0-9]+ and vscode-carve matches v* (tag v0.1.0). Push the wrong prefix and the tag lands but the release workflow never fires - a silent no-op (hit 2026-07-15: pushed v0.1.1 to carve-js, no publish; retagged bare 0.1.1).

  • A first-ever publish needs its registry token present as a repo/org secret. carve-lsp's first npm publish died ENEEDAUTH with an empty NODE_AUTH_TOKEN because NPM_TOKEN was never added to that repo (set it org-wide, then gh run rerun). Marketplace publishes likewise need VSCE_PAT/OVSX_PAT. Guard publish steps on env.<TOKEN> != '' so a tag stays green before the secret exists.

Editor marketplaces (each is different)

  • VS Code Marketplace: vsce publish (needs VSCE_PAT, a Marketplace-scoped Azure DevOps PAT) or drag-drop upload at marketplace.visualstudio.com/manage. The vsix publisher field MUST equal an existing publisher you own, or the upload is rejected. Package WITH deps unless the extension is bundled (--no-dependencies drops node_modules). The web uploader is flaky (Value cannot be null. Parameter name: v1 on a fresh publisher - retry or use the CLI).
  • Open VSX (VSCodium/Cursor/Zed-for-vscode-exts): no web upload - ovsx create-namespace <ns> then ovsx publish file.vsix -p <OVSX_PAT>.
  • Zed: NOT a tag or marketplace upload. Open a PR to zed-industries/extensions: fork it, git submodule add <ext-repo> extensions/<id> pinned to the release commit, add a [<id>] entry to extensions.toml (submodule + version), then pnpm install (the sort script needs @iarna/toml) and node src/sort-extensions.js to normalize extensions.toml + .gitmodules. The Zed team reviews/merges to publish. Updates = bump the submodule ref + version via another PR.
  • JetBrains (intellij-carve): Gradle publishPlugin / manual upload to the JetBrains Marketplace.

Release ordering (dependency chain)

  • Consumers that bundle carve-js at build time need @markup-carve/carve on npm first. shopware-carve (admin live preview), eleventy-carve, carve-wysiwyg etc. run npm install during their build/package step; if carve-js is not on npm, that step 404s.
  • The rs-backed bindings (carve-wasm, carve-go, carve-py, carve-rb) must be rebuilt after any carve-rs engine change, since they vendor or embed the engine. A carve-rs merge is not visible downstream until they are.

Shopware-specific

  • shopware-cli extension validate requires composer.json extra.description (en-GB and de-DE) to be 150-185 characters.
  • Store upload needs CHANGELOG_en-GB.md in store format (# X.Y.Z headings) inside the ZIP.
  • The ZIP is built by shopware-cli extension zip; its contents are controlled by .sw-zip-blacklist, NOT by .gitattributes export-ignore (that only affects the Composer/Packagist tarball).
  • The version field in composer.json is the plugin version Shopware reads (unlike plain Composer libs where the git tag drives it).

Release gotchas learned 2026-08-18

  • A release gate aimed at spec main cannot pass. carve-rb, carve-py and carve-wasm each checked out spec main in release.yml with no ref:, so their blocking corpus job held the artifact to a corpus NEWER than the release it was gating. The moment the spec moved after an engine was tagged - which is always - the gate became unpassable. It half-released carve-py: tag and GitHub release live, Publish to PyPI skipped, PyPI still serving the vulnerable 0.1.0. Fixed by resolving the spec commit from the engine the artifact contains, with spec-main drift reported in a separate non-blocking job - the shape carve-go already had, which is why carve-go was green while the other three were red.

  • Recovering a half-released tag: re-running does NOT work, it re-queues at the tag's own commit and hits the old gate again. Inventing a .2 leaves the live release page permanently lying. What worked was force-updating the tag onto the fixed commit, after confirming the delta was confined to paths the package excludes ([tool.maturin] exclude), so the published content still matched what the tag described.

  • A gate that passes on a clean tree cannot be validated by that tree. Every mutant of the citation matcher left normativity.test.mjs 13/13 green, because on a clean tree "no defects" and "no matches" are the same output. Drive such a gate over synthetic prose instead - twelve real dangling citations were hiding in the wrapped shape on main.

  • Editing a DRAFT release via the API silently unnames it. Any PATCH to a draft that omits tag_name replaces the tag with a generated untagged-<sha> placeholder, and publishing then creates a tag with that name. Measured: -f body="x" with no tag_name clears it; -F body=@file WITH -f tag_name=X.Y.Z preserves it. It is the absence of the field, not the file or the flag. Only bites DRAFTS - a published release's tag is a real git ref. Always send tag_name, address drafts by id rather than by tag, and read tag_name back afterwards.

  • gh release edit <tag> can no-op silently on a draft. It addresses a release BY TAG, and a draft's tag is not a ref, so it matched nothing, changed nothing and exited 0.

  • [Unreleased] sections stop short without saying so. All four repos' sections had silently stopped at an older PR, leaving a full day of merged work undescribed - including the security fix in three of them. Reconcile against the last RELEASED tag (gh api repos/O/R/compare/<tag>...main), never against the last entry.

  • crates.io's API returns nothing without a User-Agent header, which reads identically to "not published".

  • npm publish --dry-run --provenance silently ignores the flag. Measured on tree-sitter-carve run 32170740059: the word "provenance" appears in the job's 364 log lines only where the script echoes its own command. No OIDC token is minted and Sigstore is never contacted, so the provenance path cannot be rehearsed at all - a tag is the first thing that exercises it. Two rehearsals went fully green and the tag still failed there.

  • npm rejects a provenance publish whose package.json has no repository. 422 ... "repository.url" is "", expected to match "https://github.com/<owner>/<repo>" from provenance. The attestation signs a repository claim that the registry then verifies against the manifest. Compare the two strings in the guard; it is the only pre-publish form the check can take.

  • --provenance needs id-token: write, and it is never granted implicitly - not even when the repo default is read-write. Omitting the block does not weaken provenance, it makes the publish fail at the last step of the last job.

  • crates.io answers 401 for a bad token and 403 for "this action requires authentication". A token scoped to publish-new/publish-update gets 403 from /api/v1/me, because that scope does not grant the user endpoint. A "validate the token" check built on that endpoint therefore fails exactly the least-privilege token it should encourage - it blocked a good release. No crates.io endpoint validates a publish-scoped token without publishing; leave that leg unchecked rather than checked wrongly.

  • Serialize the publish jobs behind the riskiest one. tree-sitter-carve's three publishes ran in parallel; wiring crates.io and PyPI behind npm via needs: meant two npm failures left every registry untouched instead of half-shipping. No registry lets a version be reused, so a partial release forces a re-cut of the legs that did work. Cost: about two minutes.

  • A version can be re-attempted by force-moving its tag onto the fixed commit, as long as nothing was published. tree-sitter-carve 0.1.3 took three attempts on the same tag and the same version number; the registries were verified empty before each retry.

Release gotchas learned 2026-09-22

  • A release workflow that does not publish its own draft strands every release it runs. The org's pattern was: a human writes the draft, the tag push runs a workflow that verifies the draft exists and has notes, publishes to the registry, and then leaves the release a draft forever. Nothing in the workflow ever flipped it. That stranded four releases in one night (tree-sitter-carve 0.1.6, carve 0.1.6, vscode-carve v0.1.7, intellij-carve 0.1.9) and is the same failure the 2026-08-18 "draft stays invisible" bullet describes, except structural rather than forgetful. A Publish the release notes step was added to 22 release workflows to close it. Three repos correctly do not need it: carve-rs and carve-mcp trigger on: release: [published], so publishing by hand is what starts the run and the bug cannot exist; shopware-carve uses softprops/action-gh-release, which finalizes the draft itself.

  • The step looks the draft up by tag rather than assuming the workflow authored it, because almost no repo here creates its own draft, and it exits 0 when no draft is found, so it is harmless on a release cut non-draft.

  • Put the flip behind every publish job, not on one of them. tree-sitter-carve publishes to npm, crates.io and PyPI with crates and PyPI hanging off npm in parallel, so no single job is last. Flipping from either one would publish the notes while the other registry had failed. It became its own job with needs: [publish-npm, publish-crates, publish-pypi].

  • The release environment approval gate parks a run silently and forever. A gated run sits in status: waiting with no notification, no failure and nothing on the release page to suggest it. It fired on every npm repo in the 2026-09-22 round, and it is what left carve-press v0.1.3 looking completely released for two days while npm served 0.1.2. It is applied inconsistently - the PyPI repos (zensical-carve, mkdocs-carve) are not gated at all, so you cannot predict which releases need babysitting. After any tag push, check gh api repos/O/R/actions/runs/<id> --jq .status and approve:

  • A release workflow can fail BEFORE it publishes, and the release page will not say so. carve-css 0.1.2 was tagged, its GitHub release published, and npm publish skipped - the job died earlier at npm test with FAIL: no spec corpus to drive. The coverage gate drives the spec corpus and refuses to fall back to its two local fixtures, which is correct; ci.yml checked the corpus out and release.yml never had that step, so no release could ever reach its publish step. The result is the worst shape of half-release: a public release page for a version nobody can install, with every gate in the workflow reporting success. After any tag push, read the run per step and confirm the publish step itself ran - gh api repos/O/R/actions/runs/<id>/jobs --jq '.jobs[]|(.steps[]|"\(.conclusion // .status)\t\(.name)")'. A skipped publish step is not a failure anywhere in the UI.

  • An install check run straight after publishing lies, in two different ways. For carve-css 0.1.2, npm i pkg@0.1.2 returned notarget 14 seconds after a successful publish because the tarball had not propagated, and still returned notarget at 37 seconds - by then from npm's own cached packument, while a plain curl of the registry already listed 0.1.2. npm's closing line says it plainly: "Your package is being processed and may take a few minutes to become available." Verify with the tarball's HTTP status (curl -o /dev/null -w '%{http_code}' on the dist.tarball URL) and npm view --prefer-online, then install with --prefer-online. A failed install immediately after publishing is evidence of nothing.

    echo '{"environment_ids":[<int>],"state":"approved"}' | gh api repos/O/R/actions/runs/<id>/pending_deployments -X POST --input -
    

    The --input - form is load-bearing: environment_ids must be a JSON array of integers, and passing it through -f sends a string and fails 422 ... not an integer.

  • Registry read-back lies in four different ways, each its own endpoint. pip index versions caches and reports stale versions; use PyPI's JSON API (https://pypi.org/pypi/<pkg>/json). RubyGems' summary endpoint api/v1/gems/<name>.json lags after a fresh push while api/v1/versions/<name>.json is immediate. npm's dist-tags.latest can trail a successful publish by minutes, so confirm against the job log's + <pkg>@<version> line before calling it a failure. And carve-rb / carve-py publish under the renamed carve-lang identifier, so querying the repo name answers about an unrelated package.

  • A draft's html_url contains untagged-<sha> even when its tag_name is correct. That is normal for a draft and is NOT the tag-loss bug from 2026-08-18; the permalink only resolves once the release is published. Read tag_name, not the URL, to tell the two apart.

  • Verify the git remote before any tag surgery. A git push origin :refs/tags/X run from the wrong working directory deleted the tag from a different repo entirely, and the wrong repo's published release silently reverted to a draft with an untagged-* permalink as a result. Prefer creating tags through the API, where the repo is named explicitly and there is no ambient origin:

    echo '{"ref":"refs/tags/<TAG>","sha":"<SHA>"}' | gh api repos/O/R/git/refs -X POST --input -
    

Open release work

Current as of 2026-09-23, after the 0.1.6 cycle and the 2026-09-22 release round.

  1. carve-js 0.1.8 - version bumped and the CHANGELOG section written and dated, but no draft exists and no tag. npm still serves 0.1.7. This is the head of the chain: carve-lsp, carve-grammars and both IDE plugins consume it.
  2. carve-rs 0.1.7 - same state, no draft, no tag; crates.io still serves carve-lang 0.1.6. Note carve-rs is the inverted model: its workflow triggers on: release: [published], so publishing the release by hand is what creates the tag and starts the run. It does not take the draft-then-tag path the rest of the org uses.
  3. carve-lsp - 19 commits unreleased, and it pins carve-js at exact 0.1.7 with no caret, so it will not pick up 0.1.8 on its own. It needs a manual bump. Every other JS consumer uses ^0.1.7 and resolves forward without intervention.
  4. carve-grammars - 3 commits unreleased plus open pin PR #553.
  5. carve-wasm, pandoc-carve (open PR #187) - unreleased drift, no draft prepared. (carve-css was here and released 0.1.2.)
  6. carve-mcp, laravel-carve, symfony-carve - one commit each; minor. (wp-carve was here and released 0.1.7.)
  7. carve-rb PR #138 (the publish-notes workflow step) is open with auto-merge armed, blocked on the check "The gem's drift from spec main is declared". That check measures against spec main, a moving target, so it goes red when the spec advances with nothing in the repo having changed - carve#2174 did exactly that. It is a ci.yml job only; release.yml has no spec-main gate, so it did not block the v0.1.5 release.
  8. carve-okf 0.1.0 - a prepared first-release draft awaiting a deliberate decision. (carve-latex shipped 0.1.0.)
  9. Marketplace propagation - VS Code v0.1.7 published from CI but marketplace indexing lags; confirm the listing. IntelliJ 0.1.10 is confirmed live on the Marketplace. Package Control indexes Sublime from tags. MELPA still has no carve-mode entry, so emacs-carve submission remains. Zed registry entry moves to v0.1.3 when zed-industries/extensions#7709 merges.
  10. Deprecate unscoped carve-grammars on npm (needs OTP).
  11. PyPI attestations - zensical-carve and mkdocs-carve both fell back to API-token publishing rather than Trusted Publishing, so neither got attestations; mkdocs-carve logs the warning that attestations: true is ignored because an explicit password is set. Removing the password and wiring Trusted Publishing would fix both.

Updated 2026-08-12 (later): pdf-to-carve 0.1.0 and carve-lang 0.1.0 are both live on PyPI, each verified by installing from the registry rather than from a green workflow. carve-py's first tag published nothing - the macOS wheel job failed on mapfile, a bash 4 builtin absent from macOS's bash 3.2, and publish needs all three wheel jobs; the guard now runs on macOS in CI and the tag was moved onto the fix. carve-rs gained an extension registry and carve-py reads it, so Python reaches 31 extensions instead of 19. mkdocs-carve now depends on the published engine and is ready to tag.

Updated 2026-08-17: pandoc-carve released 0.1.0 to npm (tag e0993527, gitHead verified against the registry). It had no release path at all - publishing the draft would have cut a tag and left npm empty - so the release added the guarded workflow, publishConfig.access, and a cut changelog. Tag glob is the bare [0-9]+.[0-9]+.[0-9]+, matching carve-js/carve-rs/carve-php rather than the v-prefixed satellites.

Updated 2026-08-12: added pdf-to-carve (PDF/image → Carve), whose PyPI release workflow landed the same day. It is the first repo in the org whose intended PyPI name is not blocked, and its tag glob is v* (tag v0.1.0).

Updated 2026-08-11: published the eight editor GitHub releases (VS Code 0.1.1, IntelliJ 0.1.4, Zed 0.1.1, Helix 0.1.1, Vim 0.1.1, Emacs 0.1.1, Sublime 0.1.3, and Sublime LSP 0.1.1); recorded marketplace/indexing state and Zed update PR #7177. Vim and Helix are tag-complete; the other registries still need propagation or submission as noted above.

Last full audit 2026-07-14: every row re-verified against the actual tag/release and a live registry query (npm, crates.io, PyPI, RubyGems, Packagist, WP.org). Corrections made in this pass: carve is released (was listed 0.0.0/unpublished); carve-grammars is now @markup-carve/carve-grammars 0.1.2 (was "leave it unscoped"); the carve crate name is NOT free (was "appears free"); wp-carve IS live on WP.org 0.1.2 (was "unverified"); carve-rs release is a draft with no tag (was implied ready).

Updated 2026-08-18: the 0.1.x core round - spec 0.1.3, carve-js 0.1.4, carve-rs 0.1.3, carve-php 0.1.5, all tagged at their release-time main and verified live on npm, crates.io and Packagist by direct query. A security release (§25 list-valued URL attribute probe). Known and NOT fixed in it: markup-carve/carve-php#1456, a long alternating quote-and-bullet prefix segfaults rather than refusing - pre-existing in 0.1.4, adversarial input only, fix queued.

Updated 2026-08-19: jekyll-carve v0.1.0 is live on RubyGems - the release held since spring over a vulnerable engine floor, now shipping with carve-lang >= 0.1.1 and a gate that renders the §25 probe through the resolved engine before publishing. carve-hexapdf is tagged, gated and blocked only on RubyGems MFA (see 7). carve-press shipped earlier the same day.

Updated 2026-08-18 (downstream round): carve-py v0.1.1 live on PyPI with the §25 fix; carve-rb v0.1.1 live on RubyGems, which unblocked jekyll-carve; laravel 0.1.5 and symfony 0.1.4 live on Packagist. Prepared but unpublished: carve-go v0.1.1, carve-wasm v0.1.0 (blocked on carve-wasm#44), and drafts across the static-site and npm satellites. jekyll-carve and mkdocs-carve were blocked on vulnerable published engines; Both PyPI and RubyGems are now clear.

Updated 2026-08-18 (LSP + WordPress): carve-lsp v0.1.3 is live on npm with registry gitHead matching f3ed9b00; its formatter render-equivalence defect (#105) is fixed on main and corpus-gated. wp-carve 0.1.3 is live on GitHub and WordPress.org at caccdf5d; its release ZIP, SVN tag, plugin header, stable tag, and public API version were verified after the complete deployment workflow passed.

Updated 2026-09-09 (release wave): the Current column is bumped to the live tag/registry versions of this wave. Core: carve 0.1.5, carve-js 0.1.6, carve-php 0.1.7, carve-rs 0.1.5. Bindings: carve-rb v0.1.3, carve-py v0.1.3, carve-wasm v0.1.3. Grammars/tree-sitter: carve-grammars 0.1.7, tree-sitter-carve 0.1.5. Editors: emacs-carve 0.1.3, helix-carve 0.1.3, vim-carve 0.1.3, sublime-carve 0.1.5, vscode-carve 0.1.5, intellij-carve 0.1.7. Tooling: carve-lsp 0.1.6, carve-press 0.1.2, carve-mcp 0.1.4, carve-skill 0.1.1, carve-hexapdf v0.1.1, pdf-to-carve v0.1.4, wp-carve 0.1.5, carve-php-media-embed 0.1.3, pandoc-carve 0.1.4. First releases: carve-php-chat 0.1.0, hugo-carve 0.1.0. laravel-carve stays at 0.1.5 (its 0.1.6 was dropped). carve-mcp has no row on this page; its version is tracked only in the generated Dependency Map. The per-row Notes prose above still describes each repo's previous release and predates this wave.

Updated 2026-09-15: intellij-carve 0.1.8 released, carrying the PhpStorm 2026.2 preview fix (JCEF moved behind its own class loader there). The build was driven in a sandbox PhpStorm 2026.2.2 before tagging: the preview, the preview tool window, the diff fence, include highlighting and Export Bundle all work, and the 0.1.7 build reproduces the crash on the same IDE.

Updated 2026-09-23 (grammar wave): tree-sitter-carve 0.1.6 is live on npm, crates.io and PyPI. The three grammar consumers moved their pin to the 0.1.6 tag commit and released: zed-carve v0.1.3, helix-carve 0.1.4, vim-carve 0.1.4. The Zed registry entry is still 0.1.1 until zed-industries/extensions#7709 merges.

Updated 2026-09-23 (0.1.6 cycle + release round): the whole page was reconciled against live tags and live registry queries, because it had drifted three to four releases behind in the core. Core is now spec 0.1.6, carve-js 0.1.7, carve-rs 0.1.6, carve-php 0.1.9, with all four engines pinning spec 1cbd2c3. Sixteen downstream repos released the same night, every one of them shipping spec 0.1.6's include feature or a bumped engine: astro-carve, docusaurus-carve, eleventy-carve, vite-plugin-carve, webpack-loader-carve, carve-components, zensical-carve, mkdocs-carve 0.1.1, jekyll-carve v0.1.2, hugo-carve v0.1.1, rouge-carve 0.1.1, carve-rb v0.1.5, carve-py v0.1.5, emacs-carve 0.1.4, sublime-carve 0.1.6, sublime-carve-lsp 0.1.2. carve-press v0.1.3 was found half-released and finished. Rows that were factually wrong, not merely stale: carve-wasm, carve-hexapdf, pdf-to-carve, mkdocs-carve, zensical-carve and jekyll-carve were each described as prepared-but-not-tagged and had all shipped; carve-components and the npm static-site satellites were listed unpublished and are live; carve-press was listed as absent from npm; carve-php-chat was listed as having no tag and no package. The structural cause of the recurring "draft left behind" problem was found and fixed in 22 workflows - see the 2026-09-22 gotchas.

Updated 2026-10-01 (stylesheet round): carve-css 0.1.2 and wp-carve 0.1.7 are live on npm and WordPress.org. Both came out of a cross-repo audit of every Carve stylesheet in the org, which measured fourteen of them across eleven repos, 8396 lines, and found the panel bug in exactly one place: the published carve-css package. Zero of the thirteen host stylesheets carried it, and five had already solved the same problem independently - reveal-carve before carve-css did - so the duplication had not spread the defect the inventory was built to find. The audit's other headline, a 1.25:1 highlight in reveal-carve, did not reproduce either: it measured 16.86:1, because a user agent gives mark a color that beats inheritance. wp-carve's 1.01:1 was real for the inverse reason, declaring color: inherit explicitly. Six bugs fixed across carve-css, wp-carve, reveal-carve, carve-press, intellij-carve and the carve docs site; carve-pdf's vendored fork resynced to a zero delta. Rows that were factually wrong rather than stale: intellij-carve was listed 0.1.9 and is 0.1.10 on the Marketplace, and carve-latex and reveal-carve were both live on npm with no row at all, carve-latex still listed as awaiting a release decision.