Skip to content

Commit c48018f

Browse files
committed
Merge branch 'master' into report-multiple-overload-errors
2 parents 47bbc95 + cfe4cbd commit c48018f

File tree

185 files changed

+3031
-2294
lines changed

Some content is hidden

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

185 files changed

+3031
-2294
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ tests/webTestServer.js.map
3434
tests/webhost/*.d.ts
3535
tests/webhost/webtsc.js
3636
tests/cases/**/*.js
37+
!tests/cases/docker/*.js/
3738
tests/cases/**/*.js.map
3839
*.config
3940
scripts/debug.bat

scripts/update-experimental-branches.js

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -7,18 +7,23 @@ const { runSequence } = require("./run-sequence");
77
const triggeredPR = process.env.SOURCE_ISSUE || process.env.SYSTEM_PULLREQUEST_PULLREQUESTNUMBER;
88

99
/**
10-
* This program should be invoked as `node ./scripts/update-experimental-branches <GithubAccessToken> <PR1> [PR2] [...]`
11-
* The order PR numbers are passed controls the order in which they are merged together.
10+
* This program should be invoked as `node ./scripts/update-experimental-branches <GithubAccessToken>`
1211
* TODO: the following is racey - if two experiment-enlisted PRs trigger simultaneously and witness one another in an unupdated state, they'll both produce
1312
* a new experimental branch, but each will be missing a change from the other. There's no _great_ way to fix this beyond setting the maximum concurrency
1413
* of this task to 1 (so only one job is allowed to update experiments at a time).
1514
*/
1615
async function main() {
17-
const prnums = process.argv.slice(3);
18-
if (!prnums.length) {
19-
return; // No enlisted PRs, nothing to update
20-
}
21-
if (!prnums.some(n => n === triggeredPR)) {
16+
const gh = new Octokit({
17+
auth: process.argv[2]
18+
});
19+
const prnums = (await gh.issues.listForRepo({
20+
labels: "typescript@experimental",
21+
sort: "created",
22+
state: "open",
23+
owner: "Microsoft",
24+
repo: "TypeScript",
25+
})).data.filter(i => !!i.pull_request).map(i => i.number);
26+
if (triggeredPR && !prnums.some(n => n === +triggeredPR)) {
2227
return; // Only have work to do for enlisted PRs
2328
}
2429
console.log(`Performing experimental branch updating and merging for pull requests ${prnums.join(", ")}`);
@@ -34,9 +39,6 @@ async function main() {
3439
["git", ["remote", "add", "fork", remoteUrl]], // Add the remote fork
3540
]);
3641

37-
const gh = new Octokit({
38-
auth: process.argv[2]
39-
});
4042
for (const numRaw of prnums) {
4143
const num = +numRaw;
4244
if (num) {
@@ -51,9 +53,8 @@ async function main() {
5153
issue_number: num,
5254
body: `This PR is configured as an experiment, and currently has rebase conflicts with master - please rebase onto master and fix the conflicts.`
5355
});
54-
throw new Error(`Rebase conflict detected in PR ${num} with master`);
5556
}
56-
return; // A PR is currently in conflict, give up
57+
throw new Error(`Rebase conflict detected in PR ${num} with master`); // A PR is currently in conflict, give up
5758
}
5859
runSequence([
5960
["git", ["fetch", "origin", `pull/${num}/head:${num}`]],

src/compiler/builder.ts

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

src/compiler/checker.ts

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20111,6 +20111,7 @@ namespace ts {
2011120111
}
2011220112

2011320113
function checkJsxExpression(node: JsxExpression, checkMode?: CheckMode) {
20114+
checkGrammarJsxExpression(node);
2011420115
if (node.expression) {
2011520116
const type = checkExpression(node.expression, checkMode);
2011620117
if (node.dotDotDotToken && type !== anyType && !isArrayType(type)) {
@@ -22658,7 +22659,10 @@ namespace ts {
2265822659
case SyntaxKind.ElementAccessExpression:
2265922660
const expr = (<PropertyAccessExpression | ElementAccessExpression>node).expression;
2266022661
if (isIdentifier(expr)) {
22661-
const symbol = getSymbolAtLocation(expr);
22662+
let symbol = getSymbolAtLocation(expr);
22663+
if (symbol && symbol.flags & SymbolFlags.Alias) {
22664+
symbol = resolveAlias(symbol);
22665+
}
2266222666
return !!(symbol && (symbol.flags & SymbolFlags.Enum) && getEnumKind(symbol) === EnumKind.Literal);
2266322667
}
2266422668
}
@@ -32061,6 +32065,12 @@ namespace ts {
3206132065
}
3206232066
}
3206332067

32068+
function checkGrammarJsxExpression(node: JsxExpression) {
32069+
if (node.expression && isCommaSequence(node.expression)) {
32070+
return grammarErrorOnNode(node.expression, Diagnostics.JSX_expressions_may_not_use_the_comma_operator_Did_you_mean_to_write_an_array);
32071+
}
32072+
}
32073+
3206432074
function checkGrammarForInOrForOfStatement(forInOrOfStatement: ForInOrOfStatement): boolean {
3206532075
if (checkGrammarStatementInAmbientContext(forInOrOfStatement)) {
3206632076
return true;

src/compiler/commandLineParser.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -969,7 +969,8 @@ namespace ts {
969969
return typeAcquisition;
970970
}
971971

972-
function getOptionNameMap(): OptionNameMap {
972+
/* @internal */
973+
export function getOptionNameMap(): OptionNameMap {
973974
return optionNameMapCache || (optionNameMapCache = createOptionNameMap(optionDeclarations));
974975
}
975976

src/compiler/diagnosticMessages.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5025,5 +5025,9 @@
50255025
"Classes may not have a field named 'constructor'.": {
50265026
"category": "Error",
50275027
"code": 18006
5028+
},
5029+
"JSX expressions may not use the comma operator. Did you mean to write an array?": {
5030+
"category": "Error",
5031+
"code": 18007
50285032
}
50295033
}

src/compiler/emitter.ts

Lines changed: 41 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -249,14 +249,16 @@ namespace ts {
249249
};
250250

251251
function emitSourceFileOrBundle({ jsFilePath, sourceMapFilePath, declarationFilePath, declarationMapPath, buildInfoPath }: EmitFileNames, sourceFileOrBundle: SourceFile | Bundle | undefined) {
252+
let buildInfoDirectory: string | undefined;
252253
if (buildInfoPath && sourceFileOrBundle && isBundle(sourceFileOrBundle)) {
254+
buildInfoDirectory = getDirectoryPath(getNormalizedAbsolutePath(buildInfoPath, host.getCurrentDirectory()));
253255
bundleBuildInfo = {
254-
commonSourceDirectory: host.getCommonSourceDirectory(),
255-
sourceFiles: sourceFileOrBundle.sourceFiles.map(file => file.fileName)
256+
commonSourceDirectory: relativeToBuildInfo(host.getCommonSourceDirectory()),
257+
sourceFiles: sourceFileOrBundle.sourceFiles.map(file => relativeToBuildInfo(getNormalizedAbsolutePath(file.fileName, host.getCurrentDirectory())))
256258
};
257259
}
258-
emitJsFileOrBundle(sourceFileOrBundle, jsFilePath, sourceMapFilePath);
259-
emitDeclarationFileOrBundle(sourceFileOrBundle, declarationFilePath, declarationMapPath);
260+
emitJsFileOrBundle(sourceFileOrBundle, jsFilePath, sourceMapFilePath, relativeToBuildInfo);
261+
emitDeclarationFileOrBundle(sourceFileOrBundle, declarationFilePath, declarationMapPath, relativeToBuildInfo);
260262
emitBuildInfo(bundleBuildInfo, buildInfoPath);
261263

262264
if (!emitSkipped && emittedFilesList) {
@@ -278,6 +280,10 @@ namespace ts {
278280
emittedFilesList.push(declarationMapPath);
279281
}
280282
}
283+
284+
function relativeToBuildInfo(path: string) {
285+
return ensurePathIsNonModuleName(getRelativePathFromDirectory(buildInfoDirectory!, path, host.getCanonicalFileName));
286+
}
281287
}
282288

283289
function emitBuildInfo(bundle: BundleBuildInfo | undefined, buildInfoPath: string | undefined) {
@@ -291,7 +297,11 @@ namespace ts {
291297
writeFile(host, emitterDiagnostics, buildInfoPath, getBuildInfoText({ bundle, program, version }), /*writeByteOrderMark*/ false);
292298
}
293299

294-
function emitJsFileOrBundle(sourceFileOrBundle: SourceFile | Bundle | undefined, jsFilePath: string | undefined, sourceMapFilePath: string | undefined) {
300+
function emitJsFileOrBundle(
301+
sourceFileOrBundle: SourceFile | Bundle | undefined,
302+
jsFilePath: string | undefined,
303+
sourceMapFilePath: string | undefined,
304+
relativeToBuildInfo: (path: string) => string) {
295305
if (!sourceFileOrBundle || emitOnlyDtsFiles || !jsFilePath) {
296306
return;
297307
}
@@ -314,7 +324,8 @@ namespace ts {
314324
inlineSourceMap: compilerOptions.inlineSourceMap,
315325
inlineSources: compilerOptions.inlineSources,
316326
extendedDiagnostics: compilerOptions.extendedDiagnostics,
317-
writeBundleFileInfo: !!bundleBuildInfo
327+
writeBundleFileInfo: !!bundleBuildInfo,
328+
relativeToBuildInfo
318329
};
319330

320331
// Create a printer to print the nodes
@@ -335,7 +346,11 @@ namespace ts {
335346
if (bundleBuildInfo) bundleBuildInfo.js = printer.bundleFileInfo;
336347
}
337348

338-
function emitDeclarationFileOrBundle(sourceFileOrBundle: SourceFile | Bundle | undefined, declarationFilePath: string | undefined, declarationMapPath: string | undefined) {
349+
function emitDeclarationFileOrBundle(
350+
sourceFileOrBundle: SourceFile | Bundle | undefined,
351+
declarationFilePath: string | undefined,
352+
declarationMapPath: string | undefined,
353+
relativeToBuildInfo: (path: string) => string) {
339354
if (!sourceFileOrBundle || !(declarationFilePath && !isInJSFile(sourceFileOrBundle))) {
340355
return;
341356
}
@@ -366,7 +381,8 @@ namespace ts {
366381
extendedDiagnostics: compilerOptions.extendedDiagnostics,
367382
onlyPrintJsDocStyle: true,
368383
writeBundleFileInfo: !!bundleBuildInfo,
369-
recordInternalSection: !!bundleBuildInfo
384+
recordInternalSection: !!bundleBuildInfo,
385+
relativeToBuildInfo
370386
};
371387

372388
const declarationPrinter = createPrinter(printerOptions, {
@@ -613,10 +629,14 @@ namespace ts {
613629
getNewLine(): string;
614630
}
615631

616-
function createSourceFilesFromBundleBuildInfo(bundle: BundleBuildInfo): ReadonlyArray<SourceFile> {
632+
function createSourceFilesFromBundleBuildInfo(bundle: BundleBuildInfo, buildInfoDirectory: string, host: EmitUsingBuildInfoHost): ReadonlyArray<SourceFile> {
617633
const sourceFiles = bundle.sourceFiles.map(fileName => {
618634
const sourceFile = createNode(SyntaxKind.SourceFile, 0, 0) as SourceFile;
619-
sourceFile.fileName = fileName;
635+
sourceFile.fileName = getRelativePathFromDirectory(
636+
host.getCurrentDirectory(),
637+
getNormalizedAbsolutePath(fileName, buildInfoDirectory),
638+
!host.useCaseSensitiveFileNames()
639+
);
620640
sourceFile.text = "";
621641
sourceFile.statements = createNodeArray();
622642
return sourceFile;
@@ -660,6 +680,7 @@ namespace ts {
660680

661681
const buildInfo = getBuildInfo(buildInfoText);
662682
if (!buildInfo.bundle || !buildInfo.bundle.js || (declarationText && !buildInfo.bundle.dts)) return buildInfoPath!;
683+
const buildInfoDirectory = getDirectoryPath(getNormalizedAbsolutePath(buildInfoPath!, host.getCurrentDirectory()));
663684
const ownPrependInput = createInputFiles(
664685
jsFileText,
665686
declarationText!,
@@ -675,11 +696,11 @@ namespace ts {
675696
);
676697
const outputFiles: OutputFile[] = [];
677698
const prependNodes = createPrependNodes(config.projectReferences, getCommandLine, f => host.readFile(f));
678-
const sourceFilesForJsEmit = createSourceFilesFromBundleBuildInfo(buildInfo.bundle);
699+
const sourceFilesForJsEmit = createSourceFilesFromBundleBuildInfo(buildInfo.bundle, buildInfoDirectory, host);
679700
const emitHost: EmitHost = {
680701
getPrependNodes: memoize(() => [...prependNodes, ownPrependInput]),
681702
getCanonicalFileName: host.getCanonicalFileName,
682-
getCommonSourceDirectory: () => buildInfo.bundle!.commonSourceDirectory,
703+
getCommonSourceDirectory: () => getNormalizedAbsolutePath(buildInfo.bundle!.commonSourceDirectory, buildInfoDirectory),
683704
getCompilerOptions: () => config.options,
684705
getCurrentDirectory: () => host.getCurrentDirectory(),
685706
getNewLine: () => host.getNewLine(),
@@ -775,6 +796,7 @@ namespace ts {
775796
let write = writeBase;
776797
let isOwnFileEmit: boolean;
777798
const bundleFileInfo = printerOptions.writeBundleFileInfo ? { sections: [] } as BundleFileInfo : undefined;
799+
const relativeToBuildInfo = bundleFileInfo ? Debug.assertDefined(printerOptions.relativeToBuildInfo) : undefined;
778800
const recordInternalSection = printerOptions.recordInternalSection;
779801
let sourceFileTextPos = 0;
780802
let sourceFileTextKind: BundleFileTextLikeKind = BundleFileSectionKind.Text;
@@ -943,7 +965,13 @@ namespace ts {
943965
if (prepend.oldFileOfCurrentEmit) bundleFileInfo.sections.push(...newSections);
944966
else {
945967
newSections.forEach(section => Debug.assert(isBundleFileTextLike(section)));
946-
bundleFileInfo.sections.push({ pos, end: writer.getTextPos(), kind: BundleFileSectionKind.Prepend, data: (prepend as UnparsedSource).fileName, texts: newSections as BundleFileTextLike[] });
968+
bundleFileInfo.sections.push({
969+
pos,
970+
end: writer.getTextPos(),
971+
kind: BundleFileSectionKind.Prepend,
972+
data: relativeToBuildInfo!((prepend as UnparsedSource).fileName),
973+
texts: newSections as BundleFileTextLike[]
974+
});
947975
}
948976
}
949977
}

src/compiler/parser.ts

Lines changed: 26 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4430,14 +4430,18 @@ namespace ts {
44304430

44314431
if (token() !== SyntaxKind.CloseBraceToken) {
44324432
node.dotDotDotToken = parseOptionalToken(SyntaxKind.DotDotDotToken);
4433-
node.expression = parseAssignmentExpressionOrHigher();
4433+
// Only an AssignmentExpression is valid here per the JSX spec,
4434+
// but we can unambiguously parse a comma sequence and provide
4435+
// a better error message in grammar checking.
4436+
node.expression = parseExpression();
44344437
}
44354438
if (inExpressionContext) {
44364439
parseExpected(SyntaxKind.CloseBraceToken);
44374440
}
44384441
else {
4439-
parseExpected(SyntaxKind.CloseBraceToken, /*message*/ undefined, /*shouldAdvance*/ false);
4440-
scanJsxText();
4442+
if (parseExpected(SyntaxKind.CloseBraceToken, /*message*/ undefined, /*shouldAdvance*/ false)) {
4443+
scanJsxText();
4444+
}
44414445
}
44424446

44434447
return finishNode(node);
@@ -6427,6 +6431,7 @@ namespace ts {
64276431
BeginningOfLine,
64286432
SawAsterisk,
64296433
SavingComments,
6434+
SavingBackticks, // NOTE: Only used when parsing tag comments
64306435
}
64316436

64326437
const enum PropertyLikeParse {
@@ -6687,18 +6692,23 @@ namespace ts {
66876692
case SyntaxKind.NewLineTrivia:
66886693
if (state >= JSDocState.SawAsterisk) {
66896694
state = JSDocState.BeginningOfLine;
6695+
// don't use pushComment here because we want to keep the margin unchanged
66906696
comments.push(scanner.getTokenText());
66916697
}
66926698
indent = 0;
66936699
break;
66946700
case SyntaxKind.AtToken:
6701+
if (state === JSDocState.SavingBackticks) {
6702+
comments.push(scanner.getTokenText());
6703+
break;
6704+
}
66956705
scanner.setTextPos(scanner.getTextPos() - 1);
66966706
// falls through
66976707
case SyntaxKind.EndOfFileToken:
66986708
// Done
66996709
break loop;
67006710
case SyntaxKind.WhitespaceTrivia:
6701-
if (state === JSDocState.SavingComments) {
6711+
if (state === JSDocState.SavingComments || state === JSDocState.SavingBackticks) {
67026712
pushComment(scanner.getTokenText());
67036713
}
67046714
else {
@@ -6720,6 +6730,15 @@ namespace ts {
67206730
}
67216731
pushComment(scanner.getTokenText());
67226732
break;
6733+
case SyntaxKind.BacktickToken:
6734+
if (state === JSDocState.SavingBackticks) {
6735+
state = JSDocState.SavingComments;
6736+
}
6737+
else {
6738+
state = JSDocState.SavingBackticks;
6739+
}
6740+
pushComment(scanner.getTokenText());
6741+
break;
67236742
case SyntaxKind.AsteriskToken:
67246743
if (state === JSDocState.BeginningOfLine) {
67256744
// leading asterisks start recording on the *next* (non-whitespace) token
@@ -6730,7 +6749,9 @@ namespace ts {
67306749
// record the * as a comment
67316750
// falls through
67326751
default:
6733-
state = JSDocState.SavingComments; // leading identifiers start recording as well
6752+
if (state !== JSDocState.SavingBackticks) {
6753+
state = JSDocState.SavingComments; // leading identifiers start recording as well
6754+
}
67346755
pushComment(scanner.getTokenText());
67356756
break;
67366757
}

0 commit comments

Comments
 (0)