Skip to content

Commit f6148d6

Browse files
authored
refactor: rewrite transform (#273)
1 parent 430d2d7 commit f6148d6

File tree

10 files changed

+622
-587
lines changed

10 files changed

+622
-587
lines changed

jest.config.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ export default {
1515
moduleNameMapper: {
1616
'^(\\.{1,2}/.*)\\.js$': '$1',
1717
},
18-
coverageReporters: ['lcov', 'text-summary'],
18+
coverageReporters: ['text', 'lcov', 'text-summary'],
1919
collectCoverage: !!process.env.ENABLE_COVERAGE,
2020
collectCoverageFrom: ['src/**/*.ts'],
2121
coverageThreshold: {

src/index.ts

Lines changed: 20 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,27 @@
11
import type * as ng from '@angular/compiler';
2-
import type * as b from '@babel/types';
3-
import { Context } from './context.js';
4-
import { transform } from './transform.js';
2+
import transformComment from './transform-comment.js';
3+
import transformNode from './transform-node.js';
54
import { transformTemplateBindings } from './transform-microsyntax.js';
6-
import type { NGNode, RawNGComment, NGMicrosyntax } from './types.js';
5+
import type {
6+
NGNode,
7+
RawNGComment,
8+
NGMicrosyntax,
9+
ParseResult,
10+
} from './types.js';
711
import * as angularParser from './parser.js';
12+
import { type Context } from './context.js';
813

914
function createParser(
10-
parse: (input: string) => { ast: ng.AST; comments: RawNGComment[] },
15+
parse: (text: string) => {
16+
ast: ng.AST;
17+
comments: RawNGComment[];
18+
context: Context;
19+
},
1120
) {
12-
return (input: string) => {
13-
const { ast: rawNgAst, comments } = parse(input);
14-
const context = new Context(input);
15-
const ast = transform(rawNgAst, context) as NGNode;
16-
ast.comments = comments.map((comment) =>
17-
transform(comment, context),
18-
) as b.CommentLine[];
21+
return (text: string) => {
22+
const { ast: angularNode, comments, context } = parse(text);
23+
const ast = transformNode(angularNode, context) as ParseResult;
24+
ast.comments = comments.map((comment) => transformComment(comment));
1925
return ast;
2026
};
2127
}
@@ -28,9 +34,6 @@ export const parseInterpolationExpression = createParser(
2834
angularParser.parseInterpolationExpression,
2935
);
3036
export const parseAction = createParser(angularParser.parseAction);
31-
export const parseTemplateBindings = (input: string): NGMicrosyntax =>
32-
transformTemplateBindings(
33-
angularParser.parseTemplateBindings(input),
34-
new Context(input),
35-
);
37+
export const parseTemplateBindings = (text: string): NGMicrosyntax =>
38+
transformTemplateBindings(angularParser.parseTemplateBindings(text));
3639
export type { NGMicrosyntax, NGNode };

src/parser.ts

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import {
66
type ParserError,
77
} from '@angular/compiler';
88
import { type RawNGComment } from './types.js';
9+
import { Context } from './context.js';
910

1011
const NG_PARSE_FAKE_LOCATION = 'angular-estree-parser';
1112
const NG_PARSE_TEMPLATE_BINDINGS_FAKE_PREFIX = 'NgEstreeParser';
@@ -23,11 +24,12 @@ function parse(
2324
text: string,
2425
parse: (text: string, parser: Parser) => ASTWithSource,
2526
) {
27+
const context = new Context(text);
2628
const parser = createParser();
2729
const { text: textToParse, comments } = extractComments(text, parser);
2830
const { ast, errors } = parse(textToParse, parser);
2931
assertAstErrors(errors);
30-
return { ast, comments };
32+
return { ast, comments, context };
3133
}
3234

3335
function parseBinding(text: string) {
@@ -60,16 +62,18 @@ function parseInterpolationExpression(text: string) {
6062
}
6163

6264
function parseTemplateBindings(text: string) {
65+
const context = new Context(text);
6366
const parser = createParser();
64-
const { templateBindings: ast, errors } = parser.parseTemplateBindings(
65-
NG_PARSE_TEMPLATE_BINDINGS_FAKE_PREFIX,
66-
text,
67-
NG_PARSE_FAKE_LOCATION,
68-
NG_PARSE_FAKE_ABSOLUTE_OFFSET,
69-
NG_PARSE_FAKE_ABSOLUTE_OFFSET,
70-
);
67+
const { templateBindings: expressions, errors } =
68+
parser.parseTemplateBindings(
69+
NG_PARSE_TEMPLATE_BINDINGS_FAKE_PREFIX,
70+
text,
71+
NG_PARSE_FAKE_LOCATION,
72+
NG_PARSE_FAKE_ABSOLUTE_OFFSET,
73+
NG_PARSE_FAKE_ABSOLUTE_OFFSET,
74+
);
7175
assertAstErrors(errors);
72-
return ast;
76+
return { expressions, context };
7377
}
7478

7579
function assertAstErrors(errors: ParserError[]) {

src/transform-comment.ts

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
import type { RawNGComment } from './types.js';
2+
import type { CommentLine } from '@babel/types';
3+
import { sourceSpanToLocationInformation } from './utils.js';
4+
5+
function transformComment(comment: RawNGComment): CommentLine {
6+
const { value, sourceSpan } = comment;
7+
return {
8+
type: 'CommentLine',
9+
value,
10+
...sourceSpanToLocationInformation(sourceSpan),
11+
};
12+
}
13+
14+
export default transformComment;

src/transform-microsyntax.ts

Lines changed: 17 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,7 @@ import {
44
VariableBinding as NGVariableBinding,
55
} from '@angular/compiler';
66
import { type Context } from './context.js';
7-
import {
8-
type InputNode,
9-
type OutputNode,
10-
transform,
11-
transformSpan,
12-
} from './transform.js';
7+
import transformNode from './transform-node.js';
138
import type {
149
NGMicrosyntax,
1510
NGMicrosyntaxAs,
@@ -22,12 +17,15 @@ import type {
2217
RawNGSpan,
2318
} from './types.js';
2419
import { NG_PARSE_TEMPLATE_BINDINGS_FAKE_PREFIX } from './parser.js';
25-
import { toLowerCamelCase } from './utils.js';
20+
import { toLowerCamelCase, transformSpan } from './utils.js';
2621

27-
export function transformTemplateBindings(
28-
rawTemplateBindings: ng.TemplateBinding[],
29-
context: Context,
30-
): NGMicrosyntax {
22+
function transformTemplateBindings({
23+
expressions: rawTemplateBindings,
24+
context,
25+
}: {
26+
expressions: ng.TemplateBinding[];
27+
context: Context;
28+
}): NGMicrosyntax {
3129
rawTemplateBindings.forEach(fixTemplateBindingSpan);
3230

3331
const [firstTemplateBinding] = rawTemplateBindings;
@@ -62,7 +60,7 @@ export function transformTemplateBindings(
6260
);
6361
const updateSpanEnd = <T extends NGNode>(node: T, end: number): T => ({
6462
...node,
65-
...transformSpan({ start: node.start!, end }, context),
63+
...transformSpan({ start: node.start!, end }, context.text),
6664
});
6765
const updateExpressionAlias = (expression: NGMicrosyntaxExpression) => ({
6866
...updateSpanEnd(expression, alias.end),
@@ -180,21 +178,21 @@ export function transformTemplateBindings(
180178
}
181179
}
182180

183-
function _t<T extends OutputNode>(n: InputNode) {
184-
return transform(n, context) as T & RawNGSpan;
181+
function _t<T extends NGNode>(n: ng.AST) {
182+
return transformNode(n, context) as T;
185183
}
186184

187-
function _c<T extends OutputNode>(
185+
function _c<T extends NGNode>(
188186
t: T['type'],
189187
n: Partial<T>,
190188
span: RawNGSpan,
191189
stripSpaces = true,
192190
) {
193191
return {
194192
type: t,
195-
...transformSpan(span, context, stripSpaces),
193+
...transformSpan(span, context.text, { processSpan: stripSpaces }),
196194
...n,
197-
} as T & { start: number; end: number; range: [number, number] };
195+
} as T;
198196
}
199197

200198
function removePrefix(string: string) {
@@ -271,3 +269,5 @@ export function transformTemplateBindings(
271269
};
272270
}
273271
}
272+
273+
export { transformTemplateBindings };

0 commit comments

Comments
 (0)