Replies: 1 comment
-
|
Thank you for the detailed proposal, I haven't started research yet, but I like most of the above ideas. Thank you @jg-rp . |
Beta Was this translation helpful? Give feedback.
0 replies
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
Looking at your v11 project, I see that you've mentioned splitting tokenization and parsing phases, and an improved operator interface. So here is an overview of my personal preferences for a typical, single-pass lexer/parser architecture, with plain old tokens and distinct syntax tree nodes.
Even if you have a different approach in mind or you prefer to keep things closer to how they are, I hope this provides some inspiration and/or ideas.
Tokens are plain objects containing just three numbers.
With a helper function to get a token's value.
A lexer is responsible for building a flat token array. It scans markup and expressions in one pass. (I have a Shopify/liquid compatible implementation if you're interested.)
A parser transforms a token array into a syntax tree.
A syntax tree is composed of plain text, tags/output and expressions.
A tag is anything that creates a
Markupnode given a stream of tokens.Tagwould usually be implemented as a static method of a class implementingMarkup. For example:TokenStreamwould have methods likeparseBlock(end?: Set<string>): BlockandparseExpression(precedence?: number): Expression, whereparseExpressionimplements a typical recursive descent parser instead of converting to postfix notation.All literals and operators are classes implementing
Expression. For example:A template is simply an array of nodes that calls
Markup.renderfor each node.Notice that the
Liquidenvironment object is both the high-level API and central configuration object. We pass it around rather than deriving a distinct options object from it (I like the idea of configuration through extension here). Similarly, render-time configuration is aRenderContextobject. It has a reference to the environment object because the environment is conceptually part of the render context.Beta Was this translation helpful? Give feedback.
All reactions