mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-02-05 08:11:30 -06:00
Fix import assertion occurrences crash and make import assertion parsing more generous (#47535)
This commit is contained in:
parent
04d77fe900
commit
bae0f50818
@ -39786,6 +39786,16 @@ namespace ts {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
if (!isImportEqualsDeclaration(node) && node.assertClause) {
|
||||
let hasError = false;
|
||||
for (const clause of node.assertClause.elements) {
|
||||
if (!isStringLiteral(clause.value)) {
|
||||
hasError = true;
|
||||
error(clause.value, Diagnostics.Import_assertion_values_must_be_string_literal_expressions);
|
||||
}
|
||||
}
|
||||
return !hasError;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@ -3369,6 +3369,10 @@
|
||||
"category": "Error",
|
||||
"code": 2836
|
||||
},
|
||||
"Import assertion values must be string literal expressions.": {
|
||||
"category": "Error",
|
||||
"code": 2837
|
||||
},
|
||||
|
||||
"Import declaration '{0}' is using private name '{1}'.": {
|
||||
"category": "Error",
|
||||
|
||||
@ -4024,7 +4024,7 @@ namespace ts {
|
||||
}
|
||||
|
||||
// @api
|
||||
function createAssertEntry(name: AssertionKey, value: StringLiteral): AssertEntry {
|
||||
function createAssertEntry(name: AssertionKey, value: Expression): AssertEntry {
|
||||
const node = createBaseNode<AssertEntry>(SyntaxKind.AssertEntry);
|
||||
node.name = name;
|
||||
node.value = value;
|
||||
@ -4033,7 +4033,7 @@ namespace ts {
|
||||
}
|
||||
|
||||
// @api
|
||||
function updateAssertEntry(node: AssertEntry, name: AssertionKey, value: StringLiteral): AssertEntry {
|
||||
function updateAssertEntry(node: AssertEntry, name: AssertionKey, value: Expression): AssertEntry {
|
||||
return node.name !== name
|
||||
|| node.value !== value
|
||||
? update(createAssertEntry(name, value), node)
|
||||
|
||||
@ -7281,7 +7281,7 @@ namespace ts {
|
||||
const pos = getNodePos();
|
||||
const name = tokenIsIdentifierOrKeyword(token()) ? parseIdentifierName() : parseLiteralLikeNode(SyntaxKind.StringLiteral) as StringLiteral;
|
||||
parseExpected(SyntaxKind.ColonToken);
|
||||
const value = parseLiteralLikeNode(SyntaxKind.StringLiteral) as StringLiteral;
|
||||
const value = parseAssignmentExpressionOrHigher();
|
||||
return finishNode(factory.createAssertEntry(name, value), pos);
|
||||
}
|
||||
|
||||
|
||||
@ -3055,7 +3055,7 @@ namespace ts {
|
||||
readonly kind: SyntaxKind.AssertEntry;
|
||||
readonly parent: AssertClause;
|
||||
readonly name: AssertionKey;
|
||||
readonly value: StringLiteral;
|
||||
readonly value: Expression;
|
||||
}
|
||||
|
||||
export interface AssertClause extends Node {
|
||||
@ -7446,8 +7446,8 @@ namespace ts {
|
||||
updateImportClause(node: ImportClause, isTypeOnly: boolean, name: Identifier | undefined, namedBindings: NamedImportBindings | undefined): ImportClause;
|
||||
createAssertClause(elements: NodeArray<AssertEntry>, multiLine?: boolean): AssertClause;
|
||||
updateAssertClause(node: AssertClause, elements: NodeArray<AssertEntry>, multiLine?: boolean): AssertClause;
|
||||
createAssertEntry(name: AssertionKey, value: StringLiteral): AssertEntry;
|
||||
updateAssertEntry (node: AssertEntry, name: AssertionKey, value: StringLiteral): AssertEntry;
|
||||
createAssertEntry(name: AssertionKey, value: Expression): AssertEntry;
|
||||
updateAssertEntry(node: AssertEntry, name: AssertionKey, value: Expression): AssertEntry;
|
||||
createNamespaceImport(name: Identifier): NamespaceImport;
|
||||
updateNamespaceImport(node: NamespaceImport, name: Identifier): NamespaceImport;
|
||||
createNamespaceExport(name: Identifier): NamespaceExport;
|
||||
|
||||
@ -1090,7 +1090,7 @@ namespace ts {
|
||||
Debug.type<AssertEntry>(node);
|
||||
return factory.updateAssertEntry(node,
|
||||
nodeVisitor(node.name, visitor, isAssertionKey),
|
||||
nodeVisitor(node.value, visitor, isStringLiteral));
|
||||
nodeVisitor(node.value, visitor, isExpressionNode));
|
||||
|
||||
case SyntaxKind.ImportClause:
|
||||
Debug.type<ImportClause>(node);
|
||||
|
||||
@ -526,7 +526,7 @@ namespace ts.FindAllReferences {
|
||||
function getTextSpan(node: Node, sourceFile: SourceFile, endNode?: Node): TextSpan {
|
||||
let start = node.getStart(sourceFile);
|
||||
let end = (endNode || node).getEnd();
|
||||
if (isStringLiteralLike(node)) {
|
||||
if (isStringLiteralLike(node) && (end - start) > 2) {
|
||||
Debug.assert(endNode === undefined);
|
||||
start += 1;
|
||||
end -= 1;
|
||||
|
||||
@ -1652,7 +1652,7 @@ declare namespace ts {
|
||||
readonly kind: SyntaxKind.AssertEntry;
|
||||
readonly parent: AssertClause;
|
||||
readonly name: AssertionKey;
|
||||
readonly value: StringLiteral;
|
||||
readonly value: Expression;
|
||||
}
|
||||
export interface AssertClause extends Node {
|
||||
readonly kind: SyntaxKind.AssertClause;
|
||||
@ -3576,8 +3576,8 @@ declare namespace ts {
|
||||
updateImportClause(node: ImportClause, isTypeOnly: boolean, name: Identifier | undefined, namedBindings: NamedImportBindings | undefined): ImportClause;
|
||||
createAssertClause(elements: NodeArray<AssertEntry>, multiLine?: boolean): AssertClause;
|
||||
updateAssertClause(node: AssertClause, elements: NodeArray<AssertEntry>, multiLine?: boolean): AssertClause;
|
||||
createAssertEntry(name: AssertionKey, value: StringLiteral): AssertEntry;
|
||||
updateAssertEntry(node: AssertEntry, name: AssertionKey, value: StringLiteral): AssertEntry;
|
||||
createAssertEntry(name: AssertionKey, value: Expression): AssertEntry;
|
||||
updateAssertEntry(node: AssertEntry, name: AssertionKey, value: Expression): AssertEntry;
|
||||
createNamespaceImport(name: Identifier): NamespaceImport;
|
||||
updateNamespaceImport(node: NamespaceImport, name: Identifier): NamespaceImport;
|
||||
createNamespaceExport(name: Identifier): NamespaceExport;
|
||||
|
||||
@ -1652,7 +1652,7 @@ declare namespace ts {
|
||||
readonly kind: SyntaxKind.AssertEntry;
|
||||
readonly parent: AssertClause;
|
||||
readonly name: AssertionKey;
|
||||
readonly value: StringLiteral;
|
||||
readonly value: Expression;
|
||||
}
|
||||
export interface AssertClause extends Node {
|
||||
readonly kind: SyntaxKind.AssertClause;
|
||||
@ -3576,8 +3576,8 @@ declare namespace ts {
|
||||
updateImportClause(node: ImportClause, isTypeOnly: boolean, name: Identifier | undefined, namedBindings: NamedImportBindings | undefined): ImportClause;
|
||||
createAssertClause(elements: NodeArray<AssertEntry>, multiLine?: boolean): AssertClause;
|
||||
updateAssertClause(node: AssertClause, elements: NodeArray<AssertEntry>, multiLine?: boolean): AssertClause;
|
||||
createAssertEntry(name: AssertionKey, value: StringLiteral): AssertEntry;
|
||||
updateAssertEntry(node: AssertEntry, name: AssertionKey, value: StringLiteral): AssertEntry;
|
||||
createAssertEntry(name: AssertionKey, value: Expression): AssertEntry;
|
||||
updateAssertEntry(node: AssertEntry, name: AssertionKey, value: Expression): AssertEntry;
|
||||
createNamespaceImport(name: Identifier): NamespaceImport;
|
||||
updateNamespaceImport(node: NamespaceImport, name: Identifier): NamespaceImport;
|
||||
createNamespaceExport(name: Identifier): NamespaceExport;
|
||||
|
||||
@ -0,0 +1,32 @@
|
||||
tests/cases/compiler/mod.mts(1,52): error TS2837: Import assertion values must be string literal expressions.
|
||||
tests/cases/compiler/mod.mts(3,52): error TS2837: Import assertion values must be string literal expressions.
|
||||
tests/cases/compiler/mod.mts(5,52): error TS2837: Import assertion values must be string literal expressions.
|
||||
tests/cases/compiler/mod.mts(7,52): error TS2837: Import assertion values must be string literal expressions.
|
||||
tests/cases/compiler/mod.mts(9,52): error TS2837: Import assertion values must be string literal expressions.
|
||||
tests/cases/compiler/mod.mts(11,66): error TS2837: Import assertion values must be string literal expressions.
|
||||
|
||||
|
||||
==== tests/cases/compiler/mod.mts (6 errors) ====
|
||||
import * as thing1 from "./mod.mjs" assert {field: 0};
|
||||
~
|
||||
!!! error TS2837: Import assertion values must be string literal expressions.
|
||||
|
||||
import * as thing2 from "./mod.mjs" assert {field: `a`};
|
||||
~~~
|
||||
!!! error TS2837: Import assertion values must be string literal expressions.
|
||||
|
||||
import * as thing3 from "./mod.mjs" assert {field: /a/g};
|
||||
~~~~
|
||||
!!! error TS2837: Import assertion values must be string literal expressions.
|
||||
|
||||
import * as thing4 from "./mod.mjs" assert {field: ["a"]};
|
||||
~~~~~
|
||||
!!! error TS2837: Import assertion values must be string literal expressions.
|
||||
|
||||
import * as thing5 from "./mod.mjs" assert {field: { a: 0 }};
|
||||
~~~~~~~~
|
||||
!!! error TS2837: Import assertion values must be string literal expressions.
|
||||
|
||||
import * as thing6 from "./mod.mjs" assert {type: "json", field: 0..toString()}
|
||||
~~~~~~~~~~~~~
|
||||
!!! error TS2837: Import assertion values must be string literal expressions.
|
||||
15
tests/baselines/reference/importAssertionNonstring.js
Normal file
15
tests/baselines/reference/importAssertionNonstring.js
Normal file
@ -0,0 +1,15 @@
|
||||
//// [mod.mts]
|
||||
import * as thing1 from "./mod.mjs" assert {field: 0};
|
||||
|
||||
import * as thing2 from "./mod.mjs" assert {field: `a`};
|
||||
|
||||
import * as thing3 from "./mod.mjs" assert {field: /a/g};
|
||||
|
||||
import * as thing4 from "./mod.mjs" assert {field: ["a"]};
|
||||
|
||||
import * as thing5 from "./mod.mjs" assert {field: { a: 0 }};
|
||||
|
||||
import * as thing6 from "./mod.mjs" assert {type: "json", field: 0..toString()}
|
||||
|
||||
//// [mod.mjs]
|
||||
export {};
|
||||
22
tests/baselines/reference/importAssertionNonstring.symbols
Normal file
22
tests/baselines/reference/importAssertionNonstring.symbols
Normal file
@ -0,0 +1,22 @@
|
||||
=== tests/cases/compiler/mod.mts ===
|
||||
import * as thing1 from "./mod.mjs" assert {field: 0};
|
||||
>thing1 : Symbol(thing1, Decl(mod.mts, 0, 6))
|
||||
|
||||
import * as thing2 from "./mod.mjs" assert {field: `a`};
|
||||
>thing2 : Symbol(thing2, Decl(mod.mts, 2, 6))
|
||||
|
||||
import * as thing3 from "./mod.mjs" assert {field: /a/g};
|
||||
>thing3 : Symbol(thing3, Decl(mod.mts, 4, 6))
|
||||
|
||||
import * as thing4 from "./mod.mjs" assert {field: ["a"]};
|
||||
>thing4 : Symbol(thing4, Decl(mod.mts, 6, 6))
|
||||
|
||||
import * as thing5 from "./mod.mjs" assert {field: { a: 0 }};
|
||||
>thing5 : Symbol(thing5, Decl(mod.mts, 8, 6))
|
||||
>a : Symbol(a, Decl(mod.mts, 8, 52))
|
||||
|
||||
import * as thing6 from "./mod.mjs" assert {type: "json", field: 0..toString()}
|
||||
>thing6 : Symbol(thing6, Decl(mod.mts, 10, 6))
|
||||
>0..toString : Symbol(Number.toString, Decl(lib.es5.d.ts, --, --))
|
||||
>toString : Symbol(Number.toString, Decl(lib.es5.d.ts, --, --))
|
||||
|
||||
36
tests/baselines/reference/importAssertionNonstring.types
Normal file
36
tests/baselines/reference/importAssertionNonstring.types
Normal file
@ -0,0 +1,36 @@
|
||||
=== tests/cases/compiler/mod.mts ===
|
||||
import * as thing1 from "./mod.mjs" assert {field: 0};
|
||||
>thing1 : typeof thing1
|
||||
>field : any
|
||||
|
||||
import * as thing2 from "./mod.mjs" assert {field: `a`};
|
||||
>thing2 : typeof thing1
|
||||
>field : any
|
||||
|
||||
import * as thing3 from "./mod.mjs" assert {field: /a/g};
|
||||
>thing3 : typeof thing1
|
||||
>field : any
|
||||
>/a/g : RegExp
|
||||
|
||||
import * as thing4 from "./mod.mjs" assert {field: ["a"]};
|
||||
>thing4 : typeof thing1
|
||||
>field : any
|
||||
>["a"] : string[]
|
||||
>"a" : "a"
|
||||
|
||||
import * as thing5 from "./mod.mjs" assert {field: { a: 0 }};
|
||||
>thing5 : typeof thing1
|
||||
>field : any
|
||||
>{ a: 0 } : { a: number; }
|
||||
>a : number
|
||||
>0 : 0
|
||||
|
||||
import * as thing6 from "./mod.mjs" assert {type: "json", field: 0..toString()}
|
||||
>thing6 : typeof thing1
|
||||
>type : any
|
||||
>field : any
|
||||
>0..toString() : string
|
||||
>0..toString : (radix?: number) => string
|
||||
>0. : 0
|
||||
>toString : (radix?: number) => string
|
||||
|
||||
13
tests/cases/compiler/importAssertionNonstring.ts
Normal file
13
tests/cases/compiler/importAssertionNonstring.ts
Normal file
@ -0,0 +1,13 @@
|
||||
// @module: nodenext
|
||||
// @filename: mod.mts
|
||||
import * as thing1 from "./mod.mjs" assert {field: 0};
|
||||
|
||||
import * as thing2 from "./mod.mjs" assert {field: `a`};
|
||||
|
||||
import * as thing3 from "./mod.mjs" assert {field: /a/g};
|
||||
|
||||
import * as thing4 from "./mod.mjs" assert {field: ["a"]};
|
||||
|
||||
import * as thing5 from "./mod.mjs" assert {field: { a: 0 }};
|
||||
|
||||
import * as thing6 from "./mod.mjs" assert {type: "json", field: 0..toString()}
|
||||
@ -0,0 +1,8 @@
|
||||
/// <reference path="fourslash.ts" />
|
||||
|
||||
// @module: nodenext
|
||||
////import * as react from "react" assert { cache: /**/0 };
|
||||
////react.Children;
|
||||
|
||||
goTo.marker();
|
||||
verify.occurrencesAtPositionCount(0);
|
||||
Loading…
x
Reference in New Issue
Block a user