Skip to content

Conversation

@taga3s
Copy link
Contributor

@taga3s taga3s commented Dec 25, 2025

Summary

This PR adds noBeforeInteractiveScriptOutsideDocument to Next.js. It prevents usage of next/script's beforeInteractive strategy outside of pages/_document.js.

Next.js docs say this rule applies to both app/layout.jsx and pages/_document.js, but actually this rule only applies to pages/_document.js. The current implementation of the original ESLint source only handles pages/_document.js, so I followed its implementation.

Test Plan

  • I added tests that demonstrate Pages Router project.

Docs

Invalid

// pages/index.js
import Script from 'next/script'

export default function Index() {
  return (
    <div>
      <Script
        src="https://example.com/script.js"
        strategy="beforeInteractive"
      ></Script>
    </div>
  )
}

Valid

// pages/_document.js
import { Html, Head, Main, NextScript } from 'next/document'
import Script from 'next/script'

export default function Document() {
  return (
    <Html>
      <Head />
      <body>
        <Main />
        <NextScript />
        <Script
          src="https://example.com/script.js"
          strategy="beforeInteractive"
        ></Script>
      </body>
    </Html>
  )
}

@changeset-bot
Copy link

changeset-bot bot commented Dec 25, 2025

🦋 Changeset detected

Latest commit: eb5d7fb

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 14 packages
Name Type
@biomejs/biome Minor
@biomejs/cli-win32-x64 Minor
@biomejs/cli-win32-arm64 Minor
@biomejs/cli-darwin-x64 Minor
@biomejs/cli-darwin-arm64 Minor
@biomejs/cli-linux-x64 Minor
@biomejs/cli-linux-arm64 Minor
@biomejs/cli-linux-x64-musl Minor
@biomejs/cli-linux-arm64-musl Minor
@biomejs/wasm-web Minor
@biomejs/wasm-bundler Minor
@biomejs/wasm-nodejs Minor
@biomejs/backend-jsonrpc Patch
@biomejs/js-api Major

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

@github-actions github-actions bot added A-CLI Area: CLI A-Project Area: project A-Linter Area: linter L-JavaScript Language: JavaScript and super languages A-Diagnostic Area: diagnostocis labels Dec 25, 2025
@taga3s taga3s changed the title feat(linter): port `noBeforeInteractiveScriptOutsideDocument\ from Next.js feat(linter): port noBeforeInteractiveScriptOutsideDocument from Next.js Dec 25, 2025
@codspeed-hq
Copy link

codspeed-hq bot commented Dec 25, 2025

CodSpeed Performance Report

Merging #8578 will not alter performance

Comparing taga3s:feat-noBeforeInteractiveScriptOutsideDocument (eb5d7fb) with next (ab88099)1

Summary

✅ 58 untouched
⏩ 95 skipped2

Footnotes

  1. No successful run was found on next (73f4f53) during the generation of this report, so ab88099 was used instead as the comparison base. There might be some changes unrelated to this pull request in this report.

  2. 95 benchmarks were skipped, so the baseline results were used instead. If they were deleted from the codebase, click here and archive them to remove them from the performance reports.

@taga3s taga3s force-pushed the feat-noBeforeInteractiveScriptOutsideDocument branch from a06bcce to c8754fc Compare December 25, 2025 01:59
@taga3s taga3s marked this pull request as ready for review December 25, 2025 02:02
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Dec 25, 2025

Walkthrough

This pull request introduces a new lint rule noBeforeInteractiveScriptOutsideDocument that detects usage of Next.js Script component with the beforeInteractive strategy outside of permitted contexts like pages/_document.js. The implementation includes the core rule definition, an options struct, test cases, and an associated changeset. The rule validates that Script elements from next/script only use the beforeInteractive strategy within allowed document scopes and reports a warning diagnostic with a reference to Next.js documentation.

Suggested reviewers

  • dyc3
  • ematipico

Pre-merge checks and finishing touches

✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the main change: porting the Next.js rule noBeforeInteractiveScriptOutsideDocument into Biome.
Linked Issues check ✅ Passed The PR successfully implements all coding requirements from issue #7651: the rule is named noBeforeInteractiveScriptOutsideDocument, detects next/script with strategy="beforeInteractive" outside pages/_document.js, and includes test cases.
Out of Scope Changes check ✅ Passed All changes are directly related to implementing the noBeforeInteractiveScriptOutsideDocument rule, including the rule logic, options struct, test files, and registry updates.
Description check ✅ Passed The PR description clearly describes the addition of the noBeforeInteractiveScriptOutsideDocument rule for Next.js, including the issue being closed, the rule's purpose, and concrete examples of valid and invalid usage.
✨ Finishing touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a 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 (3)
.changeset/social-candies-wave.md (1)

6-6: Consider simplifying "outside of" to "outside" and add an invalid code example.

The phrase "outside of" can be simplified to "outside". Additionally, per coding guidelines, changesets for new lint rules should include an example of invalid code.

📝 Suggested improvement
-This rule prevents usage of `next/script`'s `beforeInteractive` strategy outside of `app/layout.jsx` or `pages/_document.js`.
+This rule prevents usage of `next/script`'s `beforeInteractive` strategy outside `app/layout.jsx` or `pages/_document.js`.
+
+```jsx
+// app/index.jsx - ❌ Invalid
+<Script src="example.js" strategy="beforeInteractive" />
+```

Based on learnings.

crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/layout.jsx (1)

3-3: Component naming seems inconsistent across fixtures.

This root layout is named SomePageLayout, whilst the nested layout in app/some-page/layout.jsx is named RootLayout. This appears backwards—typically root layouts use generic names like RootLayout and nested layouts have more specific names.

crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (1)

23-64: Add an Invalid example to the documentation.

The docs only show valid cases. Including an invalid example helps users understand what triggers the rule.

Suggested addition after the Valid section
    /// ### Invalid
    ///
    /// ```jsx,expect_diagnostic
    /// // pages/index.jsx
    /// import Script from 'next/script'
    ///
    /// export default function Index() {
    ///     return (
    ///         <Script
    ///           src="https://example.com/script.js"
    ///           strategy="beforeInteractive"
    ///         />
    ///     )
    /// }
    /// ```
📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 73f4f53 and 4a7e869.

⛔ Files ignored due to path filters (13)
  • crates/biome_cli/src/execute/migrate/eslint_any_rule_to_biome.rs is excluded by !**/migrate/eslint_any_rule_to_biome.rs and included by **
  • crates/biome_configuration/src/analyzer/linter/rules.rs is excluded by !**/rules.rs and included by **
  • crates/biome_configuration/src/generated/domain_selector.rs is excluded by !**/generated/**, !**/generated/** and included by **
  • crates/biome_diagnostics_categories/src/categories.rs is excluded by !**/categories.rs and included by **
  • crates/biome_js_analyze/src/lint/nursery.rs is excluded by !**/nursery.rs and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.jsx.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.tsx.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/layout.jsx.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/some-page/layout.jsx.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/_document.jsx.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx.snap is excluded by !**/*.snap and included by **
  • packages/@biomejs/backend-jsonrpc/src/workspace.ts is excluded by !**/backend-jsonrpc/src/workspace.ts and included by **
  • packages/@biomejs/biome/configuration_schema.json is excluded by !**/configuration_schema.json and included by **
📒 Files selected for processing (10)
  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.jsx
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.tsx
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/layout.jsx
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/some-page/layout.jsx
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/_document.jsx
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx
  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
🧰 Additional context used
📓 Path-based instructions (1)
**/*.rs

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.rs: Use inline rustdoc documentation for rules, assists, and their options
Use the dbg!() macro for debugging output in Rust tests and code
Use doc tests (doctest) format with code blocks in rustdoc comments; ensure assertions pass in tests

Files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧠 Learnings (29)
📓 Common learnings
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Commit rule work with message format `feat(biome_<language>_analyze): <ruleName>`
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-21T21:15:03.782Z
Learning: For new lint rules in changesets, show an example of invalid case in inline code or code block
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/lib/**/*.rs : Rule options must be placed inside the `biome_rule_options` crate

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/lib/**/*.rs : Wrap rule options fields in `Option<>` to properly track set and unset options during merge

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `options` code block property for rule-specific configuration snippets in documentation

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/lib/**/*.rs : Use `deny_unknown_fields` in serde derive macro for rule options

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Rule documentation must include `## Options` section if the rule has options

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Lines prefixed with `#` in rule documentation code examples will be hidden from output

Applied to files:

  • crates/biome_rule_options/src/lib.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 : No module may copy or clone data from another module in the module graph, not even behind an `Arc`

Applied to files:

  • crates/biome_rule_options/src/lib.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Rule documentation code blocks should be ordered as language, expect_diagnostic, options/full_options/use_options, ignore, file

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : The first paragraph of rule documentation must be a single line describing what the rule does

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/lib/**/*.rs : Implement `Merge` trait for rule options to support configuration inheritance

Applied to files:

  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Commit rule work with message format `feat(biome_<language>_analyze): <ruleName>`

Applied to files:

  • .changeset/social-candies-wave.md
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `version` field to `next` in `declare_lint_rule!` macro

Applied to files:

  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Add `sources` field with `RuleSource` to cite ESLint or other rules that inspired the implementation

Applied to files:

  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/lib/**/*.rs : Rule options struct must derive `Deserializable`, `Serialize`, `Deserialize`, and optionally `JsonSchema`

Applied to files:

  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/biome_rule_options/lib/**/*.rs : Use `rename_all = "camelCase"` in serde derive macro for rule options

Applied to files:

  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `full_options` code block property for complete biome.json configuration snippets in documentation

Applied to files:

  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `use_options` code block property for code examples that follow an options configuration in documentation

Applied to files:

  • crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Add `issue_number` field to `declare_lint_rule!` macro for work-in-progress rules

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Place new rules inside the `nursery` group during development

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should perform static analysis of source code to detect invalid or error-prone patterns and emit diagnostics with proposed fixes

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-22T09:26:56.943Z
Learnt from: ematipico
Repo: biomejs/biome PR: 8537
File: crates/biome_js_analyze/src/lint/nursery/no_leaked_render.rs:167-210
Timestamp: 2025-12-22T09:26:56.943Z
Learning: When defining lint rules (declare_lint_rule!), only specify fix_kind if the rule implements an action(...) function. Rules that only emit diagnostics without a code fix should omit fix_kind. This applies to all Rust lint rule definitions under crates/.../src/lint (e.g., crates/biome_js_analyze/src/lint/...).

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Set `recommended` field to `false` for new rules in the nursery group

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `domains` field in `declare_lint_rule!` to tag rules that belong to specific concepts like testing or frameworks

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).same()` when implementing a rule that matches the behavior of an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).inspired()` when implementing a rule inspired by but with different behavior than an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `declare_lint_rule!` macro to declare analyzer rule types and implement the RuleMeta trait

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `language` to `jsx`, `ts`, or `tsx` for rules that only apply to specific JavaScript dialects

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should check syntax according to language specification and emit error diagnostics

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧬 Code graph analysis (3)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.jsx (2)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.tsx (1)
  • Index (3-12)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx (1)
  • Index (3-12)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx (2)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.jsx (1)
  • Index (3-12)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.tsx (1)
  • Index (3-12)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.tsx (2)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.jsx (1)
  • Index (3-12)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx (1)
  • Index (3-12)
🪛 LanguageTool
.changeset/social-candies-wave.md

[style] ~6-~6: This phrase is redundant. Consider using “outside”.
Context: .../script's beforeInteractivestrategy outside ofapp/layout.jsxorpages/_document.js...

(OUTSIDE_OF)

⏰ 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: Test (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Check Dependencies
  • GitHub Check: Test (depot-windows-2022-16)
  • GitHub Check: Documentation
  • GitHub Check: Lint project (depot-windows-2022)
  • GitHub Check: Bench (biome_js_analyze)
  • GitHub Check: Bench (biome_js_formatter)
  • GitHub Check: Bench (biome_js_parser)
  • GitHub Check: autofix
  • GitHub Check: Bench (biome_configuration)
🔇 Additional comments (9)
crates/biome_rule_options/src/no_before_interactive_script_outside_document.rs (1)

1-6: LGTM!

The options struct correctly follows all required patterns: proper derives, serde attributes with camelCase and deny_unknown_fields, and conditional JSON schema support. An empty struct is appropriate for a rule without configuration options.

crates/biome_rule_options/src/lib.rs (1)

20-20: LGTM!

Module declaration is correctly placed in alphabetical order and follows the crate's conventions.

crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.jsx (1)

1-12: LGTM!

Test fixture correctly demonstrates beforeInteractive usage in app/index.jsx, which should be flagged by the rule (only app/layout.* and pages/_document.* are allowed).

crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/_document.jsx (1)

1-18: LGTM!

Test fixture correctly demonstrates valid usage of beforeInteractive in pages/_document.jsx, which is an allowed location per Next.js documentation.

crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/some-page/layout.jsx (1)

1-13: The component name RootLayout is misleading in a nested path.

The test fixture correctly demonstrates that nested layouts with beforeInteractive scripts trigger a diagnostic (as shown in the snapshot). However, calling the component RootLayout when it's in app/some-page/ is confusing—it should be SomePageLayout or similar to match the pattern in the root app/layout.jsx.snap file.

crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/index.tsx (1)

1-1: No action needed—the 'myscript' import is intentional.

This is a negative test case verifying the rule correctly targets only next/script imports. Excellent coverage.

crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx (1)

1-12: LGTM!

Solid test case for the invalid scenario — beforeInteractive in pages/index.jsx should indeed trigger the rule.

crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (2)

83-128: LGTM!

The implementation correctly identifies the Script component from next/script, validates the beforeInteractive strategy, and properly allows only the root app/layout.* and pages/_document.* files. The ancestor-based path checking handles src/ prefixed projects as well.


130-140: LGTM!

Clear diagnostic message with a helpful link to the Next.js documentation.

Copy link
Contributor

@coderabbitai coderabbitai bot left a 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 (1)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (1)

23-64: Consider adding invalid examples to documentation.

The documentation shows valid usage but lacks examples of invalid code that would trigger the rule. Adding an invalid example (e.g., using beforeInteractive in pages/index.jsx) would help users understand what the rule catches.

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 4a7e869 and 110498f.

⛔ Files ignored due to path filters (2)
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/layout.jsx.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/some-page/layout.jsx.snap is excluded by !**/*.snap and included by **
📒 Files selected for processing (3)
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/layout.jsx
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/some-page/layout.jsx
🚧 Files skipped from review as they are similar to previous changes (1)
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/layout.jsx
🧰 Additional context used
📓 Path-based instructions (1)
**/*.rs

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.rs: Use inline rustdoc documentation for rules, assists, and their options
Use the dbg!() macro for debugging output in Rust tests and code
Use doc tests (doctest) format with code blocks in rustdoc comments; ensure assertions pass in tests

Files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧠 Learnings (21)
📓 Common learnings
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-21T21:15:03.782Z
Learning: For promoting rules from nursery or implementing new features affecting end users, send PRs to the `next` branch
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Add `issue_number` field to `declare_lint_rule!` macro for work-in-progress rules
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Place new rules inside the `nursery` group during development
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Add `sources` field with `RuleSource` to cite ESLint or other rules that inspired the implementation
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `version` field to `next` in `declare_lint_rule!` macro
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `language` to `jsx`, `ts`, or `tsx` for rules that only apply to specific JavaScript dialects
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).same()` when implementing a rule that matches the behavior of an ESLint rule
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `declare_lint_rule!` macro to declare analyzer rule types and implement the RuleMeta trait
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `domains` field in `declare_lint_rule!` to tag rules that belong to specific concepts like testing or frameworks
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Specify `fix_kind: FixKind::Safe` in `declare_lint_rule!` for safe code actions
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `options` code block property for rule-specific configuration snippets in documentation
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Add `issue_number` field to `declare_lint_rule!` macro for work-in-progress rules

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Place new rules inside the `nursery` group during development

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `version` field to `next` in `declare_lint_rule!` macro

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should perform static analysis of source code to detect invalid or error-prone patterns and emit diagnostics with proposed fixes

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Add `sources` field with `RuleSource` to cite ESLint or other rules that inspired the implementation

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : The first paragraph of rule documentation must be a single line describing what the rule does

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).same()` when implementing a rule that matches the behavior of an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).inspired()` when implementing a rule inspired by but with different behavior than an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Set `recommended` field to `false` for new rules in the nursery group

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-22T09:26:56.943Z
Learnt from: ematipico
Repo: biomejs/biome PR: 8537
File: crates/biome_js_analyze/src/lint/nursery/no_leaked_render.rs:167-210
Timestamp: 2025-12-22T09:26:56.943Z
Learning: When defining lint rules (declare_lint_rule!), only specify fix_kind if the rule implements an action(...) function. Rules that only emit diagnostics without a code fix should omit fix_kind. This applies to all Rust lint rule definitions under crates/.../src/lint (e.g., crates/biome_js_analyze/src/lint/...).

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Rules with `recommended: true` and no domains are enabled by default

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Rules with `recommended: true` and domains are only enabled when the domain is enabled

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-21T21:15:03.782Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-21T21:15:03.782Z
Learning: For new nursery rules, send PRs to the maintenance branch `main`

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set rule severity to `warn` or `error` for rules in suspicious group

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set rule severity to `error` for rules in correctness, security, and a11y groups

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `declare_lint_rule!` macro to declare analyzer rule types and implement the RuleMeta trait

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `language` to `jsx`, `ts`, or `tsx` for rules that only apply to specific JavaScript dialects

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should check syntax according to language specification and emit error diagnostics

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `domains` field in `declare_lint_rule!` to tag rules that belong to specific concepts like testing or frameworks

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Rule documentation code blocks should be ordered as language, expect_diagnostic, options/full_options/use_options, ignore, file

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧬 Code graph analysis (1)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (3)
crates/biome_service/src/workspace.rs (1)
  • markup (1203-1205)
packages/@biomejs/plugin-api/index.d.ts (1)
  • Severity (1-1)
crates/biome_analyze/src/rule.rs (4)
  • sources (630-633)
  • same (249-254)
  • recommended (615-618)
  • domains (645-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). (12)
  • GitHub Check: Lint project (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Test (depot-windows-2022-16)
  • GitHub Check: End-to-end tests
  • GitHub Check: Lint project (depot-windows-2022)
  • GitHub Check: Test (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Check Dependencies
  • GitHub Check: Documentation
  • GitHub Check: Bench (biome_js_analyze)
  • GitHub Check: Bench (biome_js_formatter)
  • GitHub Check: Bench (biome_js_parser)
  • GitHub Check: autofix
  • GitHub Check: Bench (biome_configuration)
🔇 Additional comments (5)
crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/app/some-page/layout.jsx (1)

1-13: Test fixture looks good.

This correctly tests that nested layouts (e.g., app/some-page/layout.jsx) should trigger the rule, since beforeInteractive scripts must be placed in app/layout.jsx at the root.

crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (4)

1-14: Imports look good.

All necessary dependencies are present for implementing the lint rule.


77-82: Type definitions are correct.

Appropriate types for detecting JSX elements and emitting diagnostics. Correctly omits fix_kind since the rule doesn't implement an action function.


83-128: Rule logic is sound.

The implementation correctly:

  • Identifies Script components from next/script
  • Checks for the beforeInteractive strategy
  • Enforces that such scripts must be in app/layout.{jsx,tsx} at the root or pages/_document.{jsx,tsx}
  • Properly rejects nested layouts (e.g., app/some-page/layout.jsx)

The path-checking logic using .ancestors().nth(1) to verify the parent directory is appropriate for Next.js conventions.


130-140: Diagnostic message is clear and helpful.

The message effectively communicates the issue and provides a link to Next.js documentation for additional context. Good developer experience.

Comment on lines +66 to +74
pub NoBeforeInteractiveScriptOutsideDocument {
version: "next",
name: "noBeforeInteractiveScriptOutsideDocument",
language: "jsx",
sources: &[RuleSource::EslintNext("no-before-interactive-script-outside-document").same()],
recommended: false,
severity: Severity::Warning,
domains: &[RuleDomain::Next],
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion | 🟠 Major

Add issue_number field to the rule metadata.

Based on learnings, work-in-progress rules in the nursery group should include an issue_number field. Since this PR closes issue #7651, add issue_number: "7651" to the metadata.

🔎 Proposed fix
 pub NoBeforeInteractiveScriptOutsideDocument {
     version: "next",
     name: "noBeforeInteractiveScriptOutsideDocument",
     language: "jsx",
     sources: &[RuleSource::EslintNext("no-before-interactive-script-outside-document").same()],
     recommended: false,
     severity: Severity::Warning,
     domains: &[RuleDomain::Next],
+    issue_number: "7651",
 }
📝 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.

Suggested change
pub NoBeforeInteractiveScriptOutsideDocument {
version: "next",
name: "noBeforeInteractiveScriptOutsideDocument",
language: "jsx",
sources: &[RuleSource::EslintNext("no-before-interactive-script-outside-document").same()],
recommended: false,
severity: Severity::Warning,
domains: &[RuleDomain::Next],
}
pub NoBeforeInteractiveScriptOutsideDocument {
version: "next",
name: "noBeforeInteractiveScriptOutsideDocument",
language: "jsx",
sources: &[RuleSource::EslintNext("no-before-interactive-script-outside-document").same()],
recommended: false,
severity: Severity::Warning,
domains: &[RuleDomain::Next],
issue_number: "7651",
}
🤖 Prompt for AI Agents
In
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
around lines 66 to 74, the rule metadata is missing the required issue_number
field for nursery work-in-progress rules; add issue_number: "7651" to the struct
initializer alongside the existing fields so the metadata includes the linked
issue number.

@taga3s taga3s changed the title feat(linter): port noBeforeInteractiveScriptOutsideDocument from Next.js feat(biome_js_analyze): port noBeforeInteractiveScriptOutsideDocument from Next.js Dec 25, 2025
Copy link
Contributor

@coderabbitai coderabbitai bot left a 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)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (1)

49-57: Add issue_number field to the rule metadata.

Based on learnings, work-in-progress rules in the nursery group should include an issue_number field. Since this PR closes issue #7651, add issue_number: "7651" to the metadata.

🔎 Proposed fix
 pub NoBeforeInteractiveScriptOutsideDocument {
     version: "next",
     name: "noBeforeInteractiveScriptOutsideDocument",
     language: "jsx",
     sources: &[RuleSource::EslintNext("no-before-interactive-script-outside-document").same()],
     recommended: false,
     severity: Severity::Warning,
     domains: &[RuleDomain::Next],
+    issue_number: "7651",
 }
🧹 Nitpick comments (2)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (1)

23-47: Add invalid example to documentation.

The documentation only demonstrates valid usage. Including an invalid case helps users understand what the rule catches.

🔎 Suggested addition

After the valid example, add:

+    /// ### Invalid
+    ///
+    /// ```jsx,expect_diagnostic
+    /// // pages/index.js
+    /// import Script from 'next/script'
+    ///
+    /// export default function Page() {
+    ///     return (
+    ///         <Script
+    ///           src="https://example.com/script.js"
+    ///           strategy="beforeInteractive"
+    ///         ></Script>
+    ///     )
+    /// }
+    /// ```
+    ///
.changeset/social-candies-wave.md (1)

5-6: Add invalid example to changeset.

Based on learnings, changesets should demonstrate what is now invalid. Consider adding a brief example showing code that will now be flagged.

🔎 Suggested addition
 Added ['noBeforeInteractiveScriptOutsideDocument'](https://biomejs.dev/linter/rules/no-before-interactive-script-outside-document/) to Next.js.
-This rule prevents usage of `next/script`'s `beforeInteractive` strategy outside of `pages/_document.js`.
+This rule prevents usage of `next/script`'s `beforeInteractive` strategy outside `pages/_document.js`.
+
+The following code in `pages/index.js` is now flagged:
+```jsx
+<Script src="https://example.com/script.js" strategy="beforeInteractive" />
+```

Note: Also simplified "outside of" to "outside" per static analysis suggestion.

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 110498f and 99f6aaa.

⛔ Files ignored due to path filters (2)
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/suspicious/noHeadImportInDocument/app/_document.jsx.snap is excluded by !**/*.snap and included by **
📒 Files selected for processing (3)
  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
  • crates/biome_js_analyze/tests/specs/suspicious/noHeadImportInDocument/app/_document.jsx
💤 Files with no reviewable changes (1)
  • crates/biome_js_analyze/tests/specs/suspicious/noHeadImportInDocument/app/_document.jsx
🧰 Additional context used
📓 Path-based instructions (1)
**/*.rs

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.rs: Use inline rustdoc documentation for rules, assists, and their options
Use the dbg!() macro for debugging output in Rust tests and code
Use doc tests (doctest) format with code blocks in rustdoc comments; ensure assertions pass in tests

Files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧠 Learnings (17)
📓 Common learnings
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Commit rule work with message format `feat(biome_<language>_analyze): <ruleName>`
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should perform static analysis of source code to detect invalid or error-prone patterns and emit diagnostics with proposed fixes
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).same()` when implementing a rule that matches the behavior of an ESLint rule
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-21T21:15:03.782Z
Learning: For new lint rules in changesets, show an example of invalid case in inline code or code block
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Run `just l` to lint analyzer rule code
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Add `issue_number` field to `declare_lint_rule!` macro for work-in-progress rules

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Place new rules inside the `nursery` group during development

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `version` field to `next` in `declare_lint_rule!` macro

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
  • .changeset/social-candies-wave.md
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should perform static analysis of source code to detect invalid or error-prone patterns and emit diagnostics with proposed fixes

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Add `sources` field with `RuleSource` to cite ESLint or other rules that inspired the implementation

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
  • .changeset/social-candies-wave.md
📚 Learning: 2025-12-22T09:26:56.943Z
Learnt from: ematipico
Repo: biomejs/biome PR: 8537
File: crates/biome_js_analyze/src/lint/nursery/no_leaked_render.rs:167-210
Timestamp: 2025-12-22T09:26:56.943Z
Learning: When defining lint rules (declare_lint_rule!), only specify fix_kind if the rule implements an action(...) function. Rules that only emit diagnostics without a code fix should omit fix_kind. This applies to all Rust lint rule definitions under crates/.../src/lint (e.g., crates/biome_js_analyze/src/lint/...).

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).inspired()` when implementing a rule inspired by but with different behavior than an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).same()` when implementing a rule that matches the behavior of an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Set `recommended` field to `false` for new rules in the nursery group

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `domains` field in `declare_lint_rule!` to tag rules that belong to specific concepts like testing or frameworks

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `declare_lint_rule!` macro to declare analyzer rule types and implement the RuleMeta trait

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `language` to `jsx`, `ts`, or `tsx` for rules that only apply to specific JavaScript dialects

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should check syntax according to language specification and emit error diagnostics

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Rule documentation code blocks should be ordered as language, expect_diagnostic, options/full_options/use_options, ignore, file

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Commit rule work with message format `feat(biome_<language>_analyze): <ruleName>`

Applied to files:

  • .changeset/social-candies-wave.md
📚 Learning: 2025-12-21T21:15:03.782Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-21T21:15:03.782Z
Learning: For rule changes in changesets, clearly demonstrate what is now invalid that wasn't before, or vice versa

Applied to files:

  • .changeset/social-candies-wave.md
🧬 Code graph analysis (1)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (1)
crates/biome_analyze/src/rule.rs (4)
  • sources (630-633)
  • same (249-254)
  • recommended (615-618)
  • domains (645-648)
🪛 LanguageTool
.changeset/social-candies-wave.md

[style] ~6-~6: This phrase is redundant. Consider using “outside”.
Context: .../script's beforeInteractivestrategy outside ofpages/_document.js`.

(OUTSIDE_OF)

⏰ 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). (11)
  • GitHub Check: Bench (biome_js_formatter)
  • GitHub Check: Bench (biome_js_analyze)
  • GitHub Check: Bench (biome_js_parser)
  • GitHub Check: Check Dependencies
  • GitHub Check: Lint project (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Test (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Test (depot-windows-2022-16)
  • GitHub Check: Lint project (depot-windows-2022)
  • GitHub Check: Documentation
  • GitHub Check: Bench (biome_configuration)
  • GitHub Check: autofix
🔇 Additional comments (1)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (1)

66-110: Implementation logic is sound.

The rule correctly:

  • Excludes the entire app/ directory (lines 73-79), which aligns with Next.js guidance that beforeInteractive is for Pages Router only
  • Validates the Script binding originates from next/script (lines 81-87)
  • Checks for the specific strategy attribute value (lines 89-94)
  • Permits pages/_document.* files only at the root of pages/ directory (lines 101-107), correctly rejecting nested variants like pages/api/_document.js

@taga3s taga3s force-pushed the feat-noBeforeInteractiveScriptOutsideDocument branch from a36c802 to bd03848 Compare December 25, 2025 07:36
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 0

♻️ Duplicate comments (1)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (1)

67-75: Missing issue_number field.

As flagged in a previous review, add issue_number: "7651" to the rule metadata.

🧹 Nitpick comments (1)
.changeset/social-candies-wave.md (1)

5-6: Add an example of invalid code.

Per project conventions, changesets for new lint rules should include an inline example of what the rule flags.

🔎 Proposed fix
 Added ['noBeforeInteractiveScriptOutsideDocument'](https://biomejs.dev/linter/rules/no-before-interactive-script-outside-document/) to Next.js.
 This rule prevents usage of `next/script`'s `beforeInteractive` strategy outside of `pages/_document.js`.
+
+```jsx
+// Invalid: pages/index.js
+import Script from 'next/script'
+
+<Script src="https://example.com" strategy="beforeInteractive" />
+```

Based on learnings, changesets for new lint rules should show an example of invalid case.

📜 Review details

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 99f6aaa and bd03848.

⛔ Files ignored due to path filters (4)
  • crates/biome_configuration/src/analyzer/linter/rules.rs is excluded by !**/rules.rs and included by **
  • crates/biome_js_analyze/tests/specs/nursery/noBeforeInteractiveScriptOutsideDocument/pages/index.jsx.snap is excluded by !**/*.snap and included by **
  • packages/@biomejs/backend-jsonrpc/src/workspace.ts is excluded by !**/backend-jsonrpc/src/workspace.ts and included by **
  • packages/@biomejs/biome/configuration_schema.json is excluded by !**/configuration_schema.json and included by **
📒 Files selected for processing (2)
  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧰 Additional context used
📓 Path-based instructions (1)
**/*.rs

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.rs: Use inline rustdoc documentation for rules, assists, and their options
Use the dbg!() macro for debugging output in Rust tests and code
Use doc tests (doctest) format with code blocks in rustdoc comments; ensure assertions pass in tests

Files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧠 Learnings (18)
📓 Common learnings
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Commit rule work with message format `feat(biome_<language>_analyze): <ruleName>`
Learnt from: CR
Repo: biomejs/biome PR: 0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-12-21T21:15:03.782Z
Learning: For new lint rules in changesets, show an example of invalid case in inline code or code block
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Commit rule work with message format `feat(biome_<language>_analyze): <ruleName>`

Applied to files:

  • .changeset/social-candies-wave.md
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `version` field to `next` in `declare_lint_rule!` macro

Applied to files:

  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Add `sources` field with `RuleSource` to cite ESLint or other rules that inspired the implementation

Applied to files:

  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Set `language` to `jsx`, `ts`, or `tsx` for rules that only apply to specific JavaScript dialects

Applied to files:

  • .changeset/social-candies-wave.md
  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Add `issue_number` field to `declare_lint_rule!` macro for work-in-progress rules

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Place new rules inside the `nursery` group during development

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should perform static analysis of source code to detect invalid or error-prone patterns and emit diagnostics with proposed fixes

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/nursery/**/*.rs : Set `recommended` field to `false` for new rules in the nursery group

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-22T09:26:56.943Z
Learnt from: ematipico
Repo: biomejs/biome PR: 8537
File: crates/biome_js_analyze/src/lint/nursery/no_leaked_render.rs:167-210
Timestamp: 2025-12-22T09:26:56.943Z
Learning: When defining lint rules (declare_lint_rule!), only specify fix_kind if the rule implements an action(...) function. Rules that only emit diagnostics without a code fix should omit fix_kind. This applies to all Rust lint rule definitions under crates/.../src/lint (e.g., crates/biome_js_analyze/src/lint/...).

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : The first paragraph of rule documentation must be a single line describing what the rule does

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `domains` field in `declare_lint_rule!` to tag rules that belong to specific concepts like testing or frameworks

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/lint/**/*.rs : Lint rules should check syntax according to language specification and emit error diagnostics

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Prefix line with `#` in documentation code examples sparingly; prefer concise complete snippets

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).same()` when implementing a rule that matches the behavior of an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `RuleSource::Eslint(...).inspired()` when implementing a rule inspired by but with different behavior than an ESLint rule

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Use `declare_lint_rule!` macro to declare analyzer rule types and implement the RuleMeta trait

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
📚 Learning: 2025-12-19T12:53:30.399Z
Learnt from: CR
Repo: biomejs/biome PR: 0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-12-19T12:53:30.399Z
Learning: Applies to crates/biome_analyze/**/*analyze/src/**/*.rs : Rule documentation code blocks should be ordered as language, expect_diagnostic, options/full_options/use_options, ignore, file

Applied to files:

  • crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs
🧬 Code graph analysis (1)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (4)
crates/biome_service/src/workspace.rs (1)
  • markup (1203-1205)
packages/@biomejs/plugin-api/index.d.ts (1)
  • Severity (1-1)
crates/biome_analyze/src/rule.rs (4)
  • sources (630-633)
  • same (249-254)
  • recommended (615-618)
  • domains (645-648)
crates/biome_service/src/workspace_types.rs (1)
  • Self (748-748)
🪛 LanguageTool
.changeset/social-candies-wave.md

[style] ~6-~6: This phrase is redundant. Consider using “outside”.
Context: .../script's beforeInteractivestrategy outside ofpages/_document.js`.

(OUTSIDE_OF)

⏰ 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). (12)
  • GitHub Check: Lint project (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Check Dependencies
  • GitHub Check: Test (depot-windows-2022-16)
  • GitHub Check: Lint project (depot-windows-2022)
  • GitHub Check: End-to-end tests
  • GitHub Check: Test (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Documentation
  • GitHub Check: autofix
  • GitHub Check: Bench (biome_js_analyze)
  • GitHub Check: Bench (biome_js_parser)
  • GitHub Check: Bench (biome_js_formatter)
  • GitHub Check: Bench (biome_configuration)
🔇 Additional comments (4)
crates/biome_js_analyze/src/lint/nursery/no_before_interactive_script_outside_document.rs (4)

1-13: LGTM!

Imports are well-organised and all appear to be used.


15-66: Well-documented rule.

Clear explanation with good examples. The expect_diagnostic annotation on the invalid example is correct.


84-128: Solid implementation.

The logic correctly handles early exits and properly validates the semantic binding before checking attributes. Good use of is_next_import to ensure we're checking actual next/script imports rather than just any component named Script.


130-140: Clear diagnostic message.

Good use of Emphasis for highlighting key terms and the hyperlink to Next.js documentation is a nice touch.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

A-CLI Area: CLI A-Diagnostic Area: diagnostocis A-Linter Area: linter A-Project Area: project L-JavaScript Language: JavaScript and super languages

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant