|
6 | 6 | * found in the LICENSE file at https://angular.io/license
|
7 | 7 | */
|
8 | 8 |
|
9 |
| -import {AssertNotNull, BinaryOperator, BinaryOperatorExpr, BuiltinMethod, BuiltinVar, CastExpr, ClassStmt, CommaExpr, CommentStmt, CompileIdentifierMetadata, ConditionalExpr, DeclareFunctionStmt, DeclareVarStmt, ExpressionStatement, ExpressionVisitor, ExternalExpr, ExternalReference, FunctionExpr, IfStmt, InstantiateExpr, InvokeFunctionExpr, InvokeMethodExpr, LiteralArrayExpr, LiteralExpr, LiteralMapExpr, NotExpr, ParseSourceSpan, ReadKeyExpr, ReadPropExpr, ReadVarExpr, ReturnStatement, Statement, StatementVisitor, StaticSymbol, StmtModifier, ThrowStmt, TryCatchStmt, WriteKeyExpr, WritePropExpr, WriteVarExpr} from '@angular/compiler'; |
| 9 | +import {AssertNotNull, BinaryOperator, BinaryOperatorExpr, BuiltinMethod, BuiltinVar, CastExpr, ClassStmt, CommaExpr, CommentStmt, CompileIdentifierMetadata, ConditionalExpr, DeclareFunctionStmt, DeclareVarStmt, ExpressionStatement, ExpressionVisitor, ExternalExpr, ExternalReference, FunctionExpr, IfStmt, InstantiateExpr, InvokeFunctionExpr, InvokeMethodExpr, LiteralArrayExpr, LiteralExpr, LiteralMapExpr, NotExpr, ParseSourceFile, ParseSourceSpan, ReadKeyExpr, ReadPropExpr, ReadVarExpr, ReturnStatement, Statement, StatementVisitor, StaticSymbol, StmtModifier, ThrowStmt, TryCatchStmt, WriteKeyExpr, WritePropExpr, WriteVarExpr} from '@angular/compiler'; |
10 | 10 | import * as ts from 'typescript';
|
11 | 11 |
|
12 | 12 | export interface Node { sourceSpan: ParseSourceSpan|null; }
|
@@ -63,8 +63,10 @@ function createLiteral(value: any) {
|
63 | 63 | */
|
64 | 64 | class _NodeEmitterVisitor implements StatementVisitor, ExpressionVisitor {
|
65 | 65 | private _nodeMap = new Map<ts.Node, Node>();
|
| 66 | + private _mapped = new Set<Node>(); |
66 | 67 | private _importsWithPrefixes = new Map<string, string>();
|
67 | 68 | private _reexports = new Map<string, {name: string, as: string}[]>();
|
| 69 | + private _templateSources = new Map<ParseSourceFile, ts.SourceMapSource>(); |
68 | 70 |
|
69 | 71 | getReexports(): ts.Statement[] {
|
70 | 72 | return Array.from(this._reexports.entries())
|
@@ -93,11 +95,34 @@ class _NodeEmitterVisitor implements StatementVisitor, ExpressionVisitor {
|
93 | 95 | private record<T extends ts.Node>(ngNode: Node, tsNode: T|null): RecordedNode<T> {
|
94 | 96 | if (tsNode && !this._nodeMap.has(tsNode)) {
|
95 | 97 | this._nodeMap.set(tsNode, ngNode);
|
| 98 | + if (!this._mapped.has(ngNode)) { |
| 99 | + this._mapped.add(ngNode); |
| 100 | + const range = this.sourceRangeOf(ngNode); |
| 101 | + if (range) { |
| 102 | + ts.setSourceMapRange(tsNode, range); |
| 103 | + } |
| 104 | + } |
96 | 105 | ts.forEachChild(tsNode, child => this.record(ngNode, tsNode));
|
97 | 106 | }
|
98 | 107 | return tsNode as RecordedNode<T>;
|
99 | 108 | }
|
100 | 109 |
|
| 110 | + private sourceRangeOf(node: Node): ts.SourceMapRange|null { |
| 111 | + if (node.sourceSpan) { |
| 112 | + const span = node.sourceSpan; |
| 113 | + if (span.start.file == span.end.file) { |
| 114 | + const file = span.start.file; |
| 115 | + let source = this._templateSources.get(file); |
| 116 | + if (!source) { |
| 117 | + source = ts.createSourceMapSource(file.url, file.content, pos => pos); |
| 118 | + this._templateSources.set(file, source); |
| 119 | + } |
| 120 | + return {pos: span.start.offset, end: span.end.offset, source}; |
| 121 | + } |
| 122 | + } |
| 123 | + return null; |
| 124 | + } |
| 125 | + |
101 | 126 | private getModifiers(stmt: Statement) {
|
102 | 127 | let modifiers: ts.Modifier[] = [];
|
103 | 128 | if (stmt.hasModifier(StmtModifier.Exported)) {
|
|
0 commit comments