Documentation
¶
Overview ¶
Package textmate provides pure-Go, line-oriented tokenization using TextMate grammars. Token offsets are rune indices. Callers pass each LineResult's immutable RuleStack into the next line and may compare saved stacks with StateStack.Equal when incrementally re-tokenizing edited documents.
Index ¶
- Constants
- Variables
- type Document
- func (d *Document) InvalidateFrom(index int) error
- func (d *Document) Len() int
- func (d *Document) Line(index int) (LineResult, bool)
- func (d *Document) MaterializedLines() int
- func (d *Document) ReplaceLines(start, end int, replacement []string) error
- func (d *Document) SetLines(lines []string)
- func (d *Document) StateAt(index int) (*StateStack, bool)
- type DocumentOptions
- type Grammar
- type IncludeString
- type LineResult
- type Location
- type RawCaptures
- type RawGrammar
- type RawInjections
- type RawRepository
- type RawRule
- type RegExpString
- type Registry
- type RegistryOptions
- type RuleFactory
- type ScopeStack
- type ScopeStackID
- type StateStack
- type StopReason
- type Token
- type TokenCategory
- type TokenizeOptions
Constants ¶
const DefaultDocumentCacheCapacity = 20_000
DefaultDocumentCacheCapacity is the number of distinct line/state results retained by a Document when DocumentOptions.CacheCapacity is zero.
Variables ¶
var ErrInvalidLineRange = errors.New("textmate: invalid document line range")
ErrInvalidLineRange is returned when ReplaceLines receives a range outside the current document or one whose start is after its end.
InitialState is the sentinel passed when tokenizing the first line.
Functions ¶
This section is empty.
Types ¶
type Document ¶
type Document struct {
// contains filtered or unexported fields
}
Document incrementally tokenizes an editable sequence of lines. It owns a shallow copy of the supplied line slice, carries start states between lines, and reuses an unchanged suffix after an edit as soon as tokenizer state converges with the previous suffix.
All methods are safe to call concurrently. Results returned by Line are immutable, library-owned views and must not be modified; this permits cache hits without allocating. A result remains valid after later calls and cache eviction. Copy the Tokens slice before changing Token fields. ScopeStack and Token.Scopes remain library-owned and read-only, as they are for Grammar.TokenizeLine.
func NewDocument ¶
func NewDocument(grammar *Grammar, options DocumentOptions) *Document
NewDocument creates an empty document backed by grammar. A nil grammar is valid: lines remain addressable, but Line returns empty tokenization results.
func (*Document) InvalidateFrom ¶
InvalidateFrom discards materialized states for line index and all following lines, and clears the result cache. Index may equal Len. The next Line or StateAt call recomputes the discarded range.
Time-limit stops are never cached, and a state that came from one is recomputed on the next Line, StateAt or MaterializedLines call, a bounded number of times. InvalidateFrom forces the complete tail to be recomputed regardless, for example after a grammar or theme change on the caller side.
func (*Document) Line ¶
func (d *Document) Line(index int) (LineResult, bool)
Line returns the tokenization result for line index. The boolean is false when index is outside the current document. Requesting a line computes any missing start states above it and records the line's resulting state.
The returned result and its Tokens slice are immutable, library-owned views. They remain valid after later calls and cache eviction. See Document's ownership documentation.
func (*Document) MaterializedLines ¶ added in v0.2.1
MaterializedLines returns how many leading lines have a known start state. Line(index) for an index below it tokenizes only that line; a larger index first tokenizes every line from MaterializedLines up to it. An edit lowers it to the first changed line until recomputation converges with the old tail.
func (*Document) ReplaceLines ¶
ReplaceLines replaces the half-open line range [start, end) with a shallow copy of replacement. It returns ErrInvalidLineRange without changing the document when the range is invalid.
Lines and states are spliced in place, so an edit costs the replaced lines plus shifting the ones after them, rather than copying and comparing the whole document as SetLines does.
type DocumentOptions ¶
type DocumentOptions struct {
// TokenizeOptions is applied to every line tokenized by the document.
TokenizeOptions TokenizeOptions
// CacheCapacity bounds cached results keyed by line text and canonical
// start state. Zero selects DefaultDocumentCacheCapacity. A negative value
// disables result caching.
CacheCapacity int
}
DocumentOptions configures a Document. Options are fixed at construction.
type Grammar ¶
type Grammar struct {
// contains filtered or unexported fields
}
Grammar is a compiled TextMate grammar. Compilation remains lazy: rules and their regular expressions are created only when the grammar is first used. A Grammar serializes tokenization because compiled rules contain mutable scanner caches.
func (*Grammar) Diagnostics ¶
func (g *Grammar) Diagnostics() []oniguruma.Diagnostic
Diagnostics returns regex translation, compilation, and match diagnostics from rules compiled or exercised so far. Grammars compile lazily, so callers should take another snapshot after tokenizing new syntax paths. Equivalent diagnostics produced by anchor variants or shared rule lists are returned once.
func (*Grammar) TokenizeLine ¶
func (g *Grammar) TokenizeLine(line string, prev *StateStack) LineResult
TokenizeLine tokenizes line and returns immutable state to pass to the next call. A nil state and InitialState both begin a new document.
func (*Grammar) TokenizeLineWithOptions ¶
func (g *Grammar) TokenizeLineWithOptions( line string, prev *StateStack, options TokenizeOptions, ) LineResult
TokenizeLineWithOptions tokenizes line with optional soft time and line-size limits. StoppedAt is the first unparsed rune offset when Stopped is true. See TokenizeOptions for the precise limit semantics.
type IncludeString ¶
type IncludeString = string
IncludeString is a TextMate include reference such as "#rule", "$self", or "source.js#rule".
type LineResult ¶
type LineResult struct {
Tokens []Token
RuleStack *StateStack
// Stopped remains the compatibility signal for an incomplete parse.
Stopped bool
// StoppedReason is StopReasonNone when Stopped is false.
StoppedReason StopReason
// StoppedAt is the first unparsed rune offset when Stopped is true.
StoppedAt int
}
LineResult is the result of tokenizing one line.
type Location ¶
type Location struct {
Filename string `json:"filename"`
Line int `json:"line"`
Char int `json:"char"`
}
Location identifies a value in a source grammar. Plain JSON grammars do not normally contain it, but vscode-textmate can attach it while parsing.
type RawCaptures ¶
RawCaptures maps numeric capture group names to their rules.
func (*RawCaptures) UnmarshalJSON ¶
func (captures *RawCaptures) UnmarshalJSON(data []byte) error
UnmarshalJSON accepts both the specified object form and the array form emitted by a few converted TextMate grammars. Invalid capture entries are ignored, matching JavaScript's permissive property access on those values.
type RawGrammar ¶
type RawGrammar struct {
Repository RawRepository `json:"repository"`
ScopeName string `json:"scopeName"`
Patterns []*RawRule `json:"patterns"`
Injections RawInjections `json:"injections,omitempty"`
InjectionSelector string `json:"injectionSelector,omitempty"`
FileTypes []string `json:"fileTypes,omitempty"`
Name string `json:"name,omitempty"`
FirstLineMatch RegExpString `json:"firstLineMatch,omitempty"`
Location *Location `json:"$vscodeTextmateLocation,omitempty"`
}
RawGrammar is the JSON representation of a TextMate grammar.
func ParseRawGrammar ¶
func ParseRawGrammar(data []byte) (*RawGrammar, error)
ParseRawGrammar decodes a JSON TextMate grammar.
type RawInjections ¶
RawInjections maps scope selector expressions to injected rules.
type RawRepository ¶
RawRepository maps grammar-defined repository names to rules.
func (*RawRepository) UnmarshalJSON ¶
func (repository *RawRepository) UnmarshalJSON(data []byte) error
UnmarshalJSON ignores malformed non-object entries found in a small number of converted grammars. JavaScript loads these values but they do not compile into meaningful rules.
type RawRule ¶
type RawRule struct {
Include *IncludeString `json:"include,omitempty"`
Name *string `json:"name,omitempty"`
ContentName *string `json:"contentName,omitempty"`
Match *RegExpString `json:"match,omitempty"`
Captures RawCaptures `json:"captures,omitempty"`
Begin *RegExpString `json:"begin,omitempty"`
BeginCaptures RawCaptures `json:"beginCaptures,omitempty"`
End *RegExpString `json:"end,omitempty"`
EndCaptures RawCaptures `json:"endCaptures,omitempty"`
While *RegExpString `json:"while,omitempty"`
WhileCaptures RawCaptures `json:"whileCaptures,omitempty"`
Patterns []*RawRule `json:"patterns,omitempty"`
Repository RawRepository `json:"repository,omitempty"`
ApplyEndPatternLast bool `json:"applyEndPatternLast,omitempty"`
Location *Location `json:"$vscodeTextmateLocation,omitempty"`
}
RawRule is one rule in a TextMate grammar.
func (*RawRule) UnmarshalJSON ¶
type RegExpString ¶
type RegExpString = string
RegExpString is a regular expression in the grammar's Oniguruma dialect.
type Registry ¶
type Registry struct {
// contains filtered or unexported fields
}
Registry owns raw and compiled grammars and resolves their transitive dependencies. Callback invocations never occur while the registry lock is held.
func NewRegistry ¶
func NewRegistry(options RegistryOptions) *Registry
NewRegistry constructs an empty lazy-loading grammar registry.
type RegistryOptions ¶
type RegistryOptions struct {
LoadGrammar func(scopeName string) (*RawGrammar, error)
GetInjections func(scopeName string) []string
}
RegistryOptions provides the callbacks used to lazily resolve grammars. A loader may return (nil, nil) when a scope is not available. Missing root grammars are errors; missing optional dependencies are ignored.
type RuleFactory ¶
type RuleFactory struct {
// contains filtered or unexported fields
}
RuleFactory turns raw grammar nodes into registered rules. A factory belongs to one compiled Grammar; keeping raw node identity here avoids mutating the public JSON model with compilation state.
type ScopeStack ¶
type ScopeStack struct {
// contains filtered or unexported fields
}
ScopeStack is an immutable, interned sequence of TextMate scope names. Equal scope sequences produced by one Grammar have the same *ScopeStack and ScopeStackID, including when the tokenizer reconstructed its internal stack. A ScopeStack remains valid after its Grammar or Registry is no longer used.
ScopeStack values are owned by the library and must not be modified. Its accessors are safe to call concurrently.
func (*ScopeStack) At ¶
func (s *ScopeStack) At(index int) (string, bool)
At returns the scope name at index and whether index is in range.
func (*ScopeStack) Category ¶
func (s *ScopeStack) Category() TokenCategory
Category returns the cached coarse category of s. A nil ScopeStack is plain. The first call computes the result; subsequent calls are lock-free and allocate no memory.
func (*ScopeStack) ID ¶
func (s *ScopeStack) ID() ScopeStackID
ID returns the stable runtime identity of s. A nil ScopeStack has the zero ID.
func (*ScopeStack) Names ¶
func (s *ScopeStack) Names() []string
Names returns a fresh copy of the scope names, ordered outermost first.
func (*ScopeStack) Range ¶
func (s *ScopeStack) Range(yield func(string) bool)
Range calls yield for each scope name, ordered outermost first. Iteration stops when yield returns false.
type ScopeStackID ¶
type ScopeStackID struct {
// contains filtered or unexported fields
}
ScopeStackID identifies one interned scope-name stack. IDs are comparable and unique within the current process, so they can be used directly as map keys. The zero value does not identify a scope stack.
An ID remains valid for as long as the ScopeStack that returned it is reachable. IDs are runtime identities and must not be persisted.
func (ScopeStackID) IsZero ¶
func (id ScopeStackID) IsZero() bool
IsZero reports whether id is the zero value.
type StateStack ¶
type StateStack struct {
// contains filtered or unexported fields
}
StateStack is an immutable tokenizer state. A returned state can safely be retained and compared after subsequent lines have been tokenized.
While two equal states returned by the same Grammar are both live, they are represented by the same *StateStack. This makes pointers suitable as short-lived cache keys. The identity is scoped to one Grammar and lasts only as long as the state remains reachable; use Equal after discarding all previously returned equal states. States are not transferable between grammars, and no pointer identity is promised across Grammar instances.
func (*StateStack) Equal ¶
func (s *StateStack) Equal(other *StateStack) bool
Equal reports whether two stacks represent the same reusable tokenizer state. Line-local enter and anchor positions are intentionally ignored, as they are by vscode-textmate.
func (*StateStack) String ¶
func (s *StateStack) String() string
type StopReason ¶
type StopReason uint8
StopReason explains why a LineResult stopped before fully parsing its line.
const ( // StopReasonNone means the line was fully tokenized. StopReasonNone StopReason = iota // StopReasonTimeLimit means the soft time budget was exhausted. StopReasonTimeLimit // StopReasonLineLimit means a byte or rune line-length cap was exceeded. StopReasonLineLimit )
func (StopReason) String ¶
func (r StopReason) String() string
type Token ¶
type Token struct {
Start int
End int
Scopes []string
ScopeStack *ScopeStack `json:"-"`
}
Token is one contiguous span of a tokenized line. Start and End are rune offsets into the original line, and Scopes is ordered outermost first.
ScopeStack is the immutable, comparable identity for Scopes. Equal scope sequences from the same Grammar reuse both ScopeStack and the backing array of Scopes. Scopes is retained for source compatibility and must be treated as read-only; callers that need to modify it should copy it first.
func (Token) Category ¶
func (token Token) Category() TokenCategory
Category returns the token's coarse semantic category. It uses the cached ScopeStack classification when available and falls back to Scopes for tokens constructed by callers or older integrations.
type TokenCategory ¶
type TokenCategory uint8
TokenCategory is a coarse semantic classification derived from TextMate scope names. It is intentionally independent of colors and font styles. Applications can map categories to their own presentation or use a full TextMate theme resolver when selector-accurate styling is required.
const ( TokenCategoryPlain TokenCategory = iota TokenCategoryComment TokenCategoryString TokenCategoryRegexp TokenCategoryNumber TokenCategoryKeyword TokenCategoryOperator TokenCategoryFunction TokenCategoryTag TokenCategoryAttribute TokenCategoryType TokenCategoryBuiltin TokenCategoryVariable TokenCategoryHeading TokenCategoryBold TokenCategoryItalic TokenCategoryQuote TokenCategoryInserted TokenCategoryDeleted TokenCategoryPunctuation TokenCategoryInvalid )
func ClassifyScopes ¶
func ClassifyScopes(scopes []string) TokenCategory
ClassifyScopes returns a coarse category for a TextMate scope stack ordered outermost first. The innermost recognized scope wins. Within one scope, the longest prefix at a dot boundary wins. Plain is returned when no scope is recognized and for deliberate reset scopes such as meta.embedded.
Classification is a heuristic semantic layer, not TextMate theme resolution. The function does not retain or modify scopes and allocates no memory.
func (TokenCategory) String ¶
func (category TokenCategory) String() string
String returns the stable, lower-case name of category.
type TokenizeOptions ¶
TokenizeOptions bounds work performed by TokenizeLineWithOptions. Zero or negative values disable the corresponding limit.
TimeLimit is a soft budget for the complete call, including waiting for the grammar lock, lazy root compilation, and begin/while condition setup. The tokenizer checks the budget between regexp searches; an in-flight regexp search cannot be interrupted and can therefore overrun the budget.
MaxLineBytes and MaxLineRunes are independent. A line is skipped when it exceeds either enabled limit. Limits are checked before the newline-appended Oniguruma input and its rune buffer are allocated.
Source Files
¶
Directories
¶
| Path | Synopsis |
|---|---|
|
cmd
|
|
|
grammar-report
command
Command grammar-report scans a tm-grammars checkout for parser, dependency, and regular-expression compatibility failures.
|
Command grammar-report scans a tm-grammars checkout for parser, dependency, and regular-expression compatibility failures. |
|
grammar-size-probe
command
Command grammar-size-probe is the minimal executable used for reproducible embedded-grammar binary-size measurements.
|
Command grammar-size-probe is the minimal executable used for reproducible embedded-grammar binary-size measurements. |
|
textmate-cli
command
|
|
|
conformance
|
|
|
corpus/general
command
|
|
|
Code generated by gen-grammars; DO NOT EDIT.
|
Code generated by gen-grammars; DO NOT EDIT. |
|
internal
|
|
|
cmd/gen-grammars
command
Command gen-grammars deterministically generates the embedded grammar set.
|
Command gen-grammars deterministically generates the embedded grammar set. |
|
Package oniguruma adapts the Oniguruma subset used by TextMate grammars to regexp2.
|
Package oniguruma adapts the Oniguruma subset used by TextMate grammars to regexp2. |