Handle prologues in prepend outputs

This commit is contained in:
Sheetal Nandi
2019-01-25 14:31:40 -08:00
parent a90ff10d8a
commit c739defe25
11 changed files with 654 additions and 592 deletions
+46 -3
View File
@@ -727,6 +727,9 @@ namespace ts {
case SyntaxKind.UnparsedSource:
return emitUnparsedSource(<UnparsedSource>node);
case SyntaxKind.UnparsedPrologue:
return emitUnparsedPrologue(<UnparsedPrologue>node);
// Identifiers
case SyntaxKind.Identifier:
return emitIdentifier(<Identifier>node);
@@ -1211,6 +1214,11 @@ namespace ts {
writer.rawWrite(unparsed.text.substr(unparsed.pos));
}
// SyntaxKind.UnparsedPrologue
function emitUnparsedPrologue(unparsed: UnparsedPrologue) {
writer.rawWrite(unparsed.parent.text.substring(unparsed.pos, unparsed.end));
}
//
// Identifiers
//
@@ -3005,6 +3013,17 @@ namespace ts {
return statements.length;
}
function emitUnparsedPrologues(prologues: ReadonlyArray<UnparsedPrologue>, seenPrologueDirectives: Map<true>) {
for (const prologue of prologues) {
if (!seenPrologueDirectives.has(prologue.text)) {
emit(prologue);
if (seenPrologueDirectives) {
seenPrologueDirectives.set(prologue.text, true);
}
}
}
}
function emitPrologueDirectivesIfNeeded(sourceFileOrBundle: Bundle | SourceFile) {
if (isSourceFile(sourceFileOrBundle)) {
setSourceFile(sourceFileOrBundle);
@@ -3012,6 +3031,9 @@ namespace ts {
}
else {
const seenPrologueDirectives = createMap<true>();
for (const prepend of sourceFileOrBundle.prepends) {
emitUnparsedPrologues((prepend as UnparsedSource).prologues, seenPrologueDirectives);
}
for (const sourceFile of sourceFileOrBundle.sourceFiles) {
setSourceFile(sourceFile);
emitPrologueDirectives(sourceFile.statements, /*startWithNewLine*/ true, seenPrologueDirectives);
@@ -4343,17 +4365,38 @@ namespace ts {
// Source Maps
function getParsedSourceMap(node: UnparsedSource) {
if (node.parsedSourceMap === undefined && node.sourceMapText !== undefined) {
node.parsedSourceMap = tryParseRawSourceMap(node.sourceMapText) || false;
}
return node.parsedSourceMap || undefined;
}
function pipelineEmitWithSourceMap(hint: EmitHint, node: Node) {
const pipelinePhase = getNextPipelinePhase(PipelinePhase.SourceMaps, node);
if (isUnparsedSource(node) && node.sourceMapText !== undefined) {
const parsed = tryParseRawSourceMap(node.sourceMapText);
if (isUnparsedSource(node)) {
const parsed = getParsedSourceMap(node);
if (parsed) {
sourceMapGenerator!.appendSourceMap(
writer.getLine(),
writer.getColumn(),
parsed,
node.sourceMapPath!,
node.pos && node.getLineAndCharacterOfPosition(node.pos).line);
node.pos ? node.getLineAndCharacterOfPosition(node.pos) : undefined);
}
pipelinePhase(hint, node);
}
else if (isUnparsedPrologue(node)) {
const parsed = getParsedSourceMap(node.parent);
if (parsed) {
sourceMapGenerator!.appendSourceMap(
writer.getLine(),
writer.getColumn(),
parsed,
node.parent.sourceMapPath!,
node.parent.getLineAndCharacterOfPosition(node.pos),
node.parent.getLineAndCharacterOfPosition(node.end)
);
}
pipelinePhase(hint, node);
}
+16 -1
View File
@@ -2649,7 +2649,22 @@ namespace ts {
node.sourceMapText = map;
}
const text = node.text;
node.pos = isShebangTrivia(text, 0) ? skipTrivia(text, 0, /*stopAfterLineBreak*/ true) : 0;
let pos = isShebangTrivia(text, 0) ? skipTrivia(text, 0, /*stopAfterLineBreak*/ true) : 0;
const scanner = createScanner(ScriptTarget.Latest, /*skipTrivia*/ true, /*languageVariant*/ undefined, text, /*onError*/ undefined, pos);
let prologues: UnparsedPrologue[] | undefined;
while (scanner.scan() === SyntaxKind.StringLiteral) {
const start = pos;
const prologueText = scanner.getTokenValue();
scanner.tryScan(() => scanner.scan() === SyntaxKind.SemicolonToken);
pos = skipTrivia(text, scanner.getTextPos(), /*stopAfterLineBreak*/ true);
const prologue = <UnparsedPrologue>createNode(SyntaxKind.UnparsedPrologue, start, pos);
prologue.parent = node;
prologue.text = prologueText;
(prologues || (prologues = [])).push(prologue);
}
node.pos = pos;
node.prologues = prologues || emptyArray;
node.getLineAndCharacterOfPosition = pos => getLineAndCharacterOfPosition(node, pos);
return node;
}
+13 -4
View File
@@ -140,7 +140,7 @@ namespace ts {
exit();
}
function appendSourceMap(generatedLine: number, generatedCharacter: number, map: RawSourceMap, sourceMapPath: string, startLine: number) {
function appendSourceMap(generatedLine: number, generatedCharacter: number, map: RawSourceMap, sourceMapPath: string, start?: LineAndCharacter, end?: LineAndCharacter) {
Debug.assert(generatedLine >= pendingGeneratedLine, "generatedLine cannot backtrack");
Debug.assert(generatedCharacter >= 0, "generatedCharacter cannot be negative");
enter();
@@ -149,7 +149,15 @@ namespace ts {
let nameIndexToNewNameIndexMap: number[] | undefined;
const mappingIterator = decodeMappings(map.mappings);
for (let { value: raw, done } = mappingIterator.next(); !done; { value: raw, done } = mappingIterator.next()) {
if (raw.generatedLine < startLine) {
if (end && (
raw.generatedLine > end.line ||
(raw.generatedLine === end.line && raw.generatedCharacter > end.character))) {
break;
}
if (start && (
raw.generatedLine < start.line ||
(start.line === raw.generatedLine && raw.generatedCharacter < start.character))) {
continue;
}
// Then reencode all the updated mappings into the overall map
@@ -181,9 +189,10 @@ namespace ts {
}
}
const rawGeneratedLine = raw.generatedLine - startLine;
const rawGeneratedLine = raw.generatedLine - (start ? start.line : 0);
const newGeneratedLine = rawGeneratedLine + generatedLine;
const newGeneratedCharacter = rawGeneratedLine === 0 ? raw.generatedCharacter + generatedCharacter : raw.generatedCharacter;
const rawGeneratedCharacter = start && start.line === raw.generatedLine ? raw.generatedCharacter - start.character : raw.generatedCharacter;
const newGeneratedCharacter = rawGeneratedLine === 0 ? rawGeneratedCharacter + generatedCharacter : rawGeneratedCharacter;
addMapping(newGeneratedLine, newGeneratedCharacter, newSourceIndex, newSourceLine, newSourceCharacter, newNameIndex);
}
exit();
+10 -1
View File
@@ -428,6 +428,7 @@ namespace ts {
// Enum
EnumMember,
UnparsedPrologue,
// Top-level nodes
SourceFile,
Bundle,
@@ -2775,13 +2776,21 @@ namespace ts {
kind: SyntaxKind.UnparsedSource;
fileName?: string;
text: string;
prologues: ReadonlyArray<UnparsedPrologue>;
sourceMapPath?: string;
sourceMapText?: string;
/*@internal*/ parsedSourceMap?: RawSourceMap | false | undefined;
// Adding this to satisfy services, fix later
/*@internal*/
getLineAndCharacterOfPosition(pos: number): LineAndCharacter;
}
export interface UnparsedPrologue extends Node {
kind: SyntaxKind.UnparsedSource;
text: string;
parent: UnparsedSource;
}
export interface JsonSourceFile extends SourceFile {
statements: NodeArray<JsonObjectExpressionStatement>;
}
@@ -5531,7 +5540,7 @@ namespace ts {
/**
* Appends a source map.
*/
appendSourceMap(generatedLine: number, generatedCharacter: number, sourceMap: RawSourceMap, sourceMapPath: string, startLine: number): void;
appendSourceMap(generatedLine: number, generatedCharacter: number, sourceMap: RawSourceMap, sourceMapPath: string, start?: LineAndCharacter, end?: LineAndCharacter): void;
/**
* Gets the source map as a `RawSourceMap` object.
*/
+4
View File
@@ -5979,6 +5979,10 @@ namespace ts {
return node.kind === SyntaxKind.UnparsedSource;
}
export function isUnparsedPrologue(node: Node): node is UnparsedPrologue {
return node.kind === SyntaxKind.UnparsedPrologue;
}
// JSDoc
export function isJSDocTypeExpression(node: Node): node is JSDocTypeExpression {