From bbeb485405911351f590f7389d7f4f461f445125 Mon Sep 17 00:00:00 2001 From: Ryan Nowak Date: Thu, 16 Feb 2017 14:11:56 -0800 Subject: [PATCH] Refactor ParserVisitor We need the visitor to allow control over whether to recurse or not into something. This change makes the old ParserVisitor class behave much more like the newer IR Walkers. We need this for the tokens refactor because IR lowering will not be just a trivial visitor anymore in the future. --- .../DefaultDirectiveSyntaxTreePass.cs | 7 +- .../DefaultRazorIRLoweringPhase.cs | 124 +++++++++--------- .../Legacy/AttributeBlockChunkGenerator.cs | 9 +- .../Legacy/DirectiveChunkGenerator.cs | 8 +- .../DynamicAttributeBlockChunkGenerator.cs | 9 +- .../Legacy/ExpressionChunkGenerator.cs | 9 +- .../Legacy/IParentChunkGenerator.cs | 4 +- .../Legacy/ParentChunkGenerator.cs | 13 +- .../Legacy/ParserVisitor.cs | 67 +++------- .../Legacy/RazorCommentChunkGenerator.cs | 9 +- .../Legacy/TagHelperChunkGenerator.cs | 9 +- .../Legacy/TemplateBlockChunkGenerator.cs | 9 +- 12 files changed, 103 insertions(+), 174 deletions(-) diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/DefaultDirectiveSyntaxTreePass.cs b/src/Microsoft.AspNetCore.Razor.Evolution/DefaultDirectiveSyntaxTreePass.cs index ed33aa4ae4..db5383cd62 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/DefaultDirectiveSyntaxTreePass.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/DefaultDirectiveSyntaxTreePass.cs @@ -38,7 +38,7 @@ namespace Microsoft.AspNetCore.Razor.Evolution tree.Root.Accept(this); } - public override void VisitStartDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) + public override void VisitDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) { if (_nestedLevel > 0) { @@ -51,10 +51,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution } _nestedLevel++; - } - public override void VisitEndDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) - { + VisitDefault(block); + _nestedLevel--; } } diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/DefaultRazorIRLoweringPhase.cs b/src/Microsoft.AspNetCore.Razor.Evolution/DefaultRazorIRLoweringPhase.cs index b7bc7875fa..53ec9cb731 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/DefaultRazorIRLoweringPhase.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/DefaultRazorIRLoweringPhase.cs @@ -96,30 +96,6 @@ namespace Microsoft.AspNetCore.Razor.Evolution } } - public override void VisitDirectiveToken(DirectiveTokenChunkGenerator chunkGenerator, Span span) - { - _builder.Add(new DirectiveTokenIRNode() - { - Content = span.Content, - Descriptor = chunkGenerator.Descriptor, - Source = BuildSourceSpanFromNode(span), - }); - } - - public override void VisitStartDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) - { - _builder.Push(new DirectiveIRNode() - { - Name = chunkGenerator.Descriptor.Name, - Descriptor = chunkGenerator.Descriptor, - }); - } - - public override void VisitEndDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) - { - _builder.Pop(); - } - public override void VisitAddTagHelperSpan(AddTagHelperChunkGenerator chunkGenerator, Span span) { _builder.Push(new DirectiveIRNode() @@ -211,25 +187,32 @@ namespace Microsoft.AspNetCore.Razor.Evolution { if (_insideLineDirective) { - base.VisitDirectiveToken(chunkGenerator, span); + _builder.Add(new DirectiveTokenIRNode() + { + Content = span.Content, + Descriptor = chunkGenerator.Descriptor, + Source = BuildSourceSpanFromNode(span), + }); } } - public override void VisitStartDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) + public override void VisitDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) { if (chunkGenerator.Descriptor.Kind == DirectiveDescriptorKind.SingleLine) { _insideLineDirective = true; - base.VisitStartDirectiveBlock(chunkGenerator, block); - } - } - public override void VisitEndDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) - { - if (_insideLineDirective) - { + _builder.Push(new DirectiveIRNode() + { + Name = chunkGenerator.Descriptor.Name, + Descriptor = chunkGenerator.Descriptor, + }); + + base.VisitDirectiveBlock(chunkGenerator, block); + + _builder.Pop(); + _insideLineDirective = false; - base.VisitEndDirectiveBlock(chunkGenerator, block); } } } @@ -243,12 +226,35 @@ namespace Microsoft.AspNetCore.Razor.Evolution { } + public override void VisitDirectiveToken(DirectiveTokenChunkGenerator chunkGenerator, Span span) + { + _builder.Add(new DirectiveTokenIRNode() + { + Content = span.Content, + Descriptor = chunkGenerator.Descriptor, + Source = BuildSourceSpanFromNode(span), + }); + } + + public override void VisitDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) + { + _builder.Push(new DirectiveIRNode() + { + Name = chunkGenerator.Descriptor.Name, + Descriptor = chunkGenerator.Descriptor, + }); + + VisitDefault(block); + + _builder.Pop(); + } + // Example // // Name=checked // Prefix= checked=" // Suffix=" - public override void VisitStartAttributeBlock(AttributeBlockChunkGenerator chunkGenerator, Block block) + public override void VisitAttributeBlock(AttributeBlockChunkGenerator chunkGenerator, Block block) { _builder.Push(new HtmlAttributeIRNode() { @@ -257,10 +263,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution Suffix = chunkGenerator.Suffix, Source = BuildSourceSpanFromNode(block), }); - } - public override void VisitEndAttributeBlock(AttributeBlockChunkGenerator chunkGenerator, Block block) - { + VisitDefault(block); + _builder.Pop(); } @@ -268,17 +273,16 @@ namespace Microsoft.AspNetCore.Razor.Evolution // // Prefix= (space) // Children will contain a token for @false. - public override void VisitStartDynamicAttributeBlock(DynamicAttributeBlockChunkGenerator chunkGenerator, Block block) + public override void VisitDynamicAttributeBlock(DynamicAttributeBlockChunkGenerator chunkGenerator, Block block) { _builder.Push(new CSharpAttributeValueIRNode() { Prefix = chunkGenerator.Prefix, Source = BuildSourceSpanFromNode(block), }); - } - public override void VisitEndDynamicAttributeBlock(DynamicAttributeBlockChunkGenerator chunkGenerator, Block block) - { + VisitDefault(block); + _builder.Pop(); } @@ -292,14 +296,15 @@ namespace Microsoft.AspNetCore.Razor.Evolution }); } - public override void VisitStartTemplateBlock(TemplateBlockChunkGenerator chunkGenerator, Block block) + public override void VisitTemplateBlock(TemplateBlockChunkGenerator chunkGenerator, Block block) { - _builder.Push(new TemplateIRNode()); - } + var templateNode = new TemplateIRNode(); + _builder.Push(templateNode); - public override void VisitEndTemplateBlock(TemplateBlockChunkGenerator chunkGenerator, Block block) - { - var templateNode = _builder.Pop(); + VisitDefault(block); + + _builder.Pop(); + if (templateNode.Children.Count > 0) { var sourceRangeStart = templateNode @@ -327,14 +332,14 @@ namespace Microsoft.AspNetCore.Razor.Evolution // @DateTime.@*This is a comment*@Now // // We need to capture this in the IR so that we can give each piece the correct source mappings - public override void VisitStartExpressionBlock(ExpressionChunkGenerator chunkGenerator, Block block) + public override void VisitExpressionBlock(ExpressionChunkGenerator chunkGenerator, Block block) { - _builder.Push(new CSharpExpressionIRNode()); - } + var expressionNode = new CSharpExpressionIRNode(); + _builder.Push(expressionNode); - public override void VisitEndExpressionBlock(ExpressionChunkGenerator chunkGenerator, Block block) - { - var expressionNode = _builder.Pop(); + VisitDefault(block); + + _builder.Pop(); if (expressionNode.Children.Count > 0) { @@ -445,7 +450,7 @@ namespace Microsoft.AspNetCore.Razor.Evolution } } - public override void VisitStartTagHelperBlock(TagHelperChunkGenerator chunkGenerator, Block block) + public override void VisitTagHelperBlock(TagHelperChunkGenerator chunkGenerator, Block block) { var tagHelperBlock = block as TagHelperBlock; if (tagHelperBlock == null) @@ -471,15 +476,8 @@ namespace Microsoft.AspNetCore.Razor.Evolution TagName = tagName, TagMode = tagHelperBlock.TagMode }); - } - public override void VisitEndTagHelperBlock(TagHelperChunkGenerator chunkGenerator, Block block) - { - var tagHelperBlock = block as TagHelperBlock; - if (tagHelperBlock == null) - { - return; - } + VisitDefault(block); _builder.Pop(); // Pop InitializeTagHelperStructureIRNode diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/AttributeBlockChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/AttributeBlockChunkGenerator.cs index 544eb59bf3..ae55158a0e 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/AttributeBlockChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/AttributeBlockChunkGenerator.cs @@ -36,14 +36,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy //context.ChunkTreeBuilder.EndParentChunk(); } - public override void AcceptStart(ParserVisitor visitor, Block block) + public override void Accept(ParserVisitor visitor, Block block) { - visitor.VisitStartAttributeBlock(this, block); - } - - public override void AcceptEnd(ParserVisitor visitor, Block block) - { - visitor.VisitEndAttributeBlock(this, block); + visitor.VisitAttributeBlock(this, block); } public override string ToString() diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DirectiveChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DirectiveChunkGenerator.cs index b3d2570bd4..6e67cb13f4 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DirectiveChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DirectiveChunkGenerator.cs @@ -17,15 +17,11 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy public DirectiveDescriptor Descriptor { get; } - public override void AcceptStart(ParserVisitor visitor, Block block) + public override void Accept(ParserVisitor visitor, Block block) { - visitor.VisitStartDirectiveBlock(this, block); + visitor.VisitDirectiveBlock(this, block); } - public override void AcceptEnd(ParserVisitor visitor, Block block) - { - visitor.VisitEndDirectiveBlock(this, block); - } public override bool Equals(object obj) { var other = obj as DirectiveChunkGenerator; diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DynamicAttributeBlockChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DynamicAttributeBlockChunkGenerator.cs index 735e81e3cb..7b60e9c8ed 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DynamicAttributeBlockChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/DynamicAttributeBlockChunkGenerator.cs @@ -23,14 +23,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy public SourceLocation ValueStart { get; } - public override void AcceptStart(ParserVisitor visitor, Block block) + public override void Accept(ParserVisitor visitor, Block block) { - visitor.VisitStartDynamicAttributeBlock(this, block); - } - - public override void AcceptEnd(ParserVisitor visitor, Block block) - { - visitor.VisitEndDynamicAttributeBlock(this, block); + visitor.VisitDynamicAttributeBlock(this, block); } public override void GenerateStartParentChunk(Block target, ChunkGeneratorContext context) diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ExpressionChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ExpressionChunkGenerator.cs index 08d7e3d1d1..f76d5829f4 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ExpressionChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ExpressionChunkGenerator.cs @@ -29,14 +29,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy visitor.VisitExpressionSpan(this, span); } - public void AcceptStart(ParserVisitor visitor, Block block) + public void Accept(ParserVisitor visitor, Block block) { - visitor.VisitStartExpressionBlock(this, block); - } - - public void AcceptEnd(ParserVisitor visitor, Block block) - { - visitor.VisitEndExpressionBlock(this, block); + visitor.VisitExpressionBlock(this, block); } public override string ToString() diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/IParentChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/IParentChunkGenerator.cs index 072752042b..7f4b762c82 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/IParentChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/IParentChunkGenerator.cs @@ -7,7 +7,7 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy { void GenerateStartParentChunk(Block target, ChunkGeneratorContext context); void GenerateEndParentChunk(Block target, ChunkGeneratorContext context); - void AcceptStart(ParserVisitor visitor, Block block); - void AcceptEnd(ParserVisitor visitor, Block block); + + void Accept(ParserVisitor visitor, Block block); } } diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParentChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParentChunkGenerator.cs index dfa047594d..1f2387a8f3 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParentChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParentChunkGenerator.cs @@ -9,8 +9,7 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy public static readonly IParentChunkGenerator Null = new NullParentChunkGenerator(); - public abstract void AcceptStart(ParserVisitor visitor, Block block); - public abstract void AcceptEnd(ParserVisitor visitor, Block block); + public abstract void Accept(ParserVisitor visitor, Block block); public virtual void GenerateStartParentChunk(Block target, ChunkGeneratorContext context) { @@ -46,12 +45,12 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy return "None"; } - public void AcceptStart(ParserVisitor visitor, Block block) - { - } - - public void AcceptEnd(ParserVisitor visitor, Block block) + public void Accept(ParserVisitor visitor, Block block) { + for (var i = 0; i < block.Children.Count; i++) + { + block.Children[i].Accept(visitor); + } } } } diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParserVisitor.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParserVisitor.cs index de5b5ac1e7..aa96f6bc3f 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParserVisitor.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/ParserVisitor.cs @@ -5,31 +5,19 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy { internal abstract class ParserVisitor { - public virtual void VisitBlock(Block block) + protected virtual void VisitDefault(Block block) { - VisitStartBlock(block); - for (var i = 0; i < block.Children.Count; i++) { block.Children[i].Accept(this); } - - VisitEndBlock(block); } - public virtual void VisitStartBlock(Block block) + public virtual void VisitBlock(Block block) { if (block.ChunkGenerator != null) { - block.ChunkGenerator.AcceptStart(this, block); - } - } - - public virtual void VisitEndBlock(Block block) - { - if (block.ChunkGenerator != null) - { - block.ChunkGenerator.AcceptEnd(this, block); + block.ChunkGenerator.Accept(this, block); } } @@ -41,28 +29,19 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy } } - public virtual void VisitStartDynamicAttributeBlock(DynamicAttributeBlockChunkGenerator chunkGenerator, Block block) + public virtual void VisitDynamicAttributeBlock(DynamicAttributeBlockChunkGenerator chunkGenerator, Block block) { + VisitDefault(block); } - public virtual void VisitEndDynamicAttributeBlock(DynamicAttributeBlockChunkGenerator chunkGenerator, Block block) + public virtual void VisitExpressionBlock(ExpressionChunkGenerator chunkGenerator, Block block) { + VisitDefault(block); } - public virtual void VisitStartExpressionBlock(ExpressionChunkGenerator chunkGenerator, Block block) - { - } - - public virtual void VisitEndExpressionBlock(ExpressionChunkGenerator chunkGenerator, Block block) - { - } - - public virtual void VisitStartAttributeBlock(AttributeBlockChunkGenerator chunkGenerator, Block block) - { - } - - public virtual void VisitEndAttributeBlock(AttributeBlockChunkGenerator chunkGenerator, Block block) + public virtual void VisitAttributeBlock(AttributeBlockChunkGenerator chunkGenerator, Block block) { + VisitDefault(block); } public virtual void VisitExpressionSpan(ExpressionChunkGenerator chunkGenerator, Span span) @@ -89,36 +68,24 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy { } - public virtual void VisitEndTemplateBlock(TemplateBlockChunkGenerator chunkGenerator, Block block) + public virtual void VisitDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) { + VisitDefault(block); } - public virtual void VisitStartDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) + public virtual void VisitTemplateBlock(TemplateBlockChunkGenerator chunkGenerator, Block block) { + VisitDefault(block); } - public virtual void VisitEndDirectiveBlock(DirectiveChunkGenerator chunkGenerator, Block block) + public virtual void VisitCommentBlock(RazorCommentChunkGenerator chunkGenerator, Block block) { + VisitDefault(block); } - public virtual void VisitStartTemplateBlock(TemplateBlockChunkGenerator chunkGenerator, Block block) - { - } - - public virtual void VisitEndCommentBlock(RazorCommentChunkGenerator chunkGenerator, Block block) - { - } - - public virtual void VisitStartCommentBlock(RazorCommentChunkGenerator chunkGenerator, Block block) - { - } - - public virtual void VisitStartTagHelperBlock(TagHelperChunkGenerator chunkGenerator, Block block) - { - } - - public virtual void VisitEndTagHelperBlock(TagHelperChunkGenerator chunkGenerator, Block block) + public virtual void VisitTagHelperBlock(TagHelperChunkGenerator chunkGenerator, Block block) { + VisitDefault(block); } public virtual void VisitAddTagHelperSpan(AddTagHelperChunkGenerator chunkGenerator, Span span) diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/RazorCommentChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/RazorCommentChunkGenerator.cs index 73d32d1006..eb96550f48 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/RazorCommentChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/RazorCommentChunkGenerator.cs @@ -5,14 +5,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy { internal class RazorCommentChunkGenerator : ParentChunkGenerator { - public override void AcceptStart(ParserVisitor visitor, Block block) + public override void Accept(ParserVisitor visitor, Block block) { - visitor.VisitStartCommentBlock(this, block); - } - - public override void AcceptEnd(ParserVisitor visitor, Block block) - { - visitor.VisitEndCommentBlock(this, block); + visitor.VisitCommentBlock(this, block); } } } diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TagHelperChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TagHelperChunkGenerator.cs index 39f19000e6..b9c42fb6fc 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TagHelperChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TagHelperChunkGenerator.cs @@ -84,14 +84,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy //context.ChunkTreeBuilder.EndParentChunk(); } - public override void AcceptStart(ParserVisitor visitor, Block block) + public override void Accept(ParserVisitor visitor, Block block) { - visitor.VisitStartTagHelperBlock(this, block); - } - - public override void AcceptEnd(ParserVisitor visitor, Block block) - { - visitor.VisitEndTagHelperBlock(this, block); + visitor.VisitTagHelperBlock(this, block); } } } \ No newline at end of file diff --git a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TemplateBlockChunkGenerator.cs b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TemplateBlockChunkGenerator.cs index 2358e35629..54cc3874ba 100644 --- a/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TemplateBlockChunkGenerator.cs +++ b/src/Microsoft.AspNetCore.Razor.Evolution/Legacy/TemplateBlockChunkGenerator.cs @@ -5,14 +5,9 @@ namespace Microsoft.AspNetCore.Razor.Evolution.Legacy { internal class TemplateBlockChunkGenerator : ParentChunkGenerator { - public override void AcceptStart(ParserVisitor visitor, Block block) + public override void Accept(ParserVisitor visitor, Block block) { - visitor.VisitStartTemplateBlock(this, block); - } - - public override void AcceptEnd(ParserVisitor visitor, Block block) - { - visitor.VisitEndTemplateBlock(this, block); + visitor.VisitTemplateBlock(this, block); } public override void GenerateStartParentChunk(Block target, ChunkGeneratorContext context)