ferriki 0.10.0

Reusable native Rust syntax highlighter with TextMate grammars
Documentation

Part of Ferramenta, a family of Rust tools.

Ferriki

Powered by Sebastian Software CI Coverage gate >= 89% License: MIT OR Apache-2.0 Node >= 22.13.0 npm version crates.io docs.rs

Ferriki provides Shiki-shaped HTML syntax highlighting through a lean Rust core and Node bindings.

It keeps familiar highlighter factories and HTML calls, while removing the old JS/WASM multi-engine direction from the runtime. The goal is simple: keep the developer experience familiar, move the heavy lifting into Rust, and end up with a smaller, cleaner architecture that is easier to reason about and easier to ship.

Why Ferriki

  • Shiki-shaped HTML API: reusable highlighters and familiar highlight options support common migrations.
  • Rust-first by design: grammar handling, theme application, state management, and rendering belong in the native core.
  • Standard language and theme assets load lazily from a release-pinned CDN, so their payloads stay out of the packages.
  • Leaner runtime shape: no product dependency on the historical JS/WASM engine stack.
  • Verifiable compatibility: the Node layer is checked against a strict mirrored Shiki release-tag suite, while the tokenizer is checked against a pinned vscode-textmate oracle.

Ferriki is for teams that like Shiki's familiar highlighter and HTML flow and want a cleaner native foundation underneath.

Product Scope

Ferriki is intentionally narrow right now.

Area Status Notes
Core highlighting runtime Integrated Native Rust core, Node bindings, Shiki-shaped HTML rendering API
HTML output Primary Node path codeToHtml renders HTML; styleMode: "classes" adds nested scope classes; codeToHtmlWithCss also returns resolved theme CSS
HAST and token output Removed before 1.0 Standalone Node methods are removed; typed token/HAST data remain available to HTML transformer callbacks, and Rust token APIs remain public
Transformers Integrated User-supplied JavaScript hooks receive internal token/HAST data while rendering HTML (ADR 0008)
Optional Vite adapter Available @ferriki/vite highlights marked HTML and static JSX during Vite transforms, outside the core runtime
colorized-brackets, markdown-it, rehype, and VitePress integrations Out of scope These remain optional adapter projects, not Ferriki core exports

Removing public Node HAST and token methods before 1.0 is an intentional breaking divergence from Shiki, with no deprecated aliases or compatibility package. See ADR 0017 and the migration guide for the supported path.

The mirrored Shiki workspace under node/compat/upstream/shiki exists to verify compatibility claims. It is not a statement that every mirrored package is a Ferriki feature.

Products

This repository has a Rust library and a Node package:

  • ferriki (repository root package): reusable Rust highlighter and renderer
  • node/ferriki: the Node-facing package surface

The private ferriki-core crate hosts the N-API binding over the same Rust runtime.

Repository Layout

Contributor workflow, test lanes, and the mirror rules are documented in CONTRIBUTING.md.

User-facing documentation lives in the docs/ directory:

The repository root is intentionally Rust-first. All Node, npm, and upstream compatibility machinery lives under node.

Quick Start

Prerequisites: a stable Rust toolchain (cargo), Node.js >= 22.13.0, and pnpm (the pinned version in node/package.json is picked up via corepack).

Rust:

cargo check -p ferriki-core

Node (build:native compiles the Rust core and copies the addon into the package):

cd node
pnpm install --ignore-scripts
pnpm run prepare:compat
pnpm run build:native
pnpm run test:ferriki-compat:textmate

The compatibility workspace contains upstream prepare scripts that rewrite generated files. Installs intentionally skip package lifecycle scripts; the explicit prepare:compat command runs those generators in a temporary checkout and keeps the tracked mirror immutable.

The TextMate compatibility lane runs selected, unchanged Shiki tests with honest aliases so every highlighted result passes through the native addon. The broader test:ferriki-compat:core lane also runs the Ferriki-owned API, error, catalog, registration, multi-theme, transformer, token-state, packaging, and Ferromark/Ardo contract checks. Upstream cases outside that accepted boundary remain explicitly classified in the compatibility manifest.

Class-based output (next release)

Inspired by GitHub's PrettyLights and wooorm's starry-night.

Use styleMode: "classes" for nested scope classes and custom CSS. codeToHtmlWithCss returns { html, css } using unchanged TextMate themes, including theme maps that switch via data-ferriki-theme without retokenizing. See the class-based highlighting guide for examples and integration details.

Compatibility

Ferriki tracks one approved Shiki release tag at a time — currently Shiki v4.4.3 (machine-readable source of truth: node/compat/upstream/shiki/.source.json).

  • Upstream-derived files under node/compat/upstream/shiki are mirrored, not hand-edited.
  • vscode-textmate source and tests under node/compat/upstream/vscode-textmate are likewise pinned and never hand-edited.
  • Ferriki-specific behavior lives outside that mirror, mainly in node/compat/harness and the Ferriki product paths.
  • “Shiki-compatible” in this repository means compatibility is intended to be checked, not just claimed.
  • Compatibility coverage is broader than product scope. Ferriki may still test selected optional upstream adapters separately, but that does not make them first-class Ferriki features.

Status

The native TextMate runtime from issue #30 is implemented. It is a mechanical port of pinned vscode-textmate v9.3.2 onto the Scanner API of Ferroni, integrated with Ferriki's asset catalogs, native renderer, N-API host, and focused Node surface. Its inner vscode-textmate oracle and honest Shiki v4.4.3 structural gate are green.

The accepted API contract and its focused checks own token/state, lifecycle, transformer, and registration behavior. Upstream adapter fixtures that do not describe Ferriki's native boundary remain classified as explicit non-goals. The current core direction is:

  • Rust owns runtime behavior
  • Node is the thin facade and compatibility layer
  • optional ecosystem adapters do not define the core product boundary or release gate

License

Licensed under either of MIT or Apache-2.0 at your option.

More from Ferramenta

Ferramenta — A family of Rust tools.

Engines

Tool Job
ferroni Oniguruma-compatible regex engine
ferromark Markdown to HTML, sanitized by default
ferrolex Spell checking for text and code
ferrocat Translation catalog engine
ferralk Glob matching and parallel filesystem walking
ferrugo PDF previews for untrusted files

Applications

Tool Job
palamedes Internationalization for TypeScript applications
dalo Your team's agent setup, versioned like code