diff --git a/packages/compiler/src/template_parser/binding_parser.ts b/packages/compiler/src/template_parser/binding_parser.ts index 1c19d69c9c..ca0001f44e 100644 --- a/packages/compiler/src/template_parser/binding_parser.ts +++ b/packages/compiler/src/template_parser/binding_parser.ts @@ -157,10 +157,12 @@ export class BindingParser { this._parsePropertyAst( key, binding.value, sourceSpan, valueSpan, targetMatchableAttrs, targetProps); } else { - targetMatchableAttrs.push([key, '']); + targetMatchableAttrs.push([key, '' /* value */]); + // Since this is a literal attribute with no RHS, source span should be + // just the key span. this.parseLiteralAttr( - key, null, sourceSpan, absoluteValueOffset, undefined, targetMatchableAttrs, - targetProps); + key, null /* value */, keySpan, absoluteValueOffset, undefined /* valueSpan */, + targetMatchableAttrs, targetProps); } } } diff --git a/packages/compiler/test/render3/r3_ast_spans_spec.ts b/packages/compiler/test/render3/r3_ast_spans_spec.ts index 6fc6b3003b..791b36021f 100644 --- a/packages/compiler/test/render3/r3_ast_spans_spec.ts +++ b/packages/compiler/test/render3/r3_ast_spans_spec.ts @@ -174,7 +174,7 @@ describe('R3 AST source spans', () => { it('is correct for * directives', () => { expectFromHtml('
').toEqual([ ['Template', '0:17', '0:11', '11:17'], - ['TextAttribute', '5:10', ''], + ['TextAttribute', '6:10', ''], // ngIf ['Element', '0:17', '0:11', '11:17'], ]); }); @@ -237,9 +237,9 @@ describe('R3 AST source spans', () => { // expectFromHtml('
').toEqual([ ['Template', '0:38', '0:32', '32:38'], - ['TextAttribute', '5:31', ''], - ['BoundAttribute', '5:31', '25:30'], // *ngFor="let item of items" -> items - ['Variable', '13:22', ''], // let item + ['TextAttribute', '6:11', ''], // ngFor + ['BoundAttribute', '5:31', '25:30'], // *ngFor="let item of items" -> items + ['Variable', '13:22', ''], // let item ['Element', '0:38', '0:32', '32:38'], ]); @@ -260,8 +260,8 @@ describe('R3 AST source spans', () => { it('is correct for variables via let ...', () => { expectFromHtml('
').toEqual([ ['Template', '0:27', '0:21', '21:27'], - ['TextAttribute', '5:20', ''], - ['Variable', '12:19', '18:19'], // let a=b -> b + ['TextAttribute', '6:10', ''], // ngIf + ['Variable', '12:19', '18:19'], // let a=b -> b ['Element', '0:27', '0:21', '21:27'], ]); }); diff --git a/packages/language-service/ivy/test/hybrid_visitor_spec.ts b/packages/language-service/ivy/test/hybrid_visitor_spec.ts index 43820c7e45..8a9d06fc6e 100644 --- a/packages/language-service/ivy/test/hybrid_visitor_spec.ts +++ b/packages/language-service/ivy/test/hybrid_visitor_spec.ts @@ -487,8 +487,9 @@ describe('findNodeAtPosition for microsyntax expression', () => { // expect(errors).toBe(null); const node = findNodeAtPosition(nodes, position); - // TODO: this is currently wrong because it should point to ngFor text - // attribute instead of ngForOf bound attribute + expect(isTemplateNode(node!)).toBeTrue(); + expect(node).toBeInstanceOf(t.TextAttribute); + expect((node as t.TextAttribute).name).toBe('ngFor'); }); it('should locate not let keyword', () => {