feat: markdown linter - #11253
Conversation
|
✅ Organic activityNo automation signals detected in the analyzed events. This is an automated analysis by AgentScan |
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Run ID: ⛔ Files ignored due to path filters (2)
📒 Files selected for processing (1)
🚧 Files skipped from review as they are similar to previous changes (1)
WalkthroughThis change adds Markdown analysis, linting, suppression handling, code actions, fix-all support, rule registration, configuration, and tests. It adds the Possibly related PRs
Suggested reviewers: 🚥 Pre-merge checks | ✅ 4✅ Passed checks (4 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
Parser conformance results onjs/262
jsx/babel
markdown/commonmark
symbols/microsoft
ts/babel
ts/microsoft
|
Merging this PR will regress 1 benchmark
Warning Please fix the performance issues or acknowledge them on CodSpeed. Performance Changes
Tip Investigate this regression by commenting Comparing Footnotes
|
Merging this PR will not alter performance
Comparing Footnotes
|
There was a problem hiding this comment.
Actionable comments posted: 6
🧹 Nitpick comments (4)
crates/biome_service/src/file_handlers/md.rs (2)
430-450: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick winUse the destructured locals consistently.
Pass
path,language, andworkspace.as_ref()instead of accessing the originalparamsfields. Bindlanguagein the pattern. This matches the other handlers and removes unnecessary field access.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@crates/biome_service/src/file_handlers/md.rs` around lines 430 - 450, Update the analyzer setup around AnalyzerVisitorBuilder to destructure and bind language, then consistently pass the local path, language, and workspace.as_ref() values instead of accessing params fields. Preserve the existing rule and project configuration behavior.
511-522: 🚀 Performance & Scalability | 🔵 Trivial | ⚡ Quick winPass the analyser cache through
FixAllParams
WorkspaceServeralready owns the analyser cache, butfix_file_statedoes not pass it toFixAllParams. Add the field and use.with_cache(...)in analyser-backed fix-all handlers, including Markdown.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@crates/biome_service/src/file_handlers/md.rs` around lines 511 - 522, Add the analyser cache to FixAllParams and propagate WorkspaceServer’s owned cache into it via .with_cache(...) in every analyser-backed fix-all handler, including fix_file_state’s Markdown path around AnalyzerVisitorBuilder. Ensure the existing cache instance is reused rather than creating a new one.crates/biome_markdown_analyze/src/lib.rs (1)
170-179: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low valueUse
dbg!()for test debugging output.Replace these
eprintln!()calls withdbg!()or remove the ignored debugging test. The Rust testing guideline requiresdbg!()for debugging output.Proposed change
- eprintln!("{text}"); + dbg!(text); @@ - eprintln!("{new_code}"); + dbg!(new_code);As per coding guidelines, “Use the
dbg!()macro for debugging Rust code during testing”.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@crates/biome_markdown_analyze/src/lib.rs` around lines 170 - 179, Replace the two test-debugging `eprintln!` calls in the diagnostic and action-output loops with `dbg!` calls, or remove the ignored debugging test if this output is no longer needed. Preserve the existing diagnostic and mutation behavior.Source: Coding guidelines
crates/biome_markdown_analyze/tests/quick_test.rs (1)
11-53: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low valueReplace or remove this ignored test.
The test enables
suspicious/noDuplicateFontNamesagainst CSS text. It does not test the Markdown analyser ornursery/useConsistentHeaderLevel.If this test remains, enable the Markdown rule, use Markdown input, and assert its diagnostics. Remove the reviewer-directed comment and debug output when the test becomes automated.
As per coding guidelines, Rust changes need appropriate tests, use
dbg!()for test debugging, and comments must state a code purpose.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@crates/biome_markdown_analyze/tests/quick_test.rs` around lines 11 - 53, Replace or remove the ignored quick_test; if retained, configure the Markdown analyser with nursery/useConsistentHeaderLevel, provide Markdown heading input, and assert the expected diagnostics. Convert it into an automated test by removing the reviewer-directed comment and debug eprintln output, using dbg! only for temporary debugging, and asserting the collected error_ranges.Source: Coding guidelines
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In
`@crates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rs`:
- Around line 20-25: Correct the rustdoc example for the consistent-header-level
rule so the documented Markdown actually skips a heading level and produces the
expected diagnostic; update the second heading in the example while preserving
the existing expect_diagnostic annotation and example structure.
In `@crates/biome_markdown_analyze/src/suppression_action.rs`:
- Around line 60-78: Update the suppression comment construction in the token
replacement flow to use an HTML comment form (`<!-- ... -->`) instead of the
Markdown heading form, while retaining TriviaPieceKind::SingleLineComment. Add a
regression fixture covering inline suppression and verify the generated result
does not contain an MdHeader.
In `@crates/biome_markdown_parser/src/lexer/mod.rs`:
- Around line 1471-1489: Add regression cases to the tests covering the
is_in_atx_opening_sequence branch: verify a container-prefixed heading such as
“> ### heading” is recognized correctly, while non-heading text such as “text
### heading” is not. Extend the existing multiple_hashes coverage without
changing lexer behavior.
In `@crates/biome_service/src/configuration.rs`:
- Around line 971-979: Update ProjectScanComputer::compute to call
biome_markdown_analyze::visit_registry(&mut self) under the lang_md feature,
alongside the other language registry calls, so Markdown Project and Types rules
influence ScanKind. Add a regression test covering the Markdown scan requirement
path.
In `@crates/biome_service/src/file_handlers/md.rs`:
- Line 429: Update the debug_span! label in the Markdown handler to identify
Markdown processing instead of JSON, while preserving the existing range and
path fields.
In `@crates/biome_test_utils/src/lib.rs`:
- Around line 1006-1007: Update the exclusion comment above the file-type match
to explain that Markdown supports HTML comments, but the parser represents them
as MD_HTML_LITERAL rather than comment trivia; leave the exclusion list and
behavior unchanged.
---
Nitpick comments:
In `@crates/biome_markdown_analyze/src/lib.rs`:
- Around line 170-179: Replace the two test-debugging `eprintln!` calls in the
diagnostic and action-output loops with `dbg!` calls, or remove the ignored
debugging test if this output is no longer needed. Preserve the existing
diagnostic and mutation behavior.
In `@crates/biome_markdown_analyze/tests/quick_test.rs`:
- Around line 11-53: Replace or remove the ignored quick_test; if retained,
configure the Markdown analyser with nursery/useConsistentHeaderLevel, provide
Markdown heading input, and assert the expected diagnostics. Convert it into an
automated test by removing the reviewer-directed comment and debug eprintln
output, using dbg! only for temporary debugging, and asserting the collected
error_ranges.
In `@crates/biome_service/src/file_handlers/md.rs`:
- Around line 430-450: Update the analyzer setup around AnalyzerVisitorBuilder
to destructure and bind language, then consistently pass the local path,
language, and workspace.as_ref() values instead of accessing params fields.
Preserve the existing rule and project configuration behavior.
- Around line 511-522: Add the analyser cache to FixAllParams and propagate
WorkspaceServer’s owned cache into it via .with_cache(...) in every
analyser-backed fix-all handler, including fix_file_state’s Markdown path around
AnalyzerVisitorBuilder. Ensure the existing cache instance is reused rather than
creating a new one.
🪄 Autofix
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 42507852-60f2-406d-a69d-4b5d261a94a6
⛔ Files ignored due to path filters (174)
Cargo.lockis excluded by!**/*.lockand included by**crates/biome_diagnostics_categories/src/categories.rsis excluded by!**/categories.rsand included by**crates/biome_markdown_analyze/src/lint/nursery.rsis excluded by!**/nursery.rsand included by**crates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/headers_bad.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/headers_good.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/invalid.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/valid.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_factory/src/generated/node_factory.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_markdown_factory/src/generated/syntax_factory.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_markdown_parser/tests/md_test_suite/error/quote_nesting_too_deep.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/atx_heading_trailing_hash.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/autolinks.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/block_quote.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/block_quote_grouping.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/block_quote_ordered_list_interrupt.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/block_quote_ordered_sublist_after_list_item.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/block_quote_tab_separated.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/block_quote_thematic_break_after_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/blockquote_ends_at_unprefixed_ordered_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/blockquote_inside_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/blockquote_tab_indented_bullet.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/blockquote_tab_indented_bullet_siblings.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/blockquoted_fence_as_bullet_items.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bom.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bullet_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bullet_list_loose_after_empty_item.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bullet_list_space_tab_space.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bullet_list_split_after_empty_item_marker_change.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bullet_list_split_after_empty_item_paragraph.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bullet_list_tab_separated.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/bullet_to_ordered_split.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/edge_cases.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/emphasis_complex.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/emphasis_crossing.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/emphasis_edge_cases.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/emphasis_flanking.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/emphasis_link_text.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/emphasis_multibyte.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/entity_references.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fence_as_bullet_items.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_advanced.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_after_list_not_absorbed.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_block.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_blockquote_eof_after_prefix.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_document_indented_fences.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_empty_content.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_eof_after_fence.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_in_blockquote.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_indentation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/fenced_code_info_backtick.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/hard_break_in_blockquote.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/hard_break_in_list_item.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/hard_break_nested_quote_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/hard_line_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/hard_line_break_paragraph_split.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/header.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/header_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/html_block.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/html_block_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/html_block_in_list_continuation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/indent_code_block.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/indented_code_blank_lines.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/indented_code_in_list_vs_continuation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/inline_elements.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/inline_html.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/inline_html_edge_cases.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/inline_html_invalid.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/inline_link_destination_title.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/inline_link_whitespace.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/lazy_continuation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/lazy_continuation_at_marker_indent.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/lazy_continuation_emphasis_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_definition.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_definition_edge_cases.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_definition_indented_continuation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_definition_invalid.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_reference_before_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_reference_definition_paragraph_continuation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_reference_inside_quote_continuation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_reference_inside_quote_nested_quote_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/link_reference_then_quoted_ordered_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_blank_lines_between_items.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_continuation_edge_cases.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_in_blockquote.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_indentation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_interrupt_bullet.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_interrupt_empty_bullet.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_interrupt_ordered.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_item_tab_indented_fenced_code.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_lazy_link_reference_continuation.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_link_reference_before_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_link_reference_tab_non_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_link_reference_tab_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_marker_trailing_spaces.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_no_interrupt_empty_bullet.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_no_interrupt_ordered_2.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/list_tightness.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_bullet_markers_split.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_markers_after_fenced_code.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_markers_heading_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_markers_paragraph.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_markers_setext.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_markers_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_markers_three_after_heading_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/mixed_ordered_delimiters_split.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/multi_backtick_code.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/multibyte_emphasis_in_blockquote.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/multiline_label.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/multiline_label_reference.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/multiline_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/multiline_open_tag_blockquote_marker.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_bullet_indent_tokens.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_lazy_continuation_loose_item.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_lazy_continuation_same_marker_trailing.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_lazy_continuation_trailing_paragraph.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_blank_line_siblings.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_double_blank.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_double_blank_siblings.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_interrupt_after_newline.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_lazy_continuation_before_fence.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_lazy_continuation_before_link_reference.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_tab_indented_siblings.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_list_triple_blank_siblings.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/nested_quote.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_list_link_reference_tab_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_list_loose_after_empty_item.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_list_split_after_empty_item_delimiter_change.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_marker_non_one_in_bullet_item.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_marker_non_one_top_level.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_marker_one_starts_sublist_in_bullet.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_sublist_at_content_column.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_sublist_post_marker_wide_space.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_sublist_post_marker_wide_space_delimiter_cross.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/ordered_to_bullet_split.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/paragraph.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/paragraph_interruption.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/paren_depth_limit.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quote_link_reference_before_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quote_list_link_reference_before_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quote_list_link_reference_tab_non_thematic_break.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quote_pre_marker_indent.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quote_textual_marker_parity.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quoted_code_indented_bullet_stays_lazy.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quoted_ordered_marker_non_one_no_interrupt.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/quoted_space_indented_bullet_interrupts_paragraph.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/reference_link_not_implemented.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/reference_links.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/setext_heading.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/setext_heading_edge_cases.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/setext_heading_in_blockquote.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/setext_heading_inside_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/setext_heading_negative.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/single_item_lists_marker_split.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/sublist_loose_space_tab_indent.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/sublist_loose_three_space_tab_indent.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/sublist_loose_two_space_tab_indent.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/thematic_break_block.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/thematic_break_in_list.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/tilde_fence_info_backtick.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/too_many_hashes.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unclosed_bold.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unclosed_code_span.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unclosed_emphasis.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unclosed_image.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unclosed_link.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unclosed_reference_image_label.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unclosed_reference_link_label.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_parser/tests/md_test_suite/ok/unterminated_code_fence.md.snapis excluded by!**/*.snapand included by**crates/biome_markdown_syntax/src/generated/kind.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_markdown_syntax/src/generated/macros.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_markdown_syntax/src/generated/nodes.rsis excluded by!**/generated/**,!**/generated/**and included by**crates/biome_markdown_syntax/src/generated/nodes_mut.rsis excluded by!**/generated/**,!**/generated/**and included by**
📒 Files selected for processing (52)
Cargo.tomlcrates/biome_cli/Cargo.tomlcrates/biome_cli/src/reporter/sarif.rscrates/biome_configuration/Cargo.tomlcrates/biome_configuration/src/markdown.rscrates/biome_configuration_macros/Cargo.tomlcrates/biome_configuration_macros/src/lib.rscrates/biome_configuration_macros/src/visitors.rscrates/biome_markdown_analyze/Cargo.tomlcrates/biome_markdown_analyze/build.rscrates/biome_markdown_analyze/src/assist.rscrates/biome_markdown_analyze/src/lib.rscrates/biome_markdown_analyze/src/lint.rscrates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rscrates/biome_markdown_analyze/src/registry.rscrates/biome_markdown_analyze/src/suppression_action.rscrates/biome_markdown_analyze/tests/quick_test.rscrates/biome_markdown_analyze/tests/spec_tests.rscrates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/headers_bad.mdcrates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/headers_good.mdcrates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/invalid.mdcrates/biome_markdown_analyze/tests/specs/nursery/useConsistentHeaderLevel/valid.mdcrates/biome_markdown_factory/src/make.rscrates/biome_markdown_formatter/src/generated.rscrates/biome_markdown_formatter/src/markdown/auxiliary/mod.rscrates/biome_markdown_formatter/src/markdown/auxiliary/root.rscrates/biome_markdown_formatter/tests/spec_test.rscrates/biome_markdown_parser/src/lexer/mod.rscrates/biome_markdown_parser/src/lexer/tests.rscrates/biome_markdown_parser/src/lib.rscrates/biome_markdown_parser/src/syntax/header.rscrates/biome_markdown_parser/src/syntax/list.rscrates/biome_markdown_parser/src/syntax/mod.rscrates/biome_markdown_parser/src/syntax/parse_error.rscrates/biome_markdown_parser/src/to_html.rscrates/biome_markdown_parser/tests/fuzz_differential.rscrates/biome_markdown_parser/tests/md_test_suite/ok/too_many_hashes.mdcrates/biome_markdown_parser/tests/spec_test.rscrates/biome_markdown_syntax/src/header_ext.rscrates/biome_markdown_syntax/src/lib.rscrates/biome_markdown_syntax/src/syntax_node.rscrates/biome_rule_options/src/lib.rscrates/biome_rule_options/src/use_consistent_header_level.rscrates/biome_service/Cargo.tomlcrates/biome_service/src/configuration.rscrates/biome_service/src/documentation/mod.rscrates/biome_service/src/file_handlers/md.rscrates/biome_test_utils/src/lib.rsxtask/codegen/markdown.ungramxtask/codegen/src/generate_analyzer.rsxtask/codegen/src/markdown_kinds_src.rsxtask/coverage/src/markdown/commonmark.rs
💤 Files with no reviewable changes (1)
- crates/biome_markdown_parser/src/syntax/parse_error.rs
| let suppression_comment = format!("# {suppression_text}: {suppression_reason}"); | ||
| let suppression_comment = suppression_comment.as_str(); | ||
| let trivia = [ | ||
| (TriviaPieceKind::SingleLineComment, suppression_comment), | ||
| (TriviaPieceKind::Newline, "\n"), | ||
| ]; | ||
| if leading_whitespaces.is_empty() { | ||
| new_token = new_token.with_leading_trivia(trivia); | ||
| } | ||
| // Token is indented | ||
| else { | ||
| let mut trivia = trivia.to_vec(); | ||
|
|
||
| for w in leading_whitespaces.iter() { | ||
| trivia.push((TriviaPieceKind::Whitespace, w.text())); | ||
| } | ||
| new_token = new_token.with_leading_trivia(trivia); | ||
| } | ||
| mutation.replace_token_transfer_trivia(token_to_apply_suppression, new_token); |
There was a problem hiding this comment.
🎯 Functional Correctness | 🟠 Major | ⚡ Quick win
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
set -euo pipefail
rg -n -C 3 'enum\s+TriviaPieceKind|SingleLineComment|MultiLineComment' crates/biome_rowan
rg -n -C 3 'biome-ignore|suppression|MdHeader' crates/biome_markdown_analyze/testsRepository: biomejs/biome
Length of output: 10137
🏁 Script executed:
#!/bin/bash
set -euo pipefail
printf '%s\n' '--- suppression action ---'
cat -n crates/biome_markdown_analyze/src/suppression_action.rs | sed -n '1,150p'
printf '%s\n' '--- markdown comment handling ---'
rg -n -C 4 'HtmlComment|HTMLComment|html.?comment|MultiLineComment|SingleLineComment' crates/biome_markdown_parser crates/biome_markdown_syntax crates/biome_markdown_analyze
printf '%s\n' '--- suppression fixtures and helpers ---'
find crates/biome_markdown_analyze/tests -maxdepth 4 -type f | sort | sed -n '1,160p'
rg -n -C 5 'check_code_action|run_suppression_test|suppression' crates/biome_markdown_analyze/tests crates/biome_markdown_analyze/srcRepository: biomejs/biome
Length of output: 25863
🏁 Script executed:
#!/bin/bash
set -euo pipefail
printf '%s\n' '--- HTML comment parser ---'
cat -n crates/biome_markdown_parser/src/syntax/inline/html.rs | sed -n '1,130p'
printf '%s\n' '--- Markdown lexer and trivia construction ---'
rg -n -C 5 'TriviaPieceKind|trivia|html_comment|HtmlComment|HTML' crates/biome_markdown_parser/src crates/biome_markdown_syntax/src
printf '%s\n' '--- tracked suppression fixtures ---'
git ls-files 'crates/biome_markdown_analyze/tests/*' | rg 'suppression|\\.snap$' || true
printf '%s\n' '--- suppression test body ---'
cat -n crates/biome_markdown_analyze/tests/spec_tests.rs | sed -n '200,310p'Repository: biomejs/biome
Length of output: 50370
🏁 Script executed:
#!/bin/bash
set -euo pipefail
printf '%s\n' '--- Markdown lexer files ---'
find crates/biome_markdown_parser/src -maxdepth 3 -type f | sort | rg 'lexer|inline|block|token'
printf '%s\n' '--- lexer token definitions and hash handling ---'
rg -n -C 4 'MD_HEADER|HASH|b.\\#.|starts_with.*#|TriviaPieceKind|is_trivia' \
crates/biome_markdown_parser/src/lexer crates/biome_markdown_parser/src \
-g '*.rs' | head -n 240
printf '%s\n' '--- inline HTML parse production ---'
rg -n -C 8 'MD_INLINE_HTML|is_inline_html|inline_html' crates/biome_markdown_parser/src -g '*.rs' | head -n 240
printf '%s\n' '--- suppression fixture directories ---'
find crates/biome_markdown_analyze/tests -type d -print | sortRepository: biomejs/biome
Length of output: 37768
🏁 Script executed:
#!/bin/bash
set -euo pipefail
python3 - <<'PY'
from pathlib import Path
import re
action = Path("crates/biome_markdown_analyze/src/suppression_action.rs").read_text()
trivia = Path("crates/biome_rowan/src/syntax/trivia.rs").read_text()
lexer_tests = Path("crates/biome_markdown_parser/src/lexer/tests.rs").read_text()
header = Path("crates/biome_markdown_parser/src/syntax/header.rs").read_text()
html = Path("crates/biome_markdown_parser/src/syntax/inline/html.rs").read_text()
assert 'format!("# {suppression_text}: {suppression_reason}")' in action
assert 'TriviaPieceKind::SingleLineComment' in action
assert '/// Comment that does not contain any line breaks' in trivia
assert '/// Comment that contains at least one line break' in trivia
assert '"#",' in lexer_tests and 'HASH:1' in lexer_tests
assert 'if !p.at_line_start() && !p.at_start_of_input()' in header
assert 'MD_HEADER' in header
assert 'bytes.starts_with(b"<!--")' in html
assert 'find("-->")' in html
assert 'MD_INLINE_HTML' in html
print("The current suppression text is lexed as HASH at line start.")
print("Markdown parses a line-start HASH as MD_HEADER.")
print("The proposed HTML comment is parsed as MD_INLINE_HTML.")
print("TriviaPieceKind::MultiLineComment requires a line break; the proposed comment has none.")
PYRepository: biomejs/biome
Length of output: 403
Generate an HTML comment for inline suppression.
# {suppression_text}: ... is parsed as an MdHeader at line start. Use <!-- ... --> and keep TriviaPieceKind::SingleLineComment, because the comment contains no line break. Add a regression fixture that ensures suppression does not add an MdHeader.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@crates/biome_markdown_analyze/src/suppression_action.rs` around lines 60 -
78, Update the suppression comment construction in the token replacement flow to
use an HTML comment form (`<!-- ... -->`) instead of the Markdown heading form,
while retaining TriviaPieceKind::SingleLineComment. Add a regression fixture
covering inline suppression and verify the generated result does not contain an
MdHeader.
Source: Coding guidelines
| self.after_newline | ||
| || self.is_at_container_line_start() | ||
| || self.is_in_atx_opening_sequence() | ||
| || self.is_at_atx_closing_sequence() | ||
| } | ||
|
|
||
| /// Returns true when earlier hashes on the line form an ATX opening sequence. | ||
| fn is_in_atx_opening_sequence(&self) -> bool { | ||
| let before = &self.source[..self.position]; | ||
| let line_start = before.rfind(['\n', '\r']).map_or(0, |pos| pos + 1); | ||
| let line_prefix = &before[line_start..]; | ||
| let Some(hash_start) = line_prefix.find('#') else { | ||
| return false; | ||
| }; | ||
|
|
||
| line_prefix[..hash_start] | ||
| .bytes() | ||
| .all(|b| is_space_or_tab_byte(b) || b == b'>') | ||
| && line_prefix[hash_start..].bytes().all(|b| b == b'#') |
There was a problem hiding this comment.
📐 Maintainability & Code Quality | 🟠 Major | ⚡ Quick win
Add regression coverage for the ATX opening-sequence branch.
multiple_hashes only checks a bare ### sequence. Add cases for a container-prefixed heading such as > ### heading and for non-heading text such as text ### heading.
As per coding guidelines, “All code changes must include appropriate tests”.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@crates/biome_markdown_parser/src/lexer/mod.rs` around lines 1471 - 1489, Add
regression cases to the tests covering the is_in_atx_opening_sequence branch:
verify a container-prefixed heading such as “> ### heading” is recognized
correctly, while non-heading text such as “text ### heading” is not. Extend the
existing multiple_hashes coverage without changing lexer behavior.
Source: Coding guidelines
| #[cfg(feature = "lang_md")] | ||
| impl RegistryVisitor<MarkdownLanguage> for ProjectScanComputer<'_> { | ||
| fn record_rule<R>(&mut self) | ||
| where | ||
| R: Rule<Options: Default, Query: Queryable<Language = MarkdownLanguage, Output: Clone>> | ||
| + 'static, | ||
| { | ||
| self.check_rule::<R, MarkdownLanguage>(); | ||
| } |
There was a problem hiding this comment.
🎯 Functional Correctness | 🟠 Major | ⚡ Quick win
Register the Markdown registry in ProjectScanComputer::compute.
Line 972 adds the visitor, but Lines 869-877 do not call biome_markdown_analyze::visit_registry(&mut self). Markdown rules with Project or Types domains will not affect ScanKind.
Add the feature-gated registry call beside the other language registries. Add a regression test for the Markdown scan requirement path.
Proposed fix
#[cfg(feature = "lang_html")]
biome_html_analyze::visit_registry(&mut self);
+ #[cfg(feature = "lang_md")]
+ biome_markdown_analyze::visit_registry(&mut self);🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@crates/biome_service/src/configuration.rs` around lines 971 - 979, Update
ProjectScanComputer::compute to call biome_markdown_analyze::visit_registry(&mut
self) under the lang_md feature, alongside the other language registry calls, so
Markdown Project and Types rules influence ScanKind. Add a regression test
covering the Markdown scan requirement path.
| analyzer_cache, | ||
| } = params; | ||
|
|
||
| let _ = debug_span!("Code actions JSON", range =? range, path =? path).entered(); |
There was a problem hiding this comment.
📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win
Fix the span label.
The span reports "Code actions JSON" inside the Markdown handler. Traces for Markdown files then look like JSON work.
🔧 Proposed fix
- let _ = debug_span!("Code actions JSON", range =? range, path =? path).entered();
+ let _ = debug_span!("Code actions Markdown", range =? range, path =? path).entered();📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| let _ = debug_span!("Code actions JSON", range =? range, path =? path).entered(); | |
| let _ = debug_span!("Code actions Markdown", range =? range, path =? path).entered(); |
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@crates/biome_service/src/file_handlers/md.rs` at line 429, Update the
debug_span! label in the Markdown handler to identify Markdown processing
instead of JSON, while preserving the existing range and path fields.
| // Excluded files types which cannot contain comment in the source code | ||
| "snap" | "json" | "jsonc" | "svelte" | "vue" | "astro" | "html" => false, | ||
| "snap" | "json" | "jsonc" | "svelte" | "vue" | "astro" | "html" | "md" => false, |
There was a problem hiding this comment.
📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
# Check whether the Markdown lexer produces comment trivia.
rg -n -C3 'TriviaPieceKind::(Single|Multi)LineComment|Comments' crates/biome_markdown_parser/src
# Inspect the Markdown spec fixtures for expectation markers.
fd -t f -e md . crates/biome_markdown_analyze/tests/specs --exec sh -c 'echo "== $1"; cat "$1"' _ {}Repository: biomejs/biome
Length of output: 788
🏁 Script executed:
#!/bin/bash
set -e
printf '%s\n' '== utility context =='
sed -n '960,1025p' crates/biome_test_utils/src/lib.rs
printf '%s\n' '== Markdown parser structure =='
ast-grep outline crates/biome_markdown_parser/src
rg -n -i 'html comment|comment|trivia|InlineHtml|Html' crates/biome_markdown_parser crates/biome_markdown_analyze
printf '%s\n' '== expectation handling =='
rg -n -C4 'should (not )?generate diagnostics|excluded|extension|file.*type|comment' crates/biome_test_utils crates/biome_markdown_analyze/testsRepository: biomejs/biome
Length of output: 50372
🏁 Script executed:
#!/bin/bash
set -e
printf '%s\n' '== expectation implementation =='
sed -n '1000,1075p' crates/biome_test_utils/src/lib.rs
sed -n '175,205p' crates/biome_markdown_analyze/tests/spec_tests.rs
printf '%s\n' '== Markdown token and HTML-comment handling =='
sed -n '1,130p' crates/biome_markdown_parser/src/lexer/mod.rs
sed -n '1,180p' crates/biome_markdown_parser/src/syntax/inline/html.rs
sed -n '1,130p' crates/biome_markdown_parser/src/syntax/html_block.rs
printf '%s\n' '== comment token definitions =='
rg -n -C3 'Comment|comment|Html|HTML' crates/biome_markdown_parser/src/lexer crates/biome_markdown_parser/src/syntax crates/biome_markdown_parser/src/token_source.rsRepository: biomejs/biome
Length of output: 50371
Document Markdown’s exclusion rationale. Markdown supports HTML comments, but the parser stores them as MD_HTML_LITERAL, not comment trivia. Replace the current “cannot contain comment” wording with this reason.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@crates/biome_test_utils/src/lib.rs` around lines 1006 - 1007, Update the
exclusion comment above the file-type match to explain that Markdown supports
HTML comments, but the parser represents them as MD_HTML_LITERAL rather than
comment trivia; leave the exclusion list and behavior unchanged.
There was a problem hiding this comment.
♻️ Duplicate comments (1)
crates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rs (1)
20-32: 🎯 Functional Correctness | 🟠 Major | ⚡ Quick winUse executable Markdown heading examples.
The documentation parser preserves
\# Header 1. The Markdown parser then treats it as paragraph content. The invalid fixture has only a level-three header, soexpect_diagnosticfails. Use level-two and level-four headings instead. The valid fixture should also contain two real consecutive headings.Proposed fix
- /// \# Header 1 + /// ## Header 2 /// - /// ### Header 3 + /// #### Header 4 @@ - /// \# Header 1 + /// ## Header 2 /// - /// ## Header 2 + /// ### Header 3As per coding guidelines, use rustdoc documentation for documenting new rule behaviour accurately.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@crates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rs` around lines 20 - 32, Update the rustdoc examples for the heading-level rule so escaped `\#` markers become executable Markdown headings: use level-two and level-four headings in the invalid `expect_diagnostic` fixture, and make the valid fixture contain two real consecutive headings with the intended levels.Source: Coding guidelines
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Duplicate comments:
In
`@crates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rs`:
- Around line 20-32: Update the rustdoc examples for the heading-level rule so
escaped `\#` markers become executable Markdown headings: use level-two and
level-four headings in the invalid `expect_diagnostic` fixture, and make the
valid fixture contain two real consecutive headings with the intended levels.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: ea8f4db6-c1d6-41a6-a887-478a9384ddec
⛔ Files ignored due to path filters (2)
Cargo.lockis excluded by!**/*.lockand included by**packages/@biomejs/backend-jsonrpc/src/workspace.tsis excluded by!**/backend-jsonrpc/src/workspace.tsand included by**
📒 Files selected for processing (4)
crates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rscrates/biome_markdown_analyze/tests/spec_tests.rsxtask/rules_check/Cargo.tomlxtask/rules_check/src/lib.rs
🚧 Files skipped from review as they are similar to previous changes (1)
- crates/biome_markdown_analyze/tests/spec_tests.rs
19f5552 to
7ef4a23
Compare
|
Suppressions haven't been implemented yet. I will take a bit more time because they are particular here. Unfortunately, we can't even test this rule via rule docs because in Rust the |
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@xtask/codegen/src/generate_configuration.rs`:
- Around line 282-283: Update generate_rules_configuration to invoke
biome_markdown_analyze::visit_registry for both its lint and assist visitors,
matching the existing calls in generate_rule_options. Keep the visitor
registrations in generate_rule_options unchanged so generated linter and assist
configurations include Markdown rules.
🪄 Autofix
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 692d10ce-5661-4dc4-9a04-fcb1f666259b
⛔ Files ignored due to path filters (1)
Cargo.lockis excluded by!**/*.lockand included by**
📒 Files selected for processing (3)
crates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rsxtask/codegen/Cargo.tomlxtask/codegen/src/generate_configuration.rs
🚧 Files skipped from review as they are similar to previous changes (1)
- crates/biome_markdown_analyze/src/lint/nursery/use_consistent_header_level.rs
|
Isn't the official markdown syntax naming Heading instead of Header? |
I don't know, but what kind changes do you want? Feel free to suggest them and I will create a PR |
|
If that makes sense ofc 😅 |
|
Yeah it does. I'll shoot a PR sson |
Summary
This PR adds the markdown linter to our repository.
It adds one lint rule: https://github.com/markdownlint/markdownlint/blob/main/docs/RULES.md#md001---header-levels-should-only-increment-by-one-level-at-a-time
I didn't add metadata because I don't know how to link it. We can do that later.
MdDocumenttoMdRoot, in line with our nomenclatureTest Plan
Added new tests
Docs
Please review the docs, it's possible they are stale (copy-paste)