v0.2.0
This release adds in-place document normalization to the Python and JavaScript bindings, teaches the parser and serializer to preserve whitespace and spacing faithfully, and makes parsing and transforming large formulas dramatically faster.
Added
TransformEngine.transformon the Python and JavaScript bindings, for normalizing a liveDocumentin place. Every parsed document is stamped with a parse-context id, and a document produced by a different parser (or byDocument.from_syntax) is rejected with a foreign-document error, so a document is only transformed by the engine that produced it.:Ooperator-name argspec content, so arguments to\operatornameand\DeclareMathOperatorare modeled as math content and serialized compactly without special-casing command names.- Typed serialization options for the Python bindings:
serialize()andDocument.to_latex()now accept a documentedSerializeOptionsTypedDict instead of an untypeddict, mirroring the TypeScript option interfaces.
Changed
- Breaking: the public
Errorenum is now#[non_exhaustive]. Exhaustivematcharms overtexform::Errorin downstream Rust must add a wildcard arm; in return, future error variants can be introduced without another breaking change. - Parsing and transforming large formulas is dramatically faster. Release builds no longer run debug-only structural invariant sweeps, which were quadratic on wide formulas (a 60k-character formula now parses ~14× faster and transforms ~45× faster); source spans are carried as a positional tree (10–25% faster parsing); and rewrite rules are indexed by trigger name (31–48% faster transforms). Normalized output is byte-identical.
Fixed
- Edge whitespace in text arguments is preserved:
\text{ or }and\textbf{ a }no longer drop their leading and trailing spaces on parse, serialize, or transform. - Adjacent math digits stay compact: multi-digit numbers such as
1093^2no longer serialize as1 0 9 3 ^ { 2 }under the default spacing option, while letters and symbols still honor it. - Tight argspec slot spacing is preserved, so no-leading-space slots — including linebreak dimensions and custom tight optional slots — stay tight through parse/serialize round trips.
- Whitespace is kept outside attribute wrappers during transforms.
- Inline math inside text-mode control sequences, and whitespace-only text arguments, are now accepted.
- The recovery parser is hardened against an unnecessary unwrap.
- The license file is included in the Python sdist.