-
-
Notifications
You must be signed in to change notification settings - Fork 791
feat(html): support for svelte #each
#8493
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
🦋 Changeset detectedLatest commit: b22f665 The changes in this PR will be included in the next version bump. This PR includes changesets to release 13 packages
Not sure what this means? Click here to learn what changesets are. Click here if you're a maintainer who wants to add another changeset to this PR |
Parser conformance results onjs/262
jsx/babel
symbols/microsoft
ts/babel
ts/microsoft
|
WalkthroughAdds full Svelte { Possibly related PRs
Suggested reviewers
Pre-merge checks and finishing touches❌ Failed checks (1 inconclusive)
✅ Passed checks (3 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 3
🧹 Nitpick comments (2)
crates/biome_html_formatter/src/html/auxiliary/text_expression.rs (1)
14-24: Consider usingtrim()instead oftrim_start().trim_end().The current chained approach allocates an intermediate string. Using
trim()directly is more efficient and achieves the same result.Apply this diff:
- let trimmed_text = token_text.trim_start().trim_end(); + let trimmed_text = token_text.trim();crates/biome_html_parser/src/syntax/svelte.rs (1)
304-307: Minor: Redundant bitwise OR assignment.
has_errors |= trueis equivalent tohas_errors = true. The bitwise OR is unnecessary here sincetrue | true == true.if result.is_none() { - has_errors |= true; + has_errors = true; p.bump_any(); }
| // ^^^^^^^^^^^^^^^^^ | ||
| VueDirective = | ||
| name: 'vue_ident' | ||
| name: 'ident' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
any particular reason for this change? I was planning to intentionally differentiate between an ident and a vue ident at the lexer level because all vue directives start with v-. Then, the parser logic for knowing the start of a vue directive is pretty easy. (maybe vue ident isn't the ideal name for this case)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Because striking the difference doesn't really make a difference once the CST is constructed. The only difference it makes is during parsing, which we already do. After we understood that - for example - as or v-each are identifiers, we just need to emit a token.
Unless there's some future plan you have in mind, maintaining SVELTE_IDENT/VUE_IDENT might just cause confusion, and a waste of characters. Plus, JavaScript <> TypeScript are treated the same for example, where IDENT is used regardless of the dialect.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The only difference from other languages is that this method returns Option, because an identifier is such only in one dialect, while in another it's not.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
♻️ Duplicate comments (1)
xtask/codegen/html.ungram (1)
397-397: Existing concern about identifier consolidation.The change from
vue_identtoidenthas been previously flagged by dyc3, who noted that Vue directives start withv-and having a distinct token simplifies parser logic. This consolidation may increase parser complexity.
🧹 Nitpick comments (3)
xtask/codegen/html.ungram (1)
374-374: Misleading comment.The comment states "Keep it different just for svelte", but
SvelteNamenow uses the genericidentterminal rather than a Svelte-specific token. Either update the comment to reflect the consolidation, or reconsider whether the comment's intent is still relevant.crates/biome_html_parser/src/lexer/mod.rs (1)
527-567: LGTM — consider documenting the keyword set.The function correctly identifies language keywords and resets lexer position when no match is found. Per coding guidelines, adding a brief rustdoc comment listing the recognised keywords would improve discoverability.
🔎 Optional documentation improvement
+ /// Attempts to consume an HTML-ish language identifier keyword. + /// + /// Recognised keywords: `debug`, `attach`, `const`, `render`, `html`, `key`, `if`, `else`, `each`, `as`. + /// + /// If the current position matches a known keyword, returns `Some(HtmlSyntaxKind)`. + /// Otherwise, restores the lexer position and returns `None`. fn consume_language_identifier(&mut self, first: u8) -> Option<HtmlSyntaxKind> {crates/biome_html_parser/src/token_source.rs (1)
85-93: Documentation forStopAtOpeningParenOrCommais incomplete.The doc comment states "Stops at
(" but the variant name suggests it also stops at,. Consider updating the documentation for clarity.🔎 Suggested fix
#[derive(Debug, Clone, Copy, PartialEq, Eq)] pub(crate) enum RestrictedExpressionKind { /// Stops at 'as' keyword or ',' (for Svelte #each blocks) StopAtAsOrComma, - /// Stops at `(` + /// Stops at `(` or `,` StopAtOpeningParenOrComma, /// Stops at `)` StopAtClosingParen, }
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
⛔ Files ignored due to path filters (11)
crates/biome_html_factory/src/generated/node_factory.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_html_factory/src/generated/syntax_factory.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_html_formatter/tests/specs/html/interpolation/interpolation.html.snapis excluded by!**/*.snapand included by**crates/biome_html_formatter/tests/specs/html/svelte/each_with_whitespace.svelte.snapis excluded by!**/*.snapand included by**crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.svelte.snapis excluded by!**/*.snapand included by**crates/biome_html_parser/tests/html_specs/ok/svelte/each_complex_combinations.svelte.snapis excluded by!**/*.snapand included by**crates/biome_html_parser/tests/html_specs/ok/svelte/each_with_index_and_key.svelte.snapis excluded by!**/*.snapand included by**crates/biome_html_parser/tests/html_specs/ok/svelte/each_with_key.svelte.snapis excluded by!**/*.snapand included by**crates/biome_html_syntax/src/generated/kind.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_html_syntax/src/generated/nodes.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_html_syntax/src/generated/nodes_mut.rsis excluded by!**/generated/**,!**/generated/**and included by**
📒 Files selected for processing (13)
.changeset/green-clubs-search.md(1 hunks)crates/biome_html_formatter/src/html/auxiliary/double_text_expression.rs(1 hunks)crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs(1 hunks)crates/biome_html_formatter/src/svelte/auxiliary/each_key.rs(1 hunks)crates/biome_html_formatter/tests/specs/html/interpolation/interpolation.html(1 hunks)crates/biome_html_formatter/tests/specs/html/interpolation/options.json(1 hunks)crates/biome_html_parser/src/lexer/mod.rs(11 hunks)crates/biome_html_parser/src/syntax/svelte.rs(6 hunks)crates/biome_html_parser/src/token_source.rs(5 hunks)crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.svelte(1 hunks)crates/biome_html_parser/tests/quick_test.rs(1 hunks)xtask/codegen/html.ungram(3 hunks)xtask/codegen/src/html_kinds_src.rs(2 hunks)
✅ Files skipped from review due to trivial changes (3)
- crates/biome_html_formatter/src/html/auxiliary/double_text_expression.rs
- crates/biome_html_formatter/tests/specs/html/interpolation/interpolation.html
- .changeset/green-clubs-search.md
🚧 Files skipped from review as they are similar to previous changes (2)
- crates/biome_html_formatter/src/svelte/auxiliary/each_key.rs
- crates/biome_html_parser/src/syntax/svelte.rs
🧰 Additional context used
📓 Path-based instructions (1)
crates/**/*.rs
📄 CodeRabbit inference engine (CONTRIBUTING.md)
Update inline rustdoc documentation for rules, assists, and their options when adding new features or changing existing features in Rust crates
Files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rscrates/biome_html_parser/tests/quick_test.rscrates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
🧠 Learnings (45)
📚 Learning: 2025-12-04T13:29:49.287Z
Learnt from: dyc3
Repo: biomejs/biome PR: 8291
File: crates/biome_html_formatter/tests/specs/prettier/vue/html-vue/elastic-header.html:10-10
Timestamp: 2025-12-04T13:29:49.287Z
Learning: Files under `crates/biome_html_formatter/tests/specs/prettier` are test fixtures synced from Prettier and should not receive detailed code quality reviews (e.g., HTTP vs HTTPS, formatting suggestions, etc.). These files are test data meant to validate formatter behavior and should be preserved as-is.
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.sveltecrates/biome_html_parser/tests/quick_test.rscrates/biome_html_formatter/tests/specs/html/interpolation/options.json
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Applies to crates/biome_formatter/**/biome_*_formatter/tests/spec_tests.rs : Use the `tests_macros::gen_tests!` macro in `spec_tests.rs` to generate test functions for each specification file matching the pattern `tests/specs/<language>/**/*.<ext>`
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.sveltecrates/biome_html_parser/tests/quick_test.rscrates/biome_html_formatter/tests/specs/html/interpolation/options.json
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Use language tags in documentation code blocks (js, ts, tsx, json, css) and order properties consistently as: language, then `expect_diagnostic`, then options modifiers, then `ignore`, then `file=path`
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.sveltecrates/biome_html_parser/tests/quick_test.rscrates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/*.ungram : Nodes for enclosing syntax errors must have the `Bogus` word, e.g., `HtmlBogusAttribute`, and must be part of a variant
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.sveltecrates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : In rule documentation code blocks, mark invalid examples with the `expect_diagnostic` property and valid examples without it; each invalid example must emit exactly one diagnostic
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.sveltecrates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/tests/specs/**/*.{js,ts,tsx,jsx,json,css} : Test rules using snapshot tests via the `insta` library with test cases in `tests/specs/<group>/<rule_name>/` directories prefixed by `invalid` or `valid`
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.svelte
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/language_kind.rs : Add a new variant to `LanguageKind` enum in `language_kind.rs` file and implement all methods for the new language variant
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.sveltecrates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/tests/specs/**/*.jsonc : Use `.jsonc` files in test specs with code snippets as array of strings to test rules in script environment (no import/export syntax)
Applied to files:
crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.sveltecrates/biome_html_formatter/tests/specs/html/interpolation/options.json
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : Import the `FormatNode` trait and implement it for your Node when creating formatters in biome_js_formatter
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : When formatting AST nodes, use mandatory tokens from the AST instead of hardcoding token strings (e.g., use `node.l_paren_token().format()` instead of `token("(")`)
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rsxtask/codegen/src/html_kinds_src.rscrates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Applies to crates/biome_formatter/**/biome_*_formatter/src/lib.rs : Expose a public `format_node` function that accepts formatting options and a root syntax node, returning a `FormatResult<Formatted<Context>>` with appropriate documentation
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Implement the `FormatNodeRule<N>` trait with `fmt_fields` as the only required method; default implementations of `fmt`, `is_suppressed`, `fmt_leading_comments`, `fmt_dangling_comments`, and `fmt_trailing_comments` are provided
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Define `FormatHtmlSyntaxNode` struct in a `cst.rs` file implementing `FormatRule<HtmlSyntaxNode>`, `AsFormat<HtmlFormatContext>`, and `IntoFormat<HtmlFormatContext>` traits using the provided boilerplate code
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rscrates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Applies to crates/biome_formatter/**/biome_*_formatter/src/context.rs : Define `<Language>FormatContext` struct in a `context.rs` file containing `comments` and `source_map` fields, implementing `FormatContext` and `CstFormatContext` traits
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rscrates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : Do not attempt to 'fix' the code; if a token/node is known to be mandatory but is missing, return `None` instead
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs
📚 Learning: 2025-12-12T10:11:05.564Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-12T10:11:05.564Z
Learning: Applies to crates/**/*.rs : Update inline rustdoc documentation for rules, assists, and their options when adding new features or changing existing features in Rust crates
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rscrates/biome_html_parser/tests/quick_test.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/src/**/*.rs : Wrap optional rule option fields in `Option<_>` to properly track set vs unset options during configuration merging
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rscrates/biome_html_formatter/tests/specs/html/interpolation/options.json
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : For tokens that are not mandatory, use helper functions instead of hardcoding
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rscrates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: The formatter foundation relies on using the generic `Format` trait and `FormatNode` for nodes, with creation of an intermediate IR via a series of helpers
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/src/**/*.rs : Rule options struct fields should use `#[serde(rename_all = "camelCase")]`, `#[serde(deny_unknown_fields)]`, and `#[serde(default)]` attributes for proper JSON serialization
Applied to files:
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Implement a token source struct that wraps the lexer and implements `TokenSourceWithBufferedLexer` and `LexerWithCheckpoint` for lookahead and re-lexing capabilities
Applied to files:
xtask/codegen/src/html_kinds_src.rscrates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Use `p.eat(token)` for optional tokens, `p.expect(token)` for required tokens, `parse_rule(p).ok(p)` for optional nodes, and `parse_rule(p).or_add_diagnostic(p, error)` for required nodes
Applied to files:
xtask/codegen/src/html_kinds_src.rscrates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Use quick testing via `tests/quick_test.rs` by removing the `#[ignore]` macro and modifying the `SOURCE` variable to rapidly validate rule behavior during development
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Applies to crates/biome_formatter/**/biome_*_formatter/tests/language.rs : Implement `TestFormatLanguage` trait in `tests/language.rs` for the formatter's test language
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-24T18:06:12.048Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_service/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:12.048Z
Learning: Applies to crates/biome_service/src/workspace/watcher.tests.rs : Implement watcher tests for workspace methods in watcher.tests.rs and end-to-end tests in LSP tests
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-24T18:05:42.356Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:42.356Z
Learning: Applies to crates/biome_js_type_info/**/*.rs : Store type data in linear vectors instead of using recursive data structures with `Arc` for improved data locality and performance
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Applies to crates/biome_formatter/**/biome_*_formatter/Cargo.toml : Include development dependencies in `Cargo.toml` for formatter tests: `biome_formatter_test`, `biome_<language>_factory`, `biome_<language>_parser`, `biome_parser`, `biome_service`, `countme`, `iai`, `quickcheck`, `quickcheck_macros`, and `tests_macros`
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-24T18:05:42.356Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:42.356Z
Learning: Applies to crates/biome_js_type_info/**/*.rs : Use `TypeReference` instead of `Arc` for types that reference other types to avoid stale cache issues when modules are replaced
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/src/**/*.rs : Use `Box<[T]>` instead of `Vec<T>` for rule options array fields to save memory (boxed slices and boxed str use 2 words instead of three words)
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Avoid using `unwrap()` or `expect()` on `Result` and `Option` types; instead use helper functions like `map`, `filter`, `and_then` to maintain code clarity and avoid panics
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Document rules with a one-line brief description in the first paragraph of the doc comment, followed by detailed paragraphs, `## Examples` section with `### Invalid` and `### Valid` subsections, and optional `## Options` section
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Framework-specific rules should be named using the `use` or `no` prefix followed by the framework name (e.g., `noVueReservedProps`)
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Use the `useShorthand` prefix for rules that report syntax rewritable using equivalent compact syntax (e.g., `useShorthandAssign`)
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Use the `noEmpty` prefix for rules that report empty code (e.g., `noEmptyBlockStatements`)
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Implement custom `Queryable` types and `Visitor` traits for rules requiring deep AST inspection to avoid redundant traversal passes
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : For rules ported from other ecosystems like ESLint or Clippy, add a `sources` field with `RuleSource` metadata using `.same()` for identical behavior or `.inspired()` for different behavior
Applied to files:
crates/biome_html_parser/tests/quick_test.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/lexer/mod.rs : Implement a `Lexer` trait from `biome_parser` crate for the lexer struct that consumes characters from source code and emits tokens
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-09T12:47:46.298Z
Learnt from: ematipico
Repo: biomejs/biome PR: 8031
File: crates/biome_html_parser/src/syntax/svelte.rs:140-147
Timestamp: 2025-11-09T12:47:46.298Z
Learning: In the Biome HTML parser, `expect` and `expect_with_context` consume the current token and then lex the next token. The context parameter in `expect_with_context` controls how the next token (after the consumed one) is lexed, not the current token being consumed. For example, in Svelte parsing, after `bump_with_context(T!["{:"], HtmlLexContext::Svelte)`, the next token is already lexed in the Svelte context, so `expect(T![else])` is sufficient unless the token after `else` also needs to be lexed in a specific context.
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Use `ConditionalParsedSyntax` for syntax that is only valid in specific contexts (e.g., strict mode, file types, language versions) and call `or_invalid_to_bogus()` to convert to a bogus node if not supported
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:05:42.356Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:42.356Z
Learning: Applies to crates/biome_js_type_info/**/*.rs : Distinguish between `TypeData::Unknown` and `TypeData::UnknownKeyword` to measure inference effectiveness versus explicit user-provided unknown types
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/language_kind.rs : Add a new language prefix to the `LANGUAGE_PREFIXES` constant in `language_kind.rs` file
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : A parser struct must implement the `Parser` trait and save the token source, parser context, and optional parser options
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Applies to crates/biome_formatter/**/biome_*_formatter/tests/specs/**/options.json : Create an `options.json` file (formatted as `biome.json`) in test specification folders to apply non-default formatting options to all test files in that folder
Applied to files:
crates/biome_html_formatter/tests/specs/html/interpolation/options.json
📚 Learning: 2025-08-05T14:43:29.581Z
Learnt from: dyc3
Repo: biomejs/biome PR: 7081
File: packages/@biomejs/biome/configuration_schema.json:7765-7781
Timestamp: 2025-08-05T14:43:29.581Z
Learning: The file `packages/biomejs/biome/configuration_schema.json` is auto-generated and should not be manually edited or reviewed for schema issues; any changes should be made at the code generation source.
Applied to files:
crates/biome_html_formatter/tests/specs/html/interpolation/options.json
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Use the `noRestricted` prefix for rules that report user-banned entities (e.g., `noRestrictedGlobals`)
Applied to files:
crates/biome_html_parser/src/token_source.rs
🧬 Code graph analysis (2)
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs (8)
crates/biome_html_formatter/src/svelte/auxiliary/each_block.rs (1)
fmt_fields(7-22)crates/biome_html_formatter/src/svelte/auxiliary/each_keyed_item.rs (1)
fmt_fields(7-15)crates/biome_html_formatter/src/svelte/auxiliary/each_index.rs (1)
fmt_fields(7-11)crates/biome_html_formatter/src/svelte/auxiliary/each_opening_block.rs (1)
fmt_fields(7-27)crates/biome_html_formatter/src/svelte/auxiliary/else_if_clause.rs (1)
fmt_fields(9-39)crates/biome_html_formatter/src/svelte/auxiliary/if_opening_block.rs (1)
fmt_fields(9-36)crates/biome_formatter/src/builders.rs (1)
space(606-608)crates/biome_html_formatter/src/generated.rs (16)
format(28-33)format(66-71)format(104-109)format(142-144)format(174-179)format(212-217)format(250-255)format(288-293)format(326-331)format(364-370)format(404-409)format(442-447)format(480-485)format(512-517)format(550-555)format(588-594)
crates/biome_html_parser/src/lexer/mod.rs (1)
crates/biome_html_parser/src/token_source.rs (1)
current(195-197)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (10)
- GitHub Check: Check Dependencies
- GitHub Check: Test (depot-windows-2022-16)
- GitHub Check: autofix
- GitHub Check: Documentation
- GitHub Check: Test Node.js API
- GitHub Check: Parser conformance
- GitHub Check: Test (depot-ubuntu-24.04-arm-16)
- GitHub Check: Lint project (depot-ubuntu-24.04-arm-16)
- GitHub Check: End-to-end tests
- GitHub Check: Lint project (depot-windows-2022)
🔇 Additional comments (18)
crates/biome_html_formatter/tests/specs/html/interpolation/options.json (1)
1-11: LGTM!The test configuration correctly enables interpolation parsing and formatting for the new Svelte
#eachblock feature. The schema reference and settings are appropriate.xtask/codegen/html.ungram (2)
202-203: LGTM!The addition of
SvelteEachBlockto the union follows the existing pattern for Svelte block types.
316-371: LGTM!The grammar comprehensively covers Svelte
#eachblock syntax, including keyed iteration, optional index and key bindings, and else clauses. The structure follows the established pattern fromSvelteIfBlock.xtask/codegen/src/html_kinds_src.rs (4)
29-30: LGTM!Parentheses tokens are necessary for the Svelte
#eachkey syntax:(key).
33-34: LGTM!Adding
asandeachkeywords is necessary for Svelte#eachblock support.
37-37: LGTM!The consolidation of identifier tokens (
HTML_IDENT,SVELTE_IDENT,VUE_IDENT→IDENT) aligns with the grammar changes and simplifies the lexer.
80-86: LGTM!The new Svelte each-related nodes match the grammar definitions and follow the established naming conventions.
crates/biome_html_formatter/src/svelte/auxiliary/each_as_keyed_item.rs (2)
1-5: LGTM!The imports and struct definition follow the standard formatter boilerplate pattern.
6-27: LGTM!The formatter implementation correctly handles the
as name [, index] [(key)]syntax. The spacing and conditional formatting of optionalindexandkeyfields follow established patterns from similar formatters.crates/biome_html_parser/tests/quick_test.rs (1)
7-14: LGTM!The test case covers a comprehensive Svelte
{#each}block with item binding, index, and keyed iteration. Note that the test useswith_vue()options—if this is intentional for cross-compatibility testing, all good; otherwise, consider adding awith_svelte()option if one becomes available.crates/biome_html_parser/tests/html_specs/error/svelte/each_missing_closing_paren.svelte (1)
1-2: LGTM!A well-crafted error case fixture that exercises parser error recovery for unclosed key expressions in Svelte
{#each}blocks.crates/biome_html_parser/src/lexer/mod.rs (5)
485-499: LGTM!Clean implementation for consuming Svelte identifiers.
469-483: LGTM!Good addition of parenthesis handling for keyed iteration and consistent identifier consumption pattern.
95-97: LGTM!The fallback to
consume_unexpected_characteris appropriate for the inside-tag context where unknown identifiers should be flagged.
1086-1088: LGTM!Proper integration of the restricted expression context into the main lexer dispatch.
1213-1220: LGTM!Solid refactoring—generalising identifier checks makes the lexer more maintainable as template language support expands.
crates/biome_html_parser/src/token_source.rs (2)
47-48: LGTM!Clean addition of the restricted expression context with a convenient constructor.
Also applies to: 70-73
118-123: LGTM!The
HtmlTextvariant name is more descriptive than the previous naming, and the doc comment helpfully points to the implementing function.
|
I improved the parsing since last time. The AI botched some parts of the syntax, so now I improved |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
🧹 Nitpick comments (4)
crates/biome_html_parser/src/syntax/svelte.rs (2)
221-243: Consider adding a brief rustdoc comment forparse_each_key.The function parses the
(key)part of the#eachblock but lacks inline documentation. As per the coding guidelines for Rust crates, updating rustdoc for new features is recommended.🔎 Suggested addition
+/// Parses the key expression `(key)` inside a Svelte `#each` block. +/// +/// Example: `{#each items as item (item.id)}` fn parse_each_key(p: &mut HtmlParser) -> ParsedSyntax {
279-292: Error emitted when neitherasnor,is present—verify this is the desired UX.The error message assumes the user intended one of these two syntaxes, but if the expression itself is malformed, this might be confusing. The recovery is reasonable, but users might benefit from a more contextual message when the expression parsing already failed upstream.
crates/biome_html_parser/src/lexer/mod.rs (2)
377-398: Keyword lookahead within restricted expressions is clever but has a subtlety.When
consume_language_identifierreturnsNone(not a keyword), the position is already reset internally (line 563), soadvance_byte_or_charon line 396 is correct. However, the comment on line 395 says "position was reset by consume_language_identifier" which is accurate but might be clearer if it noted this is the non-keyword path.🔎 Slightly clearer comment
} else { - // Not a keyword, advance one byte (position was reset by consume_language_identifier) + // Not a keyword; consume_language_identifier already reset position, so advance manually self.advance_byte_or_char(current); }
527-567: Genericconsume_language_identifieris a good refactor.Unifying keyword detection into a single function with a fixed-size buffer and rewind-on-no-match is clean. The keyword list covers the Svelte needs (
as,each, etc.).One thought: the buffer size of 14 bytes is sufficient for current keywords (longest is "attach" at 6), but if longer keywords are added in future, this could silently fail to match. A compile-time assertion or comment noting the max keyword length would be defensive.
🔎 Optional defensive comment
fn consume_language_identifier(&mut self, first: u8) -> Option<HtmlSyntaxKind> { self.assert_current_char_boundary(); let starting_position = self.position; + // Buffer sized for longest keyword; update if adding keywords longer than 14 chars const BUFFER_SIZE: usize = 14;
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (3)
crates/biome_html_parser/src/lexer/mod.rs(11 hunks)crates/biome_html_parser/src/syntax/svelte.rs(6 hunks)crates/biome_html_parser/src/token_source.rs(5 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
crates/**/*.rs
📄 CodeRabbit inference engine (CONTRIBUTING.md)
Update inline rustdoc documentation for rules, assists, and their options when adding new features or changing existing features in Rust crates
Files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
🧠 Learnings (23)
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Implement a token source struct that wraps the lexer and implements `TokenSourceWithBufferedLexer` and `LexerWithCheckpoint` for lookahead and re-lexing capabilities
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/lexer/mod.rs : Implement a `Lexer` trait from `biome_parser` crate for the lexer struct that consumes characters from source code and emits tokens
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/language_kind.rs : Add a new variant to `LanguageKind` enum in `language_kind.rs` file and implement all methods for the new language variant
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-27T23:04:02.022Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-11-27T23:04:02.022Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Use language tags in documentation code blocks (js, ts, tsx, json, css) and order properties consistently as: language, then `expect_diagnostic`, then options modifiers, then `ignore`, then `file=path`
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : When formatting AST nodes, use mandatory tokens from the AST instead of hardcoding token strings (e.g., use `node.l_paren_token().format()` instead of `token("(")`)
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/language_kind.rs : Add a new language prefix to the `LANGUAGE_PREFIXES` constant in `language_kind.rs` file
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-09T12:47:46.298Z
Learnt from: ematipico
Repo: biomejs/biome PR: 8031
File: crates/biome_html_parser/src/syntax/svelte.rs:140-147
Timestamp: 2025-11-09T12:47:46.298Z
Learning: In the Biome HTML parser, `expect` and `expect_with_context` consume the current token and then lex the next token. The context parameter in `expect_with_context` controls how the next token (after the consumed one) is lexed, not the current token being consumed. For example, in Svelte parsing, after `bump_with_context(T!["{:"], HtmlLexContext::Svelte)`, the next token is already lexed in the Svelte context, so `expect(T![else])` is sufficient unless the token after `else` also needs to be lexed in a specific context.
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Use `p.eat(token)` for optional tokens, `p.expect(token)` for required tokens, `parse_rule(p).ok(p)` for optional nodes, and `parse_rule(p).or_add_diagnostic(p, error)` for required nodes
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Use `ConditionalParsedSyntax` for syntax that is only valid in specific contexts (e.g., strict mode, file types, language versions) and call `or_invalid_to_bogus()` to convert to a bogus node if not supported
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:05:42.356Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:42.356Z
Learning: Applies to crates/biome_js_type_info/**/*.rs : Distinguish between `TypeData::Unknown` and `TypeData::UnknownKeyword` to measure inference effectiveness versus explicit user-provided unknown types
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Implement error recovery in list parsing using `or_recover()` to wrap unparseable tokens in a `BOGUS_*` node and consume tokens until a recovery token is found
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : Do not attempt to 'fix' the code; if a token/node is known to be mandatory but is missing, return `None` instead
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-10-25T07:22:18.540Z
Learnt from: ematipico
Repo: biomejs/biome PR: 7852
File: crates/biome_css_parser/src/syntax/property/mod.rs:161-168
Timestamp: 2025-10-25T07:22:18.540Z
Learning: In the Biome CSS parser, lexer token emission should not be gated behind parser options like `is_tailwind_directives_enabled()`. The lexer must emit correct tokens regardless of parser options to enable accurate diagnostics and error messages when the syntax is used incorrectly.
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Parse rules must return `ParsedSyntax::Absent` if the rule can't predict by the next token(s) if they form the expected node, and must not progress the parser in this case
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/*.ungram : Nodes for enclosing syntax errors must have the `Bogus` word, e.g., `HtmlBogusAttribute`, and must be part of a variant
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : A parser struct must implement the `Parser` trait and save the token source, parser context, and optional parser options
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:05:27.810Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:27.810Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : For tokens that are not mandatory, use helper functions instead of hardcoding
Applied to files:
crates/biome_html_parser/src/lexer/mod.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Define `FormatHtmlSyntaxNode` struct in a `cst.rs` file implementing `FormatRule<HtmlSyntaxNode>`, `AsFormat<HtmlFormatContext>`, and `IntoFormat<HtmlFormatContext>` traits using the provided boilerplate code
Applied to files:
crates/biome_html_parser/src/lexer/mod.rscrates/biome_html_parser/src/token_source.rscrates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:05:20.371Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:05:20.371Z
Learning: Applies to crates/biome_formatter/**/biome_*_formatter/src/context.rs : Define `<Language>FormatContext` struct in a `context.rs` file containing `comments` and `source_map` fields, implementing `FormatContext` and `CstFormatContext` traits
Applied to files:
crates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-12-12T10:11:05.564Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-12T10:11:05.564Z
Learning: Applies to crates/**/*.rs : Update inline rustdoc documentation for rules, assists, and their options when adding new features or changing existing features in Rust crates
Applied to files:
crates/biome_html_parser/src/token_source.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Use `ParseSeparatedList` and `ParseNodeList` for parsing lists with error recovery to avoid infinite loops
Applied to files:
crates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Parse rules must take a mutable reference to the parser as their only parameter and return a `ParsedSyntax`
Applied to files:
crates/biome_html_parser/src/syntax/svelte.rs
📚 Learning: 2025-11-24T18:06:03.545Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_parser/CONTRIBUTING.md:0-0
Timestamp: 2025-11-24T18:06:03.545Z
Learning: Applies to crates/biome_parser/**/src/**/*.rs : Parse rule functions must be prefixed with `parse_` and use the name defined in the grammar file, e.g., `parse_for_statement` or `parse_expression`
Applied to files:
crates/biome_html_parser/src/syntax/svelte.rs
🧬 Code graph analysis (1)
crates/biome_html_parser/src/syntax/svelte.rs (3)
crates/biome_html_parser/src/token_source.rs (1)
restricted_expression(71-73)crates/biome_html_parser/src/syntax/parse_error.rs (1)
expected_svelte_closing_block(104-106)crates/biome_html_parser/src/syntax/mod.rs (1)
parse_single_text_expression_content(639-648)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
- GitHub Check: Test Node.js API
- GitHub Check: autofix
- GitHub Check: Parser conformance
🔇 Additional comments (16)
crates/biome_html_parser/src/syntax/svelte.rs (7)
154-182: LGTM! Clean structure for the each block parser.The
parse_each_blockfunction follows the established pattern fromparse_if_blockandparse_key_block. The bogus node emission whenhas_errorsis set is a sensible approach for error recovery.
184-219: Well-structured keyed item parsing with appropriate context switching.The use of
RestrictedExpressionStopAt::OpeningParenOrCommaand re-lexing viaHtmlReLexContext::Sveltecorrectly handles the complex tokenisation needs foras item, index (key)syntax.
294-335: Solid implementation with good error tracking.The
has_errorsflag propagation and the recovery viap.bump_any()on line 319 are sensible. The pattern of returning a tuple(ParsedSyntax, bool)is a pragmatic approach for signalling downstream bogus node emission.
584-591: Updatedis_at_list_endlogic is cleaner with direct lookahead.The condition
p.at(T!["{:"]) && p.nth_at(1, T![else]) && !p.nth_at(2, T![if])correctly identifies a standalone{:else}block without consuming tokens. This is a nice improvement over the previous checkpoint-based approach.
609-626: New helpers are concise and well-placed.Both
is_at_svelte_keywordandat_else_opening_blockare appropriately scoped and follow existing patterns. The keyword set inis_at_svelte_keywordaligns with the Svelte specification.
245-258: The wrapper node is required by the grammar.SvelteEachKeyedItemis defined inxtask/codegen/html.ungramas a distinct rule wrappingSvelteEachIndex, so the function's implementation is correct.Likely an incorrect or invalid review comment.
517-522: Formatter already handles IDENT tokens correctly within SvelteNameFields.The formatter in
crates/biome_html_formatter/src/svelte/auxiliary/name.rsextractsident_tokenfromSvelteNameFieldsand delegates to its.format()method without checking token kind. No downstream formatter changes are needed—this implementation already works with the IDENT token.crates/biome_html_parser/src/token_source.rs (4)
19-60: Well-structured context enum extension.The addition of
RestrictedSingleExpression(RestrictedExpressionStopAt)follows the established pattern of theTextExpression(TextExpressionKind)variant. The derive adjustments (removingPartialOrd,Ord) are sensible since ordering isn't semantically meaningful for lex contexts.
70-74: Consistent constructor pattern.
restricted_expressionmirrorssingle_expressionanddouble_expressionnicely.
85-93: Clear enum for stop conditions.The
RestrictedExpressionStopAtvariants are self-documenting. The doc comments succinctly explain each stop condition.
118-123:HtmlTextre-lex context is aptly named.The docstring clarifies the re-lex behaviour. This is a clean addition.
crates/biome_html_parser/src/lexer/mod.rs (5)
339-410: Solid implementation of restricted expression lexing with proper nesting.The bracket stack tracking and keyword-aware stopping logic is well thought out. The fix to return
ERROR_TOKENinstead ofEOFwhen nothing is consumed (lines 405-409) addresses the previous review concern correctly.One minor observation: the
checkpoint_possave/restore pattern for rewinding when hitting a stop keyword is effective but could benefit from a brief inline comment explaining the rewind rationale.
469-499: Svelte context lexing updated cleanly.The addition of
(and)tokens (lines 474-475) and the fallback toconsume_svelte_identifier(line 480) integrate well with the new each-block parsing. Theconsume_svelte_identifierfunction correctly producesIDENTtokens for non-keyword identifiers.
1086-1088: Integration point for restricted expressions innext_token.The match arm correctly delegates to
consume_restricted_single_text_expression. This is the expected integration pattern.
1169-1169: Re-lex context forHtmlTextcorrectly wired.Maps to
consume_html_textas documented in the token source. Consistent with the design.
1213-1220: Function renames fromis_at_svelte_*to genericis_at_*_identifierare sensible.These are now used for broader language identifier detection, not just Svelte. The rename reflects the generalisation.
| // In case there's nothing parsed, it's possible we have whitespaces or noice. | ||
| // We consume any possible token, so we can recover and resume normal parsing. | ||
| if result.is_none() { | ||
| has_errors |= true; | ||
| p.bump_any(); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Typo in comment: "noice" should be "noise".
Minor textual fix.
🔎 Fix
- // In case there's nothing parsed, it's possible we have whitespaces or noice.
+ // In case there's nothing parsed, it's possible we have whitespaces or noise.🤖 Prompt for AI Agents
In crates/biome_html_parser/src/syntax/svelte.rs around lines 315 to 320, the
comment contains a typo: change "noice" to "noise" so the comment reads "we have
whitespaces or noise." Make only this textual correction in the comment; do not
alter code logic.
dyc3
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nice work! I like the improvements to the lexer too
|
Thank you @ematipico !! :) |
Summary
Closes #8020
This one took a while! I had to get creating with the parsing of keyword when parsing expressions.
The PR was partially implemented with AI, this is where I asked help:
Where I implemented the PR:
In this PR I also changed how identifiers are parsed. Up until now, we were using different tokens for svelte and vue, which is not needed. Everything is now an
IDENT.Test Plan
CI should stay green
Docs
Not needed, since we're still under experimental