+
Skip to content

Conversation

arendjr
Copy link
Contributor

@arendjr arendjr commented Sep 26, 2025

Summary

Fixed #6432: useImportExtensions now works correctly with aliased paths.

Also fixed an issue where package.json manifests would not be correctly discovered when evaluating files in the same directory.

Test Plan

Tests added.

Docs

N/A

Copy link

changeset-bot bot commented Sep 26, 2025

🦋 Changeset detected

Latest commit: a5d398e

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

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

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

@arendjr arendjr changed the title fix(linter): fix aliased paths in useImportExtensions fix(linter): fix aliased paths in useImportExtensions Sep 26, 2025
@github-actions github-actions bot added A-Project Area: project A-Linter Area: linter L-JavaScript Language: JavaScript and super languages labels Sep 26, 2025
Copy link
Contributor

coderabbitai bot commented Sep 26, 2025

Walkthrough

The use_import_extensions rule now consults TS config path aliases via RuleContext to decide on extension handling for non-relative imports. ModuleGraphService now stores both ModuleGraph and ProjectLayout and exposes project_layout(). ProjectLayout gained insert_tsconfig and query_tsconfig_for_path, and manifest/tsconfig discovery behaviour was adjusted. Test utilities renamed to project_layout_for_test_file and now load package.json and tsconfig.json. New tests cover path alias imports and npm package imports; a .gitignore exception for node_modules was added. Watcher tests now sleep unconditionally across platforms. Changesets document two patch fixes: alias handling and manifest discovery.

Possibly related PRs

Suggested labels

A-Linter, A-Resolver, A-Project

Suggested reviewers

  • siketyan
  • ematipico

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Out of Scope Changes Check ⚠️ Warning The unconditional sleep introduced in the scanner watcher tests is unrelated to the linter alias or package.json discovery fixes and falls outside the scope of issue #6432. Please revert or isolate the unrelated test timing changes into a separate PR so this one remains focused on the linter and manifest discovery fixes.
✅ Passed checks (4 passed)
Check name Status Explanation
Title Check ✅ Passed The title clearly identifies the primary fix to the linter rule’s handling of aliased paths in useImportExtensions, matching the main change in the PR.
Linked Issues Check ✅ Passed The implementation adds TS config alias support to the useImportExtensions rule and includes tests that cover aliased imports, fully satisfying the objectives of issue #6432.
Description Check ✅ Passed The description succinctly outlines the two key fixes and notes the added tests, directly reflecting the changes in the PR.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
✨ Finishing touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Tip

👮 Agentic pre-merge checks are now available in preview!

Pro plan users can now enable pre-merge checks in their settings to enforce checklists before merging PRs.

  • Built-in checks – Quickly apply ready-made checks to enforce title conventions, require pull request descriptions that follow templates, validate linked issues for compliance, and more.
  • Custom agentic checks – Define your own rules using CodeRabbit’s advanced agentic capabilities to enforce organization-specific policies and workflows. For example, you can instruct CodeRabbit’s agent to verify that API documentation is updated whenever API schema files are modified in a PR. Note: Upto 5 custom checks are currently allowed during the preview period. Pricing for this feature will be announced in a few weeks.

Please see the documentation for more information.

Example:

reviews:
  pre_merge_checks:
    custom_checks:
      - name: "Undocumented Breaking Changes"
        mode: "warning"
        instructions: |
          Pass/fail criteria: All breaking changes to public APIs, CLI flags, environment variables, configuration keys, database schemas, or HTTP/GraphQL endpoints must be documented in the "Breaking Change" section of the PR description and in CHANGELOG.md. Exclude purely internal or private changes (e.g., code not exported from package entry points or explicitly marked as internal).

Please share your feedback with us on this Discord post.


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

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
crates/biome_js_analyze/src/lint/correctness/use_import_extensions.rs (1)

236-244: Bug: reversed filename check causes false positives for sub-extensions

The guard intended to skip cases like "./foo.css" resolving to "./foo.css.ts" is inverted. It compares import starts_with resolved, which is never true. Reverse the check.

Apply this diff:

-        (Some(_), _) if path.file_name()?.starts_with(resolved_path.file_name()?) => {
+        (Some(_), _) if resolved_path.file_name()?.starts_with(path.file_name()?) => {
             return None; // For cases like `./foo.css` -> `./foo.css.ts`
         }
🧹 Nitpick comments (3)
crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.tsconfig.json (1)

2-5: TS path alias looks good; consider baseUrl if you want TS parity.

For alias detection this is fine. If you later aim to mirror TypeScript resolution semantics, you may want to add "baseUrl": "." under compilerOptions. Optional for these tests.

.changeset/packaged-parcels-ponder.md (1)

5-6: Add an issue link if one exists.

Guidelines prefer bug-fix entries to start with an issue link (e.g., “Fixed #1234: …”). If there’s no issue, ignore me and carry on.

As per coding guidelines

crates/biome_js_analyze/src/services/module_graph.rs (1)

12-25: Exposing ProjectLayout via ModuleGraphService looks good

Carrying ProjectLayout alongside ModuleGraph unlocks alias-aware rules cleanly. Tuple struct access via .0/.1 is fine; consider named fields later for readability.

📜 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 f18dac1 and a5d398e.

⛔ Files ignored due to path filters (4)
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.ts.snap is excluded by !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/node_modules/lodash/index.js is excluded by !**/node_modules/** and included by **
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/node_modules/lodash/index.js.snap is excluded by !**/node_modules/**, !**/*.snap and included by **
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/validNpmPackage.ts.snap is excluded by !**/*.snap and included by **
📒 Files selected for processing (14)
  • .changeset/aliased-angels-ascend.md (1 hunks)
  • .changeset/packaged-parcels-ponder.md (1 hunks)
  • crates/biome_js_analyze/src/lint/correctness/use_import_extensions.rs (4 hunks)
  • crates/biome_js_analyze/src/services/module_graph.rs (3 hunks)
  • crates/biome_js_analyze/tests/spec_tests.rs (2 hunks)
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/.gitignore (1 hunks)
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.package.json (1 hunks)
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.ts (1 hunks)
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.tsconfig.json (1 hunks)
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/validNpmPackage.ts (1 hunks)
  • crates/biome_package/src/node_js_package/tsconfig_json.rs (1 hunks)
  • crates/biome_project_layout/src/project_layout.rs (5 hunks)
  • crates/biome_service/src/scanner/watcher.tests.rs (0 hunks)
  • crates/biome_test_utils/src/lib.rs (3 hunks)
💤 Files with no reviewable changes (1)
  • crates/biome_service/src/scanner/watcher.tests.rs
🧰 Additional context used
📓 Path-based instructions (5)
crates/biome_*_{syntax,parser,formatter,analyze,factory,semantic}/**

📄 CodeRabbit inference engine (CLAUDE.md)

Maintain the per-language crate structure: biome_{lang}_{syntax,parser,formatter,analyze,factory,semantic}

Files:

  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.tsconfig.json
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.package.json
  • crates/biome_js_analyze/src/services/module_graph.rs
  • crates/biome_js_analyze/tests/spec_tests.rs
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/validNpmPackage.ts
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.ts
  • crates/biome_js_analyze/src/lint/correctness/use_import_extensions.rs
crates/biome_*/**

📄 CodeRabbit inference engine (CLAUDE.md)

Place core crates under /crates/biome_*/

Files:

  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.tsconfig.json
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.package.json
  • crates/biome_package/src/node_js_package/tsconfig_json.rs
  • crates/biome_js_analyze/src/services/module_graph.rs
  • crates/biome_js_analyze/tests/spec_tests.rs
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/validNpmPackage.ts
  • crates/biome_test_utils/src/lib.rs
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.ts
  • crates/biome_js_analyze/src/lint/correctness/use_import_extensions.rs
  • crates/biome_project_layout/src/project_layout.rs
**/tests/**

📄 CodeRabbit inference engine (CLAUDE.md)

Place test files under a tests/ directory in each crate

Files:

  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.tsconfig.json
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.package.json
  • crates/biome_js_analyze/tests/spec_tests.rs
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/validNpmPackage.ts
  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.ts
**/*.rs

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Format all Rust source files before committing (just f)

Files:

  • crates/biome_package/src/node_js_package/tsconfig_json.rs
  • crates/biome_js_analyze/src/services/module_graph.rs
  • crates/biome_js_analyze/tests/spec_tests.rs
  • crates/biome_test_utils/src/lib.rs
  • crates/biome_js_analyze/src/lint/correctness/use_import_extensions.rs
  • crates/biome_project_layout/src/project_layout.rs
.changeset/*.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

.changeset/*.md: In changeset files, only use #### or ##### headers; avoid other header levels
Changeset descriptions should use past tense for what you did (e.g., "Added...")
Describe current Biome behavior in present tense within changesets (e.g., "Biome now supports...")
For bug fixes in changesets, start with a link to the issue (e.g., "Fixed #1234: ...")
When referencing rules or assists in changesets, include links to their documentation pages
Include a minimal code block in the changeset when applicable to demonstrate the change
End every sentence in the changeset description with a period

Files:

  • .changeset/packaged-parcels-ponder.md
  • .changeset/aliased-angels-ascend.md
🧠 Learnings (19)
📓 Common learnings
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_service/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:53:15.299Z
Learning: Use the `noImportCycles` rule to observe project layout and module graph state during debugging
📚 Learning: 2025-09-10T08:05:22.867Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-09-10T08:05:22.867Z
Learning: Applies to crates/biome_analyze/crates/**/tests/specs/**/*.jsonc : Snapshot test `.jsonc` files must contain an array of code snippets (strings); these run in script mode (no ESM syntax)

Applied to files:

  • crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.tsconfig.json
📚 Learning: 2025-08-11T11:50:12.090Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:50:12.090Z
Learning: Applies to crates/biome_js_type_info/biome_module_graph/src/**/*.rs : In the module graph, no module may copy or clone data from another module, not even behind Arc; entries must not depend on each other’s data

Applied to files:

  • crates/biome_js_analyze/src/services/module_graph.rs
📚 Learning: 2025-09-10T08:05:22.867Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-09-10T08:05:22.867Z
Learning: Applies to crates/biome_analyze/crates/biome_js_analyze/tests/quick_test.rs : Quick test: edit `tests/quick_test.rs`, remove or comment `#[ignore]`, set `SOURCE`, and adjust `RuleFilter`

Applied to files:

  • crates/biome_js_analyze/tests/spec_tests.rs
📚 Learning: 2025-08-17T08:55:30.118Z
Learnt from: CR
PR: biomejs/biome#0
File: CLAUDE.md:0-0
Timestamp: 2025-08-17T08:55:30.118Z
Learning: Applies to **/tests/specs/**/*.snap : Use snapshot spec tests stored as .snap files under tests/specs/ (via cargo insta)

Applied to files:

  • crates/biome_js_analyze/tests/spec_tests.rs
📚 Learning: 2025-08-11T11:48:27.774Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:48:27.774Z
Learning: Applies to crates/biome_formatter/biome_html_formatter/tests/spec_test.rs : Create tests/spec_test.rs implementing the run(spec_input_file, _expected_file, test_directory, _file_type) function as shown and include!("language.rs")

Applied to files:

  • crates/biome_js_analyze/tests/spec_tests.rs
  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-09-10T08:05:22.867Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_analyze/CONTRIBUTING.md:0-0
Timestamp: 2025-09-10T08:05:22.867Z
Learning: Applies to crates/biome_analyze/crates/biome_js_analyze/lib/src/{lint,assist}/**/*.rs : When banning globals (e.g., `noConsoleLog`), check the semantic model to avoid false positives from locally shadowed bindings

Applied to files:

  • crates/biome_js_analyze/tests/spec_tests.rs
📚 Learning: 2025-08-11T11:48:27.774Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:48:27.774Z
Learning: Applies to crates/biome_formatter/biome_html_formatter/tests/spec_tests.rs : Create tests/spec_tests.rs in the biome_html_formatter crate that generates tests via tests_macros::gen_tests! for all HTML files at tests/specs/html/**/*.html

Applied to files:

  • crates/biome_js_analyze/tests/spec_tests.rs
📚 Learning: 2025-08-11T11:53:15.299Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_service/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:53:15.299Z
Learning: Applies to crates/biome_service/src/workspace/watcher.tests.rs : Place watcher tests for workspace methods in src/workspace/watcher.tests.rs

Applied to files:

  • crates/biome_js_analyze/tests/spec_tests.rs
📚 Learning: 2025-08-11T11:53:15.299Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_service/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:53:15.299Z
Learning: Applies to crates/biome_service/../biome_lsp/src/server.tests.rs : Keep end-to-end LSP tests in biome_lsp’s server.tests.rs

Applied to files:

  • crates/biome_js_analyze/tests/spec_tests.rs
  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-09-07T17:35:00.517Z
Learnt from: CR
PR: biomejs/biome#0
File: CONTRIBUTING.md:0-0
Timestamp: 2025-09-07T17:35:00.517Z
Learning: Applies to .changeset/*.md : Describe current Biome behavior in present tense within changesets (e.g., "Biome now supports...")

Applied to files:

  • .changeset/packaged-parcels-ponder.md
📚 Learning: 2025-08-11T11:46:05.836Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_diagnostics/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:46:05.836Z
Learning: Applies to crates/biome_diagnostics/**/*.rs : Use helper advice types from biome_diagnostics::v2 (CodeFrameAdvice, CommandAdvice, DiffAdvice, LogAdvice) when suitable

Applied to files:

  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-08-11T11:48:52.001Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:48:52.001Z
Learning: Applies to crates/biome_js_formatter/**/Cargo.toml : Add biome_js_formatter as a path dependency in Cargo.toml: biome_js_formatter = { version = "0.0.1", path = "../biome_js_formatter" }

Applied to files:

  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-08-11T11:50:12.090Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:50:12.090Z
Learning: Applies to crates/biome_js_type_info/{src,resolver,biome_module_graph/src}/**/*.rs : Implement and use type resolution via the TypeResolver trait; resolvers own TypeStore vectors and provide fast by-id and hashed lookups

Applied to files:

  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-08-11T11:50:12.090Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:50:12.090Z
Learning: Applies to crates/biome_js_type_info/{src,biome_module_graph/src}/**/*.rs : When pattern-matching on ResolvedTypeData via as_raw_data(), ensure any nested TypeReferences are subsequently resolved using the correct ResolverId; never use the raw data with a resolver without applying the right ResolverId to avoid panics

Applied to files:

  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-08-11T11:50:12.090Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:50:12.090Z
Learning: Applies to crates/biome_js_type_info/src/**/*.rs : Represent links between types using TypeReference (not Arc) to avoid cross-module retention and recursive structures; store type data in linear vectors

Applied to files:

  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-08-11T11:48:52.001Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_js_formatter/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:48:52.001Z
Learning: Applies to crates/biome_js_formatter/**/*.rs : Import the FormatNode trait and implement it for your Node

Applied to files:

  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-08-11T11:50:12.090Z
Learnt from: CR
PR: biomejs/biome#0
File: crates/biome_js_type_info/CONTRIBUTING.md:0-0
Timestamp: 2025-08-11T11:50:12.090Z
Learning: Applies to crates/biome_js_type_info/src/**/*.rs : Use TypeData::Unknown for unimplemented inference and TypeData::UnknownKeyword for the explicit TypeScript unknown keyword; treat them semantically the same but keep them distinct for measurement

Applied to files:

  • crates/biome_test_utils/src/lib.rs
📚 Learning: 2025-08-20T16:24:59.781Z
Learnt from: arendjr
PR: biomejs/biome#7266
File: crates/biome_js_type_info/src/type.rs:94-102
Timestamp: 2025-08-20T16:24:59.781Z
Learning: In crates/biome_js_type_info/src/type.rs, the flattened_union_variants() method returns TypeReference instances that already have the correct module IDs applied to them. These references should be used directly with resolver.resolve_reference() without applying additional module ID transformations, as variant references may originate from nested unions in different modules.

Applied to files:

  • crates/biome_test_utils/src/lib.rs
🧬 Code graph analysis (3)
crates/biome_js_analyze/tests/spec_tests.rs (1)
crates/biome_test_utils/src/lib.rs (1)
  • project_layout_for_test_file (206-273)
crates/biome_test_utils/src/lib.rs (3)
crates/biome_service/src/file_handlers/json.rs (1)
  • deserialized (535-539)
crates/biome_package/src/node_js_package/package_json.rs (1)
  • deserialize_from_json_str (368-368)
crates/biome_service/src/file_handlers/mod.rs (5)
  • new (502-515)
  • new (703-717)
  • new (972-990)
  • new (1261-1275)
  • new (1396-1406)
crates/biome_project_layout/src/project_layout.rs (1)
crates/biome_package/src/node_js_package/mod.rs (1)
  • manifest (59-61)
⏰ 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). (25)
  • GitHub Check: Lint project (depot-ubuntu-24.04-arm-16)
  • GitHub Check: End-to-end tests
  • GitHub Check: Lint project (depot-windows-2022)
  • GitHub Check: Test (depot-windows-2022-16)
  • GitHub Check: Test (depot-ubuntu-24.04-arm-16)
  • GitHub Check: Check Dependencies
  • GitHub Check: Documentation
  • GitHub Check: Bench (biome_html_parser)
  • GitHub Check: Bench (biome_graphql_formatter)
  • GitHub Check: Bench (biome_module_graph)
  • GitHub Check: Bench (biome_configuration)
  • GitHub Check: Bench (biome_package)
  • GitHub Check: Bench (biome_html_formatter)
  • GitHub Check: Bench (biome_js_analyze)
  • GitHub Check: Bench (biome_json_analyze)
  • GitHub Check: Bench (biome_css_parser)
  • GitHub Check: Bench (biome_json_parser)
  • GitHub Check: Bench (biome_graphql_parser)
  • GitHub Check: Bench (biome_json_formatter)
  • GitHub Check: Bench (biome_css_analyze)
  • GitHub Check: Bench (biome_css_formatter)
  • GitHub Check: Bench (biome_js_formatter)
  • GitHub Check: Bench (biome_js_parser)
  • GitHub Check: Test Node.js API
  • GitHub Check: autofix
🔇 Additional comments (18)
crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/.gitignore (1)

1-1: All good on the fixture override. Letting that local node_modules slip past the global ignore keeps the alias tests honest. No worries here.

.changeset/aliased-angels-ascend.md (1)

5-5: Changeset reads well.

Clear bug reference and rule link; sentence ends cleanly. Ship it.

crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.package.json (1)

1-1: Empty manifest is fine for the test harness.

This will deserialize to defaults and won’t force CJS mode. All good.

crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/invalidWithPathAlias.ts (1)

3-5: Good coverage for aliased imports.

Both imports should trigger the rule under the provided alias. Looks spot on.

crates/biome_js_analyze/tests/spec_tests.rs (2)

18-19: Switched to project_layout_for_test_file — good move.

Aligns with the new test utility API and tsconfig/package discovery.


170-193: Plumbs project layout into module graph and services correctly.

  • Layout created once and reused.
  • CJS manifest check preserved.
  • Services now receive (module_graph, project_layout, source_type). All consistent with the new service shape.
crates/biome_js_analyze/src/lint/correctness/use_import_extensions.rs (4)

150-151: Plumbing ctx into get_extensionless_import is correct

This enables alias-aware gating without widening the rule’s surface area elsewhere.


200-205: Signature change is appropriate

Passing RuleContext allows local tsconfig alias checks without global state.


212-227: Sensible gating on TS path aliases

Non-relative specifiers now only trigger when they match a tsconfig path alias; npm/bare specifiers are excluded. This aligns with the issue’s expectation.

Please confirm matches_path_alias handles wildcard patterns and prefix segments as expected (e.g., "@lib/*" matching "@lib/foo/bar").


304-306: Minor: avoid intermediate String in set_extension

format! allocates; micro-optimisation isn’t necessary here. Safe to keep as-is given infrequent use in lint actions.

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

206-273: Great test helper: loads both package.json and tsconfig.json

Initialising ProjectLayout with both manifests mirrors real projects and enables alias-aware tests. Error-to-string handling is consistent with existing utilities.

crates/biome_project_layout/src/project_layout.rs (5)

50-57: Manifest discovery now includes current directory

Including the starting path fixes same-directory lookups as advertised. Nice.


95-119: insert_node_manifest preserves existing tsconfig

Good state merge, avoids losing tsconfig when manifests arrive in different orders.


122-155: insert_tsconfig mirrors insert_node_manifest

Symmetric API is clear and keeps node_package coherent. No concerns.


170-171: Deserialised-insert keeps existing tsconfig via and_then

Subtle improvement: avoids injecting defaults when none exist.


241-259: query_tsconfig_for_path is a neat primitive

Clean ancestor search with functional query; perfect for alias checks.

crates/biome_js_analyze/src/services/module_graph.rs (1)

49-54: All JsAnalyzerServices::from calls include ProjectLayout Verified every initialization path supplies project_layout.

crates/biome_js_analyze/tests/specs/correctness/useImportExtensions/validNpmPackage.ts (1)

1-3: No lint sniffles here

Fixture does exactly what's needed for the npm package sanity check. Cheers.

Comment on lines +86 to +96
/// Returns whether the given `path` matches a configured path alias.
pub fn matches_path_alias(&self, path: &str) -> bool {
self.compiler_options.paths.as_ref().is_some_and(|paths| {
paths
.keys()
.any(|alias_path| match alias_path.split_once('*') {
Some((before, after)) => path.starts_with(before) && path.ends_with(after),
None => path == alias_path,
})
})
}
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 | 🟠 Major

Catch‑all '*' alias will match everything — likely too broad.

With a key "*" in paths, this returns true for any specifier, which can misclassify package imports (e.g., "lodash") as aliased and skew useImportExtensions behaviour. Let’s ignore the pure catch‑all to avoid disabling the rule across projects that use it.

Apply this diff to treat "*" as non‑specific and skip it:

-    /// Returns whether the given `path` matches a configured path alias.
-    pub fn matches_path_alias(&self, path: &str) -> bool {
+    /// Returns whether the given `path` matches a configured, non catch‑all path alias.
+    /// Note: ignores a pure `"*"` alias to avoid over‑matching.
+    pub fn matches_path_alias(&self, path: &str) -> bool {
         self.compiler_options.paths.as_ref().is_some_and(|paths| {
             paths
                 .keys()
-                .any(|alias_path| match alias_path.split_once('*') {
-                    Some((before, after)) => path.starts_with(before) && path.ends_with(after),
-                    None => path == alias_path,
-                })
+                .any(|alias_path| match alias_path.split_once('*') {
+                    Some((before, after)) => {
+                        // Ignore catch‑all "*"
+                        if before.is_empty() && after.is_empty() {
+                            return false;
+                        }
+                        path.starts_with(before) && path.ends_with(after)
+                    }
+                    None => path == alias_path,
+                })
         })
     }
📝 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
/// Returns whether the given `path` matches a configured path alias.
pub fn matches_path_alias(&self, path: &str) -> bool {
self.compiler_options.paths.as_ref().is_some_and(|paths| {
paths
.keys()
.any(|alias_path| match alias_path.split_once('*') {
Some((before, after)) => path.starts_with(before) && path.ends_with(after),
None => path == alias_path,
})
})
}
/// Returns whether the given `path` matches a configured, non catch-all path alias.
/// Note: ignores a pure `"*"` alias to avoid over-matching.
pub fn matches_path_alias(&self, path: &str) -> bool {
self.compiler_options.paths.as_ref().is_some_and(|paths| {
paths
.keys()
.any(|alias_path| match alias_path.split_once('*') {
Some((before, after)) => {
// Ignore catch-all "*"
if before.is_empty() && after.is_empty() {
return false;
}
path.starts_with(before) && path.ends_with(after)
}
None => path == alias_path,
})
})
}
🤖 Prompt for AI Agents
In crates/biome_package/src/node_js_package/tsconfig_json.rs around lines 86 to
96, the current matches_path_alias treats a catch‑all alias key "*" as matching
any path; update the function to ignore the exact "*" key so it doesn't count as
a specific alias. Keep the existing wildcard logic (split_once('*') branch and
exact match branch) but skip any alias_path that is exactly "*" (e.g., by
filtering alias keys or adding a guard inside the any closure) so pure catch‑all
entries do not make the function return true for every specifier.

Copy link

codspeed-hq bot commented Sep 26, 2025

CodSpeed Performance Report

Merging #7597 will improve performances by 6.26%

Comparing arendjr:fix-aliased-paths-in-useImportExtensions (a5d398e) with main (f18dac1)

Summary

⚡ 1 improvement
✅ 132 untouched

Benchmarks breakdown

Benchmark BASE HEAD Change
json_analyzer[big5-added_15586211152145260264.json] 461.4 µs 434.2 µs +6.26%

@arendjr arendjr merged commit 5c3d542 into biomejs:main Sep 26, 2025
31 checks passed
@github-actions github-actions bot mentioned this pull request Sep 26, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

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.

💅 useImportExtension doesn't flag or flix missing extension in alias

1 participant

点击 这是indexloc提供的php浏览器服务,不要输入任何密码和下载