# Parser

Construct a Parser, parse LaTeX, configure strictness, and inspect the knowledge base.

https://texform.dev/api/js/parser

## `Parser`

Kind: class

```ts
Parser(options: ParserOptions | null | undefined)
```

A knowledge-driven LaTeX parser.

`Parser` turns LaTeX source into a [ParseResult](/api/js/parser#ParseResult) by consulting the
knowledge base for command and environment signatures. It does not normalize
— use [TransformEngine](/api/js/transform-engine#TransformEngine) for that. Parsing never throws on malformed
input; failures surface in the result. For the conceptual model, see the
Parsing guide.

Since 0.4.0 the default is [ParseConfig](/api/js/parser#ParseConfig) `LENIENT`
(`rejectUnknown: false`, `abortOnError: false`). Per-call `config` is a
camelCase overlay object: `null` / `undefined` / omitted means not set.
Unknown keys, snake_case keys, arrays in object positions, and wrong scalar
types throw [TexformConfigError](/api/js/utilities#TexformConfigError) with a camelCase path. Omit `knowledgeBase`
to share the default instance, or construct a [KnowledgeBase](/api/js/knowledge-base#KnowledgeBase) to customize packages and entries.

```ts
import { Parser, KnowledgeBase } from 'texform';

const parser = new Parser();
parser.parse(String.raw`\frac{x}{y}`).document?.toLatex(); // '\\frac { x } { y }'
const restricted = new Parser({ knowledgeBase: new KnowledgeBase({ packages: ['base', 'ams'] }) });
```

- [ParseResult](https://texform.dev/api/js/parser.md#ParseResult)
- [TransformEngine](https://texform.dev/api/js/transform-engine.md#TransformEngine)
- [ParseConfig](https://texform.dev/api/js/parser.md#ParseConfig)
- [TexformConfigError](https://texform.dev/api/js/utilities.md#TexformConfigError)
- [KnowledgeBase](https://texform.dev/api/js/knowledge-base.md#KnowledgeBase)
- [Parsing](https://texform.dev/docs/parsing.md)

#### `Parser`

```ts
Parser(options: ParserOptions | null | undefined)
```

Construct a parser with an optional shared knowledge base.

| Name | Type | Default | Description |
| --- | --- | --- | --- |
| `options` | ParserOptions | null | undefined | — | - A [ParserOptions](/api/js/parser#ParserOptions) object, or omit/`null` to load
the default runtime packages with no customization. |

#### `parse`

```ts
parse(src: string, config: ParseConfig | null | undefined): ParseResult
```

Parse a LaTeX string into a [ParseResult](/api/js/parser#ParseResult).

Never throws on malformed input: the result has one of three honest states
(no tree, complete tree, or partial tree with `Error` nodes). Empty input
(`''`) yields a clean, complete document, not `null`.

| Name | Type | Default | Description |
| --- | --- | --- | --- |
| `src` | string | — | - The LaTeX source string. |
| `config` | ParseConfig | null | undefined | — | - A [ParseConfig](/api/js/parser#ParseConfig) overlay, or omit/`null` for the
defaults. |

**Returns** `ParseResult` The parse result (`document` and `diagnostics`).

```ts
const result = new Parser().parse(String.raw`\frac{x}{y}`);
const document = result.document;
const diagnostics = result.diagnostics;
```

- [ParseResult](https://texform.dev/api/js/parser.md#ParseResult)
- [ParseConfig](https://texform.dev/api/js/parser.md#ParseConfig)

#### `defaultParseConfig`

```ts
defaultParseConfig(): Complete<ParseConfig>
```

Return this parser's complete default [ParseConfig](/api/js/parser#ParseConfig).

Every field is present. Use it as a starting point when you want to
change one key and pass the rest through.

**Returns** `Complete<ParseConfig>`

- [ParseConfig](https://texform.dev/api/js/parser.md#ParseConfig)

### Knowledge-base lookups

Query the knowledge the parser loaded. Predicate methods take a single `name`; lookup methods take `name` and a `mode` of `"math"` or `"text"` and return a knowledge-entry object or `null`.

#### `knowledgeBase`

```ts
knowledgeBase(): KnowledgeBase
```

**Returns** `KnowledgeBase`

### Lifecycle

#### `free`

```ts
free(): void
```

Release the WASM handle for this parser immediately.

Prefer a `using` declaration so `[Symbol.dispose]()` runs at scope exit.
After `free()`, further use is invalid. Skipping `free()` is safe:
garbage collection still reclaims the handle, just not at a determined
time. Call `free()` (or use `using`) when many short-lived parsers
would otherwise accumulate WASM memory.

**Returns** `void`

#### `[Symbol.dispose]`

```ts
[Symbol.dispose](): void
```

Release the WASM handle. Same as [Parser.free](/api/js/parser#Parser.free); used by `using`.

**Returns** `void`

- [Parser.free](https://texform.dev/api/js/parser.md#Parser.free)

## `ParserOptions`

Kind: interface

| Name | Type | Description |
| --- | --- | --- |
| `knowledgeBase` | KnowledgeBase | undefined |  |
| `defaultParseConfig` | ParseConfig | null | undefined | Overlay applied to [ParseConfig](/api/js/parser#ParseConfig) `LENIENT` as this parser's default. |

## `ParseConfig`

Kind: interface

Parser strictness configuration overlay, as a plain object with camelCase
keys. All fields are optional; `null` / `undefined` means not set. Unknown
keys, snake_case keys, arrays in object positions, and wrong scalar types
throw [TexformConfigError](/api/js/utilities#TexformConfigError) with a path.

The two boolean axes are orthogonal: [ParseConfig.rejectUnknown](/api/js/parser#ParseConfig.rejectUnknown)
controls how unknown names are handled, while
[ParseConfig.abortOnError](/api/js/parser#ParseConfig.abortOnError) controls whether the parser stops at
the first error or keeps recovering. Neither implies the other, and neither
is equivalent to the resulting tree's [Document.hasErrors](/api/js/document#Document.hasErrors) signal.

| Name | Type | Description |
| --- | --- | --- |
| `rejectUnknown` | boolean | undefined | Reject unknown command and environment names. Default `false`.

When `true`, an unknown command or environment becomes an
`unknown-command` / `unknown-environment` diagnostic. When `false`, unknown
names are preserved as `known: false` nodes for lenient exploration. |
| `abortOnError` | boolean | undefined | Stop at the first error per item instead of recovering. Default `false`.

When `true` (strict), the parser stops at the first error per item and
produces no recovery `Error` nodes. When `false` (lenient), it keeps
collecting diagnostics and emits `Error` placeholder nodes. The
max-group-depth guard emits an `Error` node regardless of this setting.
This is a parse-strictness knob, distinct from [Document.hasErrors](/api/js/document#Document.hasErrors),
which is a property of the resulting tree. |
| `maxGroupDepth` | number | undefined | Maximum group nesting depth before the parser aborts a group. Default
`128`. Exceeding it emits a `max-group-depth-exceeded` diagnostic and an
`Error` node unconditionally. |

```ts
new Parser().parse(String.raw`\foobar{x}`, {
  rejectUnknown: true,
  abortOnError: true,
});
```

- [TexformConfigError](https://texform.dev/api/js/utilities.md#TexformConfigError)
- [ParseConfig.rejectUnknown](https://texform.dev/api/js/parser.md#ParseConfig.rejectUnknown)
- [ParseConfig.abortOnError](https://texform.dev/api/js/parser.md#ParseConfig.abortOnError)
- [Document.hasErrors](https://texform.dev/api/js/document.md#Document.hasErrors)

## `ParseResult`

Kind: interface

The outcome of [Parser.parse](/api/js/parser#Parser.parse) (and [TransformEngine.parse](/api/js/transform-engine#TransformEngine.parse)): an
optional [Document](/api/js/document#Document) plus the diagnostics emitted while parsing.

There are exactly three honest states, and `parse` never throws on malformed
input nor fabricates a placeholder tree:

- **Hard failure** — `document` is `null`; the failure is described entirely
  by `diagnostics`.
- **Clean parse** — `document` is a complete, editable tree with
  `hasErrors() === false`. Empty input (`''`) lands here, not in `null`.
- **Partial parse** — `document` is present with `hasErrors() === true`;
  recovery preserved the unparseable parts as read-only `Error` nodes.

| Name | Type | Description |
| --- | --- | --- |
| `document` | Document | null | The parsed document, or `null` on a hard failure with no tree. |
| `diagnostics` | ParseDiagnostic[] | Diagnostics emitted while parsing; may be empty on a clean parse. |

- [Parser.parse](https://texform.dev/api/js/parser.md#Parser.parse)
- [TransformEngine.parse](https://texform.dev/api/js/transform-engine.md#TransformEngine.parse)
- [Document](https://texform.dev/api/js/document.md#Document)

## `ParseDiagnostic`

Kind: interface

One diagnostic emitted while parsing, describing a recovered or rejected
condition.

Diagnostics are a separate channel from `Error` placeholder nodes: a
diagnostic does not by itself make an otherwise editable tree read-only.
Within a parser-produced result, however, a tree that
[Document.hasErrors](/api/js/document#Document.hasErrors) always comes with at least one diagnostic.

| Name | Type | Description |
| --- | --- | --- |
| `kind` | ParseDiagnosticKind | null | The diagnostic category, or `null` when uncategorized. |
| `message` | string | Human-readable description of the problem. |
| `span` | Span | Source span the diagnostic points at. |
| `expected` | string[] | Tokens the parser expected at this position; may be empty. |
| `found` | string | null | The token actually found, or `null`. |
| `contexts` | ParseDiagnosticContext[] | Enclosing-construct frames, outermost-relevant first; may be empty. |

- [Document.hasErrors](https://texform.dev/api/js/document.md#Document.hasErrors)
- [ParseResult](https://texform.dev/api/js/parser.md#ParseResult)

## `ParseDiagnosticContext`

Kind: interface

One nested context frame attached to a [ParseDiagnostic](/api/js/parser#ParseDiagnostic), locating the
enclosing construct (such as the command or environment) the error occurred
within.

| Name | Type | Description |
| --- | --- | --- |
| `label` | string | Human-readable label for the enclosing construct. |
| `span` | Span | Source span of the enclosing construct. |

- [ParseDiagnostic](https://texform.dev/api/js/parser.md#ParseDiagnostic)

## `ParseDiagnosticKind`

Kind: typeAlias

```ts
"ambiguous-infix" | "argument-validation" | "command-mode-error" | "comment-truncated-argument" | "environment-mode-error" | "environment-name-mismatch" | "invalid-character" | "left-right-delimiter" | "max-group-depth-exceeded" | "raw-expected-found" | "text-script-error" | "unclosed-environment" | "unclosed-inline-math" | "unexpected-math-shift" | "unknown-command" | "unknown-environment"
```

The category of a [ParseDiagnostic](/api/js/parser#ParseDiagnostic), or `null` when the parser emits a
diagnostic without a specific category.

Each variant names a distinct recoverable or rejected parse condition, such
as an unknown command, an argument-validation failure, or an unclosed inline
math span.

- [ParseDiagnostic](https://texform.dev/api/js/parser.md#ParseDiagnostic)

## `Span`

Kind: interface

A source byte range, half-open as `[start, end)`, indexing into the original
LaTeX input.

| Name | Type | Description |
| --- | --- | --- |
| `start` | number | Inclusive start byte offset. |
| `end` | number | Exclusive end byte offset. |

## `SyntaxNode`

Kind: typeAlias

```ts
{ Root: { mode: SyntaxContentMode; children: SyntaxNode[] } } | { Group: { mode: SyntaxContentMode; kind: GroupKind; children: SyntaxNode[]; }; } | { Command: { name: string; args: ArgumentSlot[]; known: boolean } } | { Infix: { name: string; args: ArgumentSlot[]; left: SyntaxNode; right: SyntaxNode; }; } | { Declarative: { name: string; args: ArgumentSlot[] } } | { Environment: { name: string; args: ArgumentSlot[]; known: boolean; body: SyntaxNode; }; } | { Scripted: { base: SyntaxNode; subscript?: SyntaxNode; superscript?: SyntaxNode; }; } | { Prime: { count: number } } | { Error: { message: string; snippet: string } } | { Text: string } | { Char: string } | "ActiveSpace" | "AlignmentTab"
```

The lossless, immutable parse snapshot — the single serde wire format.

`SyntaxNode` is a plain object (not a class instance) that backs JSON
snapshots, transport across the binding, and test fixtures. It can represent
a partial parse: unparseable fragments survive as `Error` nodes. It carries
no editing behavior; bridge it into an editable tree with
[Document.fromSyntax](/api/js/document#Document.fromSyntax), and recover one with [Document.toSyntax](/api/js/document#Document.toSyntax).
The two conversions are symmetric over every node kind, including `Error` and
`Prime`. A `Prime` node represents symbols in the current math list;
`Scripted` supplies any superscript binding. A leading quote has an empty
group as its scripted base. External snapshots cannot infer the old intent
of a bare `Prime` node; reparse the source or update the tree explicitly.

- [Document.fromSyntax](https://texform.dev/api/js/document.md#Document.fromSyntax)
- [Document.toSyntax](https://texform.dev/api/js/document.md#Document.toSyntax)
- [Document](https://texform.dev/api/js/document.md#Document)

## `ContextItem`

Kind: typeAlias

```ts
{ target: "command"; name: string; kind: CommandKind; allowedMode: string; argspec: string; tags?: string[]; } | { target: "environment"; name: string; allowedMode: string; bodyMode: RuntimeContentMode; argspec: string; tags?: string[]; } | { target: "delimiter"; name: string; }
```

One custom knowledge entry supplied to [KnowledgeBase](/api/js/knowledge-base#KnowledgeBase)
through the `items` option, discriminated by
`target`.

A `command` entry carries its kind, allowed mode, and `argspec`; an
`environment` entry additionally carries its `bodyMode`; a `delimiter` entry
registers a delimiter-control name. Unknown keys and disallowed fields throw
[TexformConfigError](/api/js/utilities#TexformConfigError).

- [KnowledgeBase](https://texform.dev/api/js/knowledge-base.md#KnowledgeBase)
- [TexformConfigError](https://texform.dev/api/js/utilities.md#TexformConfigError)

## `CommandInfo`

Kind: interface

The knowledge-base entry for a command, returned by
[KnowledgeBase.lookupCommand](/api/js/knowledge-base#KnowledgeBase.lookupCommand) and related lookups.

| Name | Type | Description |
| --- | --- | --- |
| `name` | string | The command name, without the leading backslash. |
| `kind` | CommandKind | The command's syntactic role (prefix, infix, declarative). |
| `allowedMode` | string | The modes the command is allowed in. |
| `specString` | string | The raw xparse-style argument-specification string. |
| `fromPackages` | string[] | The knowledge packages that define this command. |
| `tags` | string[] | Free-form classification tags. |
| `args` | ParsedArgSpecSlot[] | The parsed argument slots, mirroring [validateArgspec](/api/js/validate-argspec#validateArgspec) output. |

- [KnowledgeBase.lookupCommand](https://texform.dev/api/js/knowledge-base.md#KnowledgeBase.lookupCommand)

## `EnvInfo`

Kind: interface

The knowledge-base entry for an environment, returned by
[KnowledgeBase.lookupEnv](/api/js/knowledge-base#KnowledgeBase.lookupEnv).

| Name | Type | Description |
| --- | --- | --- |
| `name` | string | The environment name. |
| `allowedMode` | string | The modes the environment is allowed in. |
| `bodyMode` | RuntimeContentMode | The content mode the environment body is parsed in. |
| `specString` | string | The raw xparse-style argument-specification string. |
| `fromPackages` | string[] | The knowledge packages that define this environment. |
| `tags` | string[] | Free-form classification tags. |
| `args` | ParsedArgSpecSlot[] | The parsed argument slots for the environment's arguments. |

- [KnowledgeBase.lookupEnv](https://texform.dev/api/js/knowledge-base.md#KnowledgeBase.lookupEnv)

## `CharacterInfo`

Kind: interface

The knowledge-base entry for a special character, returned by
[KnowledgeBase.lookupCharacter](/api/js/knowledge-base#KnowledgeBase.lookupCharacter).

| Name | Type | Description |
| --- | --- | --- |
| `name` | string | The character name, without the leading backslash. |
| `allowedMode` | string | The modes the character is allowed in. |
| `unicodeValue` | string | The Unicode code point the character maps to, as a string. |
| `attributes` | CharacterAttributesInfo | Rendering attributes such as `mathvariant`. |
| `package` | string | The knowledge package that defines this character. |

- [KnowledgeBase.lookupCharacter](https://texform.dev/api/js/knowledge-base.md#KnowledgeBase.lookupCharacter)

## `CharacterAttributesInfo`

Kind: interface

Rendering attributes for a special character in the knowledge base.

| Name | Type | Description |
| --- | --- | --- |
| `mathvariant` | string | null | The MathML `mathvariant` the character renders with, or `null`. |

## `AllowedMode`

Kind: typeAlias

```ts
"math" | "text" | "both"
```

The content modes a command, environment, or character is allowed in:
`"math"`, `"text"`, or `"both"`.

## `CommandKind`

Kind: typeAlias

```ts
"prefix" | "infix" | "declarative"
```

The syntactic role of a command in the knowledge base: `"prefix"` (takes its
arguments after the control sequence), `"infix"` (binds operands on both
sides, like `\over`), or `"declarative"` (a scope-affecting declaration).

## `ArgSpecKindInfo`

Kind: typeAlias

```ts
{ type: "content"; mode: RuntimeContentMode } | { type: "operatorname" } | { type: "delimiter" } | { type: "csname" } | { type: "dimension" } | { type: "integer" } | { type: "keyval" } | { type: "column" } | { type: "star" }
```

The value kind one parsed argument slot accepts, with a `type` discriminator.

`content` carries the [RuntimeContentMode](/api/js/node#RuntimeContentMode) its body parses in; the
other variants are leaf kinds (operatorname, delimiter, csname, dimension,
integer, keyval, column, star).

- [RuntimeContentMode](https://texform.dev/api/js/node.md#RuntimeContentMode)
- [ParsedArgSpecSlot](https://texform.dev/api/js/validate-argspec.md#ParsedArgSpecSlot)

## `DelimiterTokenInfo`

Kind: typeAlias

```ts
{ type: "char"; value: string } | { type: "control-seq"; value: string }
```

A single delimiter token in an argspec form: a literal `char` (such as `(`)
or a `control-seq` (such as `langle`).

## `ArgSpecFormInfo`

Kind: typeAlias

```ts
{ type: "standard" } | { type: "star" } | { type: "group" } | { type: "until"; close: DelimiterTokenInfo } | { type: "delimited"; open: DelimiterTokenInfo; close: DelimiterTokenInfo } | { type: "paired"; pairs: Array<{ open: DelimiterTokenInfo; close: DelimiterTokenInfo }>; }
```

The syntactic form one parsed argument slot takes, with a `type`
discriminator: a `standard` argument, a `star` flag, a brace `group`, a
`delimited` argument bounded by an `open`/`close` pair, or a `paired` argument
accepting any of several interchangeable delimiter `pairs`.

- [ParsedArgSpecSlot](https://texform.dev/api/js/validate-argspec.md#ParsedArgSpecSlot)

