Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 11 additions & 10 deletions src/compiler/parser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4562,16 +4562,17 @@ namespace Parser {
else {
parseErrorAtCurrentToken(Diagnostics._0_expected, tokenToString(SyntaxKind.WithKeyword));
}
parseExpected(SyntaxKind.ColonToken);
attributes = parseImportAttributes(currentToken as SyntaxKind.WithKeyword | SyntaxKind.AssertKeyword, /*skipKeyword*/ true);
if (!parseExpected(SyntaxKind.CloseBraceToken)) {
const lastError = lastOrUndefined(parseDiagnostics);
if (lastError && lastError.code === Diagnostics._0_expected.code) {
addRelatedInfo(
lastError,
createDetachedDiagnostic(fileName, sourceText, openBracePosition, 1, Diagnostics.The_parser_expected_to_find_a_1_to_match_the_0_token_here, "{", "}"),
);
}
parseExpected(SyntaxKind.ColonToken);
attributes = parseImportAttributes(currentToken as SyntaxKind.WithKeyword | SyntaxKind.AssertKeyword, /*skipKeyword*/ true);
parseOptional(SyntaxKind.CommaToken); // Allow trailing comma after import attributes
if (!parseExpected(SyntaxKind.CloseBraceToken)) {
const lastError = lastOrUndefined(parseDiagnostics);
if (lastError && lastError.code === Diagnostics._0_expected.code) {
addRelatedInfo(
lastError,
createDetachedDiagnostic(fileName, sourceText, openBracePosition, 1, Diagnostics.The_parser_expected_to_find_a_1_to_match_the_0_token_here, "{", "}"),
);
}
}
}
parseExpected(SyntaxKind.CloseParenToken);
Expand Down
44 changes: 44 additions & 0 deletions tests/baselines/reference/importTypeTrailingComma.errors.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
importTypeTrailingComma.ts(5,17): error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?
importTypeTrailingComma.ts(8,17): error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?
importTypeTrailingComma.ts(11,17): error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?
importTypeTrailingComma.ts(14,17): error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?
importTypeTrailingComma.ts(17,24): error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?
importTypeTrailingComma.ts(20,17): error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?
importTypeTrailingComma.ts(20,42): error TS1464: Type import attributes should have exactly one key - 'resolution-mode' - with value 'import' or 'require'.


==== importTypeTrailingComma.ts (7 errors) ====
// Test that trailing commas are allowed in import type attributes
// This should work consistently with dynamic imports

// Trailing comma inside with object (already worked)
type A = import("./nonexistent", { with: { type: "json", } })
~~~~~~~~~~~~~~~
!!! error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?

// Trailing comma after with object (this is the fix)
type B = import("./nonexistent", { with: { type: "json" }, })
~~~~~~~~~~~~~~~
!!! error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?

// No trailing comma for comparison
type C = import("./nonexistent", { with: { type: "json" } })
~~~~~~~~~~~~~~~
!!! error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?

// Assert syntax with trailing comma
type D = import("./nonexistent", { assert: { type: "json" }, })
~~~~~~~~~~~~~~~
!!! error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?

// typeof with trailing comma
type E = typeof import("./nonexistent", { with: { type: "json" }, })
~~~~~~~~~~~~~~~
!!! error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?

// Multiple properties in with object with trailing comma after
type F = import("./nonexistent", { with: { type: "json", "resolution-mode": "import" }, })
~~~~~~~~~~~~~~~
!!! error TS2792: Cannot find module './nonexistent'. Did you mean to set the 'moduleResolution' option to 'nodenext', or to add aliases to the 'paths' option?
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
!!! error TS1464: Type import attributes should have exactly one key - 'resolution-mode' - with value 'import' or 'require'.
27 changes: 27 additions & 0 deletions tests/baselines/reference/importTypeTrailingComma.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
//// [tests/cases/compiler/importTypeTrailingComma.ts] ////

//// [importTypeTrailingComma.ts]
// Test that trailing commas are allowed in import type attributes
// This should work consistently with dynamic imports

// Trailing comma inside with object (already worked)
type A = import("./nonexistent", { with: { type: "json", } })

// Trailing comma after with object (this is the fix)
type B = import("./nonexistent", { with: { type: "json" }, })

// No trailing comma for comparison
type C = import("./nonexistent", { with: { type: "json" } })

// Assert syntax with trailing comma
type D = import("./nonexistent", { assert: { type: "json" }, })

// typeof with trailing comma
type E = typeof import("./nonexistent", { with: { type: "json" }, })

// Multiple properties in with object with trailing comma after
type F = import("./nonexistent", { with: { type: "json", "resolution-mode": "import" }, })

//// [importTypeTrailingComma.js]
// Test that trailing commas are allowed in import type attributes
// This should work consistently with dynamic imports
30 changes: 30 additions & 0 deletions tests/baselines/reference/importTypeTrailingComma.symbols
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
//// [tests/cases/compiler/importTypeTrailingComma.ts] ////

=== importTypeTrailingComma.ts ===
// Test that trailing commas are allowed in import type attributes
// This should work consistently with dynamic imports

// Trailing comma inside with object (already worked)
type A = import("./nonexistent", { with: { type: "json", } })
>A : Symbol(A, Decl(importTypeTrailingComma.ts, 0, 0))

// Trailing comma after with object (this is the fix)
type B = import("./nonexistent", { with: { type: "json" }, })
>B : Symbol(B, Decl(importTypeTrailingComma.ts, 4, 61))

// No trailing comma for comparison
type C = import("./nonexistent", { with: { type: "json" } })
>C : Symbol(C, Decl(importTypeTrailingComma.ts, 7, 61))

// Assert syntax with trailing comma
type D = import("./nonexistent", { assert: { type: "json" }, })
>D : Symbol(D, Decl(importTypeTrailingComma.ts, 10, 60))

// typeof with trailing comma
type E = typeof import("./nonexistent", { with: { type: "json" }, })
>E : Symbol(E, Decl(importTypeTrailingComma.ts, 13, 63))

// Multiple properties in with object with trailing comma after
type F = import("./nonexistent", { with: { type: "json", "resolution-mode": "import" }, })
>F : Symbol(F, Decl(importTypeTrailingComma.ts, 16, 68))

48 changes: 48 additions & 0 deletions tests/baselines/reference/importTypeTrailingComma.types
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
//// [tests/cases/compiler/importTypeTrailingComma.ts] ////

=== importTypeTrailingComma.ts ===
// Test that trailing commas are allowed in import type attributes
// This should work consistently with dynamic imports

// Trailing comma inside with object (already worked)
type A = import("./nonexistent", { with: { type: "json", } })
>A : any
> : ^^^
>type : any
> : ^^^

// Trailing comma after with object (this is the fix)
type B = import("./nonexistent", { with: { type: "json" }, })
>B : any
> : ^^^
>type : any
> : ^^^

// No trailing comma for comparison
type C = import("./nonexistent", { with: { type: "json" } })
>C : any
> : ^^^
>type : any
> : ^^^

// Assert syntax with trailing comma
type D = import("./nonexistent", { assert: { type: "json" }, })
>D : any
> : ^^^
>type : any
> : ^^^

// typeof with trailing comma
type E = typeof import("./nonexistent", { with: { type: "json" }, })
>E : any
> : ^^^
>type : any
> : ^^^

// Multiple properties in with object with trailing comma after
type F = import("./nonexistent", { with: { type: "json", "resolution-mode": "import" }, })
>F : any
> : ^^^
>type : any
> : ^^^

21 changes: 21 additions & 0 deletions tests/cases/compiler/importTypeTrailingComma.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
// @module: esnext
// Test that trailing commas are allowed in import type attributes
// This should work consistently with dynamic imports

// Trailing comma inside with object (already worked)
type A = import("./nonexistent", { with: { type: "json", } })

// Trailing comma after with object (this is the fix)
type B = import("./nonexistent", { with: { type: "json" }, })

// No trailing comma for comparison
type C = import("./nonexistent", { with: { type: "json" } })

// Assert syntax with trailing comma
type D = import("./nonexistent", { assert: { type: "json" }, })

// typeof with trailing comma
type E = typeof import("./nonexistent", { with: { type: "json" }, })

// Multiple properties in with object with trailing comma after
type F = import("./nonexistent", { with: { type: "json", "resolution-mode": "import" }, })
Loading