Skip to content

Filter non-contextual keyword auto-imports to prevent keyword shadowing#3400

Merged
andrewbranch merged 3 commits intomainfrom
copilot/fix-code-suggestion-issue
Apr 15, 2026
Merged

Filter non-contextual keyword auto-imports to prevent keyword shadowing#3400
andrewbranch merged 3 commits intomainfrom
copilot/fix-code-suggestion-issue

Conversation

Copy link
Copy Markdown
Contributor

Copilot AI commented Apr 14, 2026

Auto-imports with names matching reserved keywords (function, class, const, etc.) were shadowing the keyword completions, preventing users from typing basic language constructs when a module exports a symbol with a keyword name.

// mod.ts
const value = 1;
export { value as function }

// index.ts
function/**/ // ← only showed auto-import "function" from ./mod, not the keyword

Changes

  • internal/ls/completions.go: Skip auto-imports whose names are non-contextual keywords in getCompletionEntriesFromSymbols, matching the isStringANonContextualKeyword filter in TypeScript's collectAutoImports (completions.ts:4179). Contextual keywords like type, abstract, async are unaffected and continue to coexist with auto-imports.

  • internal/fourslash/tests/keywordShadowsAutoImport_test.go: Test verifying that the function keyword completion is present and the auto-import function is excluded, using Includes to match the keyword entry and Excludes to confirm no auto-import with the same name remains.

…adowing

Auto-imports whose names are non-contextual keywords (e.g. `function`,
`class`, `const`) now get filtered out during completion processing,
matching the TypeScript reference implementation behavior. This ensures
that keyword completions are not shadowed by auto-import suggestions
with the same name.

Agent-Logs-Url: https://github.com/microsoft/typescript-go/sessions/ab9b1d54-fb2f-4faa-8093-d6ac10e25fae

Co-authored-by: andrewbranch <3277153+andrewbranch@users.noreply.github.com>
Copilot AI changed the title [WIP] Fix global keywords in code suggestion overshadowed by auto imports Filter non-contextual keyword auto-imports to prevent keyword shadowing Apr 14, 2026
Copilot AI requested a review from andrewbranch April 14, 2026 18:17
f, done := fourslash.NewFourslash(t, nil /*capabilities*/, content)
defer done()
// Both the keyword `type` and the auto-import `type` should appear.
f.VerifyCompletions(t, "", &fourslash.CompletionsExpectedList{
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

This is pretty hard to read. What will this end up being?

mod.type, or just type? The latter is fine, but it doesn't work for function, which is a reserved keyword in value-space.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Removed the contextual keyword test entirely in d60ec53 — it was confusing and the important thing to test is that reserved keywords shadow their auto-imports, which the remaining test covers.

EditRange: Ignored,
},
Items: &fourslash.CompletionsExpectedItems{
Includes: []fourslash.CompletionsExpectedItem{
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

@copilot while you showed that the global is included, you didn't show whether or not the auto-import is excluded. You either need to use Includes and Excludes together or (preferably) just use Exact. Same for the other test.

That said, if you run node internal/fourslash/_scripts/updateFailing.mts and existing failing tests start passing, you can probably just delete this test. I would be surprised if there's not already coverage for this.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Updated the test in d60ec53 to use Includes + Excludes together: Includes matches and consumes the keyword function entry, then Excludes: []string{"function"} verifies no auto-import function item remains. Also removed the confusing type contextual keyword test per Daniel's feedback. Ran updateFailing.mts — no existing tests flipped.

…remove confusing contextual keyword test

Agent-Logs-Url: https://github.com/microsoft/typescript-go/sessions/2c71ae50-e850-4141-a051-0920d522e251

Co-authored-by: andrewbranch <3277153+andrewbranch@users.noreply.github.com>
Copilot AI requested a review from andrewbranch April 14, 2026 20:18
@andrewbranch andrewbranch marked this pull request as ready for review April 14, 2026 20:29
Copilot AI review requested due to automatic review settings April 14, 2026 20:29
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Note

Copilot was unable to run its full agentic suite in this review.

Prevents auto-import completion entries whose names are non-contextual (reserved) keywords from shadowing keyword completions, so users can type language constructs like function without interference.

Changes:

  • Filter auto-import entries by checking whether the symbol name is a non-contextual keyword.
  • Add a fourslash regression test asserting keyword completion is present and conflicting auto-import is excluded.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.

File Description
internal/ls/completions.go Skips auto-import completion entries whose names are non-contextual keywords.
internal/fourslash/tests/keywordShadowsAutoImport_test.go Adds coverage ensuring function keyword completion is not shadowed by an auto-import.

Comment thread internal/fourslash/tests/keywordShadowsAutoImport_test.go
Comment on lines +1897 to +1898
// Non-contextual keywords (e.g., `function`, `class`, `const`) cannot be used as identifiers,
// so auto-imports with these names should not shadow keyword completions.
Copy link

Copilot AI Apr 14, 2026

Choose a reason for hiding this comment

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

The comment is a bit imprecise given the example in the PR description/export syntax: these keywords can appear as IdentifierName in some syntactic positions (e.g., export specifiers, object properties), but they cannot be used as binding identifiers (e.g., import { function } ... is invalid). Consider rewording to “cannot be used as binding identifiers (such as in import specifiers)” to match the actual reason for filtering.

Suggested change
// Non-contextual keywords (e.g., `function`, `class`, `const`) cannot be used as identifiers,
// so auto-imports with these names should not shadow keyword completions.
// Non-contextual keywords (e.g., `function`, `class`, `const`) cannot be used as binding identifiers
// (such as in import specifiers), so auto-imports with these names should not shadow keyword completions.

Copilot uses AI. Check for mistakes.
@andrewbranch andrewbranch enabled auto-merge April 14, 2026 22:03
@andrewbranch andrewbranch added this pull request to the merge queue Apr 14, 2026
Merged via the queue into main with commit 7cc3325 Apr 15, 2026
25 checks passed
@andrewbranch andrewbranch deleted the copilot/fix-code-suggestion-issue branch April 15, 2026 03:51
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Global keywords in code suggestion shadowed by auto imports with same name

4 participants