Skip to content

feat(lint): add nursery rule useImportsFirst#9272

Open
terror wants to merge 1 commit intobiomejs:mainfrom
terror:use-imports-first
Open

feat(lint): add nursery rule useImportsFirst#9272
terror wants to merge 1 commit intobiomejs:mainfrom
terror:use-imports-first

Conversation

@terror
Copy link

@terror terror commented Feb 28, 2026

Resolves #9265

This diff implements the useImportsFirst lint rule, which enforces that all import statements appear before any non-import statements in a module. This corresponds to the ESLint import/first rule (see #9265). The rule iterates over the module item list and flags any JsImport that appears after a non-import item.

@changeset-bot
Copy link

changeset-bot bot commented Feb 28, 2026

⚠️ No Changeset found

Latest commit: c6d9702

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@github-actions github-actions bot added A-Project Area: project A-Linter Area: linter L-JavaScript Language: JavaScript and super languages A-Diagnostic Area: diagnostocis labels Feb 28, 2026
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 28, 2026

Walkthrough

A new linting rule UseImportsFirst has been added to enforce import statements appearing exclusively at the top of JavaScript modules. The implementation includes the rule logic in the nursery lint rules, an empty options struct for configuration, and test files covering valid and invalid scenarios (imports interleaved with code, imports with exports, and standard import-first patterns). The rule is registered as a non-recommended ESLint-compatible lint rule aligned with the eslint-plugin-import source.

Suggested labels

A-Linter, L-JavaScript, A-Diagnostic, A-CLI

Suggested reviewers

  • ematipico
  • dyc3
  • Netail
🚥 Pre-merge checks | ✅ 4
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title 'feat(lint): add nursery rule useImportsFirst' accurately summarises the main change: introducing a new lint rule in the nursery category.
Linked Issues check ✅ Passed All code changes implement the stated objective from #9265: a lint rule enforcing imports at the top of modules, matching ESLint's import/first behaviour.
Out of Scope Changes check ✅ Passed All changes are directly related to implementing the useImportsFirst rule: rule implementation, test files, and configuration options. No extraneous modifications detected.
Description check ✅ Passed The PR description accurately describes the implementation of the useImportsFirst lint rule and its purpose, directly relating to the changeset.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ 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 (1)
crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/valid.js (1)

1-5: Optional: add a directive-focused valid fixture.

Given the rule docs explicitly allow directives, a tiny valid_with_directive.js (e.g. "use strict"; then imports) would lock that behaviour in and guard regressions.

Based on learnings: Add tests for all code changes - lint rules need snapshot tests in tests/specs/{group}/{rule}/.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/valid.js` around
lines 1 - 5, Add a new valid fixture file (e.g., valid_with_directive.js) under
tests/specs/nursery/useImportsFirst/ that begins with a directive like "use
strict"; followed by the same import lines (import { foo } from "foo"; import {
bar } from "bar"; import { baz } from "baz"; const qux = 1;) and the same top
comment ("should not generate diagnostics") so the test suite captures that
directives are allowed by the useImportsFirst rule; ensure the file follows the
existing snapshot test pattern used in tests/specs/{group}/{rule}/ so it is
picked up by the rule tests.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@crates/biome_rule_options/src/use_imports_first.rs`:
- Line 6: Add a rustdoc comment above the public struct UseImportsFirstOptions
explaining what this options type configures (options for the
"use-imports-first" rule/assist), what each field would control (if currently
empty, state that it has no configurable fields yet and is reserved for future
settings), and include example usage or default behavior; ensure the doc uses
standard /// rustdoc format placed immediately before the declaration of
UseImportsFirstOptions.

---

Nitpick comments:
In `@crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/valid.js`:
- Around line 1-5: Add a new valid fixture file (e.g., valid_with_directive.js)
under tests/specs/nursery/useImportsFirst/ that begins with a directive like
"use strict"; followed by the same import lines (import { foo } from "foo";
import { bar } from "bar"; import { baz } from "baz"; const qux = 1;) and the
same top comment ("should not generate diagnostics") so the test suite captures
that directives are allowed by the useImportsFirst rule; ensure the file follows
the existing snapshot test pattern used in tests/specs/{group}/{rule}/ so it is
picked up by the rule tests.

ℹ️ Review info

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 412a08d and c6d9702.

⛔ Files ignored due to path filters (7)
  • crates/biome_configuration/src/analyzer/linter/rules.rs is excluded by !**/rules.rs and included by **
  • crates/biome_diagnostics_categories/src/categories.rs is excluded by !**/categories.rs and included by **
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/invalid.js.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/invalid_mixed.js.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/valid.js.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/valid_with_export.js.snap is excluded by !**/*.snap and included by **
  • packages/@biomejs/biome/configuration_schema.json is excluded by !**/configuration_schema.json and included by **
📒 Files selected for processing (7)
  • crates/biome_js_analyze/src/lint/nursery/use_imports_first.rs
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/invalid.js
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/invalid_mixed.js
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/valid.js
  • crates/biome_js_analyze/tests/specs/nursery/useImportsFirst/valid_with_export.js
  • crates/biome_rule_options/src/lib.rs
  • crates/biome_rule_options/src/use_imports_first.rs

#[derive(Default, Clone, Debug, Deserialize, Deserializable, Merge, Eq, PartialEq, Serialize)]
#[cfg_attr(feature = "schema", derive(schemars::JsonSchema))]
#[serde(rename_all = "camelCase", deny_unknown_fields, default)]
pub struct UseImportsFirstOptions {}
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Please add rustdoc for the public options type.

Line 6 introduces UseImportsFirstOptions without inline docs; a brief rustdoc block keeps generated docs clear for users.

Suggested patch
+/// Options for the `useImportsFirst` rule.
+///
+/// This rule currently has no configurable options.
 pub struct UseImportsFirstOptions {}

As per coding guidelines: **/*.rs: Use inline rustdoc documentation for rules, assists, and their options.

📝 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 struct UseImportsFirstOptions {}
/// Options for the `useImportsFirst` rule.
///
/// This rule currently has no configurable options.
pub struct UseImportsFirstOptions {}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@crates/biome_rule_options/src/use_imports_first.rs` at line 6, Add a rustdoc
comment above the public struct UseImportsFirstOptions explaining what this
options type configures (options for the "use-imports-first" rule/assist), what
each field would control (if currently empty, state that it has no configurable
fields yet and is reserved for future settings), and include example usage or
default behavior; ensure the doc uses standard /// rustdoc format placed
immediately before the declaration of UseImportsFirstOptions.

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

Labels

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.

📎 Implement rule to enforce all imports go at the top of the file

1 participant