Skip to content

Commit 234b3bb

Browse files
authored
Merge master 08/22 (#10487)
* Add test case for #8229 * Do not report errors during contextual typecheck Fixes #8229 * Handle the scenario when let [a=undefined]=[] * Instantiate contextual this parameters if needed * Test that contextually typed generic this parameters are instantiated * Don't allow `.ts` to appear in an import * Add specific error message for unwanted '.ts' extension * Allow `await` in a simple unary expression * More tests * Forbid `await await` * Allow `await await` * Improve error message * Don't allow ".d.ts" extension in an import either. * Rename 'find' functions * Assign and instantiate contextual this type if not present * JSDoc supports null, undefined and never types * Update baselines in jsDocParsing unit tests * Return non-JsDocComment children ... to make syntactic classification work * Move supportedTypescriptExtensionsWithDtsFirst next to supportedTypeScriptExtensions and rename * Fix comment * Treat special property access symbol differently ... when retriving documentation * Fix tests * Update shim version to be 2.1 (#10424) * Check return code paths on getters (#10102) * Check return paths on getters * Remove TODO comment * Remove extraneous arguments from harness's runBaseline (#10419) * Remove extraneous arguments from runBaseline * Address comments from @yuit * Remove needless call to basename * Refactor baseliners out of compiler runner (#10440) * CR feedback * fix broken tests * Pass in baselineOpts into types baselines so that RWC baselines can be written to internal folder (#10443) * Add more test for 10426 * routine update of dom libs * Add test for jsdoc syntactic classification for function declaration * Simplify implementation * Tolerate certain errors in tsconfig.json * Add test for configFile error tolerance * Use TS parser to tolerate more errors in tsconfig.json * Implement tuple types as type references to synthesized generic types * Add comments + minor changes * Accept new baselines * Add .types extension * Properly guard for undefined in getTypeReferenceArity * Add jsdoc nullable union test case to fourslash * Fix class/interface merging issue + lint error * Allow "typings" in a package.json to be missing its extension (but also allow it to have an extension) * Contextually type this in getDeclFromSig, not checkThisExpr * Update parser comment with es7 grammar (#10459) * Use ES7 term of ExponentiationExpression * Update timeout for mac OS * Address PR: add space * allowSyntheticDefaultImports resolves to modules instead of variables Fixes #10429 by improving the fix in #10096 * Rename getContextuallyTypedThisParameter to getContextualThisParameter * Fix 10472: Invalid emitted code for await expression (#10483) * Properly emit await expression with yield expression * Add tests and update baselines * Move parsing await expression into parse unary-expression * Update incorrect comment
1 parent c05a866 commit 234b3bb

File tree

73 files changed

+1609
-438
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

73 files changed

+1609
-438
lines changed

Gulpfile.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -551,7 +551,7 @@ function restoreSavedNodeEnv() {
551551
process.env.NODE_ENV = savedNodeEnv;
552552
}
553553

554-
let testTimeout = 20000;
554+
let testTimeout = 40000;
555555
function runConsoleTests(defaultReporter: string, runInParallel: boolean, done: (e?: any) => void) {
556556
const lintFlag = cmdLineOptions["lint"];
557557
cleanTestDirs((err) => {

src/compiler/checker.ts

Lines changed: 128 additions & 107 deletions
Large diffs are not rendered by default.

src/compiler/emitter.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1817,6 +1817,10 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
18171817
else if (node.parent.kind === SyntaxKind.ConditionalExpression && (<ConditionalExpression>node.parent).condition === node) {
18181818
return true;
18191819
}
1820+
else if (node.parent.kind === SyntaxKind.PrefixUnaryExpression || node.parent.kind === SyntaxKind.DeleteExpression ||
1821+
node.parent.kind === SyntaxKind.TypeOfExpression || node.parent.kind === SyntaxKind.VoidExpression) {
1822+
return true;
1823+
}
18201824

18211825
return false;
18221826
}

src/compiler/parser.ts

Lines changed: 39 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -912,7 +912,7 @@ namespace ts {
912912
// Note: it is not actually necessary to save/restore the context flags here. That's
913913
// because the saving/restoring of these flags happens naturally through the recursive
914914
// descent nature of our parser. However, we still store this here just so we can
915-
// assert that that invariant holds.
915+
// assert that invariant holds.
916916
const saveContextFlags = contextFlags;
917917

918918
// If we're only looking ahead, then tell the scanner to only lookahead as well.
@@ -2765,7 +2765,7 @@ namespace ts {
27652765
// Note: for ease of implementation we treat productions '2' and '3' as the same thing.
27662766
// (i.e. they're both BinaryExpressions with an assignment operator in it).
27672767

2768-
// First, do the simple check if we have a YieldExpression (production '5').
2768+
// First, do the simple check if we have a YieldExpression (production '6').
27692769
if (isYieldExpression()) {
27702770
return parseYieldExpression();
27712771
}
@@ -3373,24 +3373,40 @@ namespace ts {
33733373
}
33743374

33753375
/**
3376-
* Parse ES7 unary expression and await expression
3376+
* Parse ES7 exponential expression and await expression
3377+
*
3378+
* ES7 ExponentiationExpression:
3379+
* 1) UnaryExpression[?Yield]
3380+
* 2) UpdateExpression[?Yield] ** ExponentiationExpression[?Yield]
33773381
*
3378-
* ES7 UnaryExpression:
3379-
* 1) SimpleUnaryExpression[?yield]
3380-
* 2) IncrementExpression[?yield] ** UnaryExpression[?yield]
33813382
*/
33823383
function parseUnaryExpressionOrHigher(): UnaryExpression | BinaryExpression {
3383-
if (isAwaitExpression()) {
3384-
return parseAwaitExpression();
3385-
}
3386-
3387-
if (isIncrementExpression()) {
3384+
/**
3385+
* ES7 UpdateExpression:
3386+
* 1) LeftHandSideExpression[?Yield]
3387+
* 2) LeftHandSideExpression[?Yield][no LineTerminator here]++
3388+
* 3) LeftHandSideExpression[?Yield][no LineTerminator here]--
3389+
* 4) ++UnaryExpression[?Yield]
3390+
* 5) --UnaryExpression[?Yield]
3391+
*/
3392+
if (isUpdateExpression()) {
33883393
const incrementExpression = parseIncrementExpression();
33893394
return token() === SyntaxKind.AsteriskAsteriskToken ?
33903395
<BinaryExpression>parseBinaryExpressionRest(getBinaryOperatorPrecedence(), incrementExpression) :
33913396
incrementExpression;
33923397
}
33933398

3399+
/**
3400+
* ES7 UnaryExpression:
3401+
* 1) UpdateExpression[?yield]
3402+
* 2) delete UpdateExpression[?yield]
3403+
* 3) void UpdateExpression[?yield]
3404+
* 4) typeof UpdateExpression[?yield]
3405+
* 5) + UpdateExpression[?yield]
3406+
* 6) - UpdateExpression[?yield]
3407+
* 7) ~ UpdateExpression[?yield]
3408+
* 8) ! UpdateExpression[?yield]
3409+
*/
33943410
const unaryOperator = token();
33953411
const simpleUnaryExpression = parseSimpleUnaryExpression();
33963412
if (token() === SyntaxKind.AsteriskAsteriskToken) {
@@ -3408,8 +3424,8 @@ namespace ts {
34083424
/**
34093425
* Parse ES7 simple-unary expression or higher:
34103426
*
3411-
* ES7 SimpleUnaryExpression:
3412-
* 1) IncrementExpression[?yield]
3427+
* ES7 UnaryExpression:
3428+
* 1) UpdateExpression[?yield]
34133429
* 2) delete UnaryExpression[?yield]
34143430
* 3) void UnaryExpression[?yield]
34153431
* 4) typeof UnaryExpression[?yield]
@@ -3432,13 +3448,15 @@ namespace ts {
34323448
return parseTypeOfExpression();
34333449
case SyntaxKind.VoidKeyword:
34343450
return parseVoidExpression();
3435-
case SyntaxKind.AwaitKeyword:
3436-
return parseAwaitExpression();
34373451
case SyntaxKind.LessThanToken:
34383452
// This is modified UnaryExpression grammar in TypeScript
34393453
// UnaryExpression (modified):
34403454
// < type > UnaryExpression
34413455
return parseTypeAssertion();
3456+
case SyntaxKind.AwaitKeyword:
3457+
if (isAwaitExpression()) {
3458+
return parseAwaitExpression();
3459+
}
34423460
default:
34433461
return parseIncrementExpression();
34443462
}
@@ -3447,14 +3465,14 @@ namespace ts {
34473465
/**
34483466
* Check if the current token can possibly be an ES7 increment expression.
34493467
*
3450-
* ES7 IncrementExpression:
3468+
* ES7 UpdateExpression:
34513469
* LeftHandSideExpression[?Yield]
34523470
* LeftHandSideExpression[?Yield][no LineTerminator here]++
34533471
* LeftHandSideExpression[?Yield][no LineTerminator here]--
34543472
* ++LeftHandSideExpression[?Yield]
34553473
* --LeftHandSideExpression[?Yield]
34563474
*/
3457-
function isIncrementExpression(): boolean {
3475+
function isUpdateExpression(): boolean {
34583476
// This function is called inside parseUnaryExpression to decide
34593477
// whether to call parseSimpleUnaryExpression or call parseIncrementExpression directly
34603478
switch (token()) {
@@ -3465,6 +3483,7 @@ namespace ts {
34653483
case SyntaxKind.DeleteKeyword:
34663484
case SyntaxKind.TypeOfKeyword:
34673485
case SyntaxKind.VoidKeyword:
3486+
case SyntaxKind.AwaitKeyword:
34683487
return false;
34693488
case SyntaxKind.LessThanToken:
34703489
// If we are not in JSX context, we are parsing TypeAssertion which is an UnaryExpression
@@ -5893,6 +5912,9 @@ namespace ts {
58935912
case SyntaxKind.BooleanKeyword:
58945913
case SyntaxKind.SymbolKeyword:
58955914
case SyntaxKind.VoidKeyword:
5915+
case SyntaxKind.NullKeyword:
5916+
case SyntaxKind.UndefinedKeyword:
5917+
case SyntaxKind.NeverKeyword:
58965918
return parseTokenNode<JSDocType>();
58975919
case SyntaxKind.StringLiteral:
58985920
case SyntaxKind.NumericLiteral:

src/compiler/program.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -721,8 +721,10 @@ namespace ts {
721721
const typesFile = tryReadTypesSection(packageJsonPath, candidate, state);
722722
if (typesFile) {
723723
const onlyRecordFailures = !directoryProbablyExists(getDirectoryPath(typesFile), state.host);
724-
// The package.json "typings" property must specify the file with extension, so just try that exact filename.
725-
const result = tryFile(typesFile, failedLookupLocation, onlyRecordFailures, state);
724+
// A package.json "typings" may specify an exact filename, or may choose to omit an extension.
725+
const result = tryFile(typesFile, failedLookupLocation, onlyRecordFailures, state) ||
726+
tryAddingExtensions(typesFile, extensions, failedLookupLocation, onlyRecordFailures, state);
727+
726728
if (result) {
727729
return result;
728730
}

src/compiler/types.ts

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -351,6 +351,9 @@ namespace ts {
351351
JSDocPropertyTag,
352352
JSDocTypeLiteral,
353353
JSDocLiteralType,
354+
JSDocNullKeyword,
355+
JSDocUndefinedKeyword,
356+
JSDocNeverKeyword,
354357

355358
// Synthesized list
356359
SyntaxList,
@@ -383,7 +386,7 @@ namespace ts {
383386
FirstJSDocNode = JSDocTypeExpression,
384387
LastJSDocNode = JSDocLiteralType,
385388
FirstJSDocTagNode = JSDocComment,
386-
LastJSDocTagNode = JSDocLiteralType
389+
LastJSDocTagNode = JSDocNeverKeyword
387390
}
388391

389392
export const enum NodeFlags {
@@ -2263,7 +2266,7 @@ namespace ts {
22632266
Class = 1 << 15, // Class
22642267
Interface = 1 << 16, // Interface
22652268
Reference = 1 << 17, // Generic type reference
2266-
Tuple = 1 << 18, // Tuple
2269+
Tuple = 1 << 18, // Synthesized generic tuple type
22672270
Union = 1 << 19, // Union (T | U)
22682271
Intersection = 1 << 20, // Intersection (T & U)
22692272
Anonymous = 1 << 21, // Anonymous
@@ -2385,11 +2388,6 @@ namespace ts {
23852388
instantiations: Map<TypeReference>; // Generic instantiation cache
23862389
}
23872390

2388-
export interface TupleType extends ObjectType {
2389-
elementTypes: Type[]; // Element types
2390-
thisType?: Type; // This-type of tuple (only needed for tuples that are constraints of type parameters)
2391-
}
2392-
23932391
export interface UnionOrIntersectionType extends Type {
23942392
types: Type[]; // Constituent types
23952393
/* @internal */

src/compiler/utilities.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -301,6 +301,10 @@ namespace ts {
301301
return node.kind >= SyntaxKind.FirstJSDocNode && node.kind <= SyntaxKind.LastJSDocNode;
302302
}
303303

304+
export function isJSDocTag(node: Node) {
305+
return node.kind >= SyntaxKind.FirstJSDocTagNode && node.kind <= SyntaxKind.LastJSDocTagNode;
306+
}
307+
304308
export function getNonDecoratorTokenPosOfNode(node: Node, sourceFile?: SourceFile): number {
305309
if (nodeIsMissing(node) || !node.decorators) {
306310
return getTokenPosOfNode(node, sourceFile);

src/harness/rwcRunner.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -158,13 +158,13 @@ namespace RWC {
158158

159159

160160
it("has the expected emitted code", () => {
161-
Harness.Baseline.runBaseline(baseName + ".output.js", () => {
161+
Harness.Baseline.runBaseline(`${baseName}.output.js`, () => {
162162
return Harness.Compiler.collateOutputs(compilerResult.files);
163163
}, baselineOpts);
164164
});
165165

166166
it("has the expected declaration file content", () => {
167-
Harness.Baseline.runBaseline(baseName + ".d.ts", () => {
167+
Harness.Baseline.runBaseline(`${baseName}.d.ts`, () => {
168168
if (!compilerResult.declFilesCode.length) {
169169
return null;
170170
}
@@ -174,7 +174,7 @@ namespace RWC {
174174
});
175175

176176
it("has the expected source maps", () => {
177-
Harness.Baseline.runBaseline(baseName + ".map", () => {
177+
Harness.Baseline.runBaseline(`${baseName}.map`, () => {
178178
if (!compilerResult.sourceMaps.length) {
179179
return null;
180180
}
@@ -192,7 +192,7 @@ namespace RWC {
192192
});*/
193193

194194
it("has the expected errors", () => {
195-
Harness.Baseline.runBaseline(baseName + ".errors.txt", () => {
195+
Harness.Baseline.runBaseline(`${baseName}.errors.txt`, () => {
196196
if (compilerResult.errors.length === 0) {
197197
return null;
198198
}
@@ -207,7 +207,7 @@ namespace RWC {
207207
// declaration file errors as part of the baseline.
208208
it("has the expected errors in generated declaration files", () => {
209209
if (compilerOptions.declaration && !compilerResult.errors.length) {
210-
Harness.Baseline.runBaseline(baseName + ".dts.errors.txt", () => {
210+
Harness.Baseline.runBaseline(`${baseName}.dts.errors.txt`, () => {
211211
const declFileCompilationResult = Harness.Compiler.compileDeclarationFiles(
212212
inputFiles, otherFiles, compilerResult, /*harnessSettings*/ undefined, compilerOptions, currentDirectory);
213213

@@ -223,7 +223,7 @@ namespace RWC {
223223
});
224224

225225
it("has the expected types", () => {
226-
Harness.Compiler.doTypeAndSymbolBaseline(baseName, compilerResult, inputFiles
226+
Harness.Compiler.doTypeAndSymbolBaseline(`${baseName}.types`, compilerResult, inputFiles
227227
.concat(otherFiles)
228228
.filter(file => !!compilerResult.program.getSourceFile(file.unitName))
229229
.filter(e => !Harness.isDefaultLibraryFile(e.unitName)), baselineOpts);

src/harness/unittests/jsDocParsing.ts

Lines changed: 5 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -767,33 +767,19 @@ namespace ts {
767767
parsesCorrectly(
768768
"{null}",
769769
`{
770-
"kind": "JSDocTypeReference",
770+
"kind": "NullKeyword",
771771
"pos": 1,
772-
"end": 5,
773-
"name": {
774-
"kind": "Identifier",
775-
"pos": 1,
776-
"end": 5,
777-
"originalKeywordKind": "NullKeyword",
778-
"text": "null"
779-
}
772+
"end": 5
780773
}`);
781774
});
782775

783776
it("keyword3", () => {
784777
parsesCorrectly(
785778
"{undefined}",
786779
`{
787-
"kind": "JSDocTypeReference",
780+
"kind": "UndefinedKeyword",
788781
"pos": 1,
789-
"end": 10,
790-
"name": {
791-
"kind": "Identifier",
792-
"pos": 1,
793-
"end": 10,
794-
"originalKeywordKind": "UndefinedKeyword",
795-
"text": "undefined"
796-
}
782+
"end": 10
797783
}`);
798784
});
799785

@@ -2379,4 +2365,4 @@ namespace ts {
23792365
});
23802366
});
23812367
});
2382-
}
2368+
}

src/harness/unittests/tsconfigParsing.ts

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -181,5 +181,25 @@ namespace ts {
181181
["/d.ts", "/folder/e.ts"]
182182
);
183183
});
184+
185+
it("parse and re-emit tsconfig.json file with diagnostics", () => {
186+
const content = `{
187+
"compilerOptions": {
188+
"allowJs": true
189+
"outDir": "bin"
190+
}
191+
"files": ["file1.ts"]
192+
}`;
193+
const { configJsonObject, diagnostics } = parseAndReEmitConfigJSONFile(content);
194+
const expectedResult = {
195+
compilerOptions: {
196+
allowJs: true,
197+
outDir: "bin"
198+
},
199+
files: ["file1.ts"]
200+
};
201+
assert.isTrue(diagnostics.length === 2);
202+
assert.equal(JSON.stringify(configJsonObject), JSON.stringify(expectedResult));
203+
});
184204
});
185205
}

src/harness/unittests/tsserverProjectSystem.ts

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -623,5 +623,23 @@ namespace ts {
623623
checkNumberOfConfiguredProjects(projectService, 1);
624624
checkNumberOfInferredProjects(projectService, 0);
625625
});
626+
627+
it("should tolerate config file errors and still try to build a project", () => {
628+
const configFile: FileOrFolder = {
629+
path: "/a/b/tsconfig.json",
630+
content: `{
631+
"compilerOptions": {
632+
"target": "es6",
633+
"allowAnything": true
634+
},
635+
"someOtherProperty": {}
636+
}`
637+
};
638+
const host = new TestServerHost(/*useCaseSensitiveFileNames*/ false, getExecutingFilePathFromLibFile(libFile), "/", [commonFile1, commonFile2, libFile, configFile]);
639+
const projectService = new server.ProjectService(host, nullLogger);
640+
projectService.openClientFile(commonFile1.path);
641+
checkNumberOfConfiguredProjects(projectService, 1);
642+
checkConfiguredProjectRootFiles(projectService.configuredProjects[0], [commonFile1.path, commonFile2.path]);
643+
});
626644
});
627645
}

0 commit comments

Comments
 (0)