Refactor WriteAttribute \ AddHtmlAttribute

Fixes #177
This commit is contained in:
Pranav K 2015-09-29 18:03:22 -07:00
parent ef799223de
commit 3e8b7b607d
11 changed files with 297 additions and 147 deletions

View File

@ -106,11 +106,9 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
public CSharpCodeWriter WriteLocationTaggedString(LocationTagged<string> value) public CSharpCodeWriter WriteLocationTaggedString(LocationTagged<string> value)
{ {
WriteStartMethodInvocation("Tuple.Create");
WriteStringLiteral(value.Value); WriteStringLiteral(value.Value);
WriteParameterSeparator(); WriteParameterSeparator();
Write(value.Location.AbsoluteIndex.ToString(CultureInfo.CurrentCulture)); Write(value.Location.AbsoluteIndex.ToString(CultureInfo.InvariantCulture));
WriteEndMethodInvocation(false);
return this; return this;
} }

View File

@ -3,6 +3,7 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization; using System.Globalization;
using System.Linq; using System.Linq;
using Microsoft.AspNet.Razor.Chunks; using Microsoft.AspNet.Razor.Chunks;
@ -26,6 +27,7 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
private readonly CodeGeneratorContext _context; private readonly CodeGeneratorContext _context;
private readonly IChunkVisitor _bodyVisitor; private readonly IChunkVisitor _bodyVisitor;
private readonly IChunkVisitor _literalBodyVisitor; private readonly IChunkVisitor _literalBodyVisitor;
private readonly TagHelperAttributeCodeVisitor _attributeCodeVisitor;
private readonly GeneratedTagHelperContext _tagHelperContext; private readonly GeneratedTagHelperContext _tagHelperContext;
private readonly bool _designTimeMode; private readonly bool _designTimeMode;
@ -63,6 +65,7 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
_designTimeMode = context.Host.DesignTimeMode; _designTimeMode = context.Host.DesignTimeMode;
_literalBodyVisitor = new CSharpLiteralCodeVisitor(this, writer, context); _literalBodyVisitor = new CSharpLiteralCodeVisitor(this, writer, context);
_attributeCodeVisitor = new TagHelperAttributeCodeVisitor(writer, context);
AttributeValueCodeRenderer = new TagHelperAttributeValueCodeRenderer(); AttributeValueCodeRenderer = new TagHelperAttributeValueCodeRenderer();
} }
@ -467,15 +470,32 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
// Dynamic attribute value should be run through the conditional attribute removal system. It's // Dynamic attribute value should be run through the conditional attribute removal system. It's
// unbound and contains C#. // unbound and contains C#.
// TagHelper attribute rendering is buffered by default. We do not want to write to the current
// writer.
var currentTargetWriter = _context.TargetWriterName;
var currentWriteAttributeMethodName = _context.Host.GeneratedClassContext.WriteAttributeValueMethodName;
_context.TargetWriterName = null;
Debug.Assert(attributeValueChunk is ParentChunk);
var children = ((ParentChunk)attributeValueChunk).Children;
var attributeCount = children.Count(c => c is DynamicCodeAttributeChunk || c is LiteralCodeAttributeChunk);
_writer _writer
.WriteStartMethodInvocation(_tagHelperContext.AddHtmlAttributeValuesMethodName) .WriteStartMethodInvocation(_tagHelperContext.BeginAddHtmlAttributeValuesMethodName)
.Write(ExecutionContextVariableName)
.WriteParameterSeparator()
.WriteStringLiteral(attributeName) .WriteStringLiteral(attributeName)
.WriteParameterSeparator() .WriteParameterSeparator()
.Write(ExecutionContextVariableName); .Write(attributeCount.ToString(CultureInfo.InvariantCulture))
.WriteEndMethodInvocation();
_bodyVisitor.Accept(attributeValueChunk); _attributeCodeVisitor.Accept(attributeValueChunk);
_writer.WriteEndMethodInvocation(); _writer.WriteMethodInvocation(
_tagHelperContext.EndAddHtmlAttributeValuesMethodName,
ExecutionContextVariableName);
_context.TargetWriterName = currentTargetWriter;
} }
else else
{ {
@ -722,5 +742,18 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
} }
} }
} }
private class TagHelperAttributeCodeVisitor : CSharpCodeVisitor
{
public TagHelperAttributeCodeVisitor(
CSharpCodeWriter writer,
CodeGeneratorContext context)
: base(writer, context)
{
}
protected override string WriteAttributeValueMethodName =>
Context.Host.GeneratedClassContext.GeneratedTagHelperContext.AddHtmlAttributeValueMethodName;
}
} }
} }

View File

@ -11,16 +11,22 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
public static readonly string DefaultWriteMethodName = "Write"; public static readonly string DefaultWriteMethodName = "Write";
public static readonly string DefaultWriteLiteralMethodName = "WriteLiteral"; public static readonly string DefaultWriteLiteralMethodName = "WriteLiteral";
public static readonly string DefaultExecuteMethodName = "ExecuteAsync"; public static readonly string DefaultExecuteMethodName = "ExecuteAsync";
public static readonly string DefaultWriteAttributeMethodName = "WriteAttribute"; public static readonly string DefaultBeginWriteAttributeMethodName = "BeginWriteAttribute";
public static readonly string DefaultWriteAttributeToMethodName = "WriteAttributeTo"; public static readonly string DefaultBeginWriteAttributeToMethodName = "BeginWriteAttributeTo";
public static readonly string DefaultEndWriteAttributeMethodName = "EndWriteAttribute";
public static readonly string DefaultEndWriteAttributeToMethodName = "EndWriteAttributeTo";
public static readonly string DefaultWriteAttributeValueMethodName = "WriteAttributeValue";
public static readonly string DefaultWriteAttributeValueToMethodName = "WriteAttributeValueTo";
public static readonly GeneratedClassContext Default = public static readonly GeneratedClassContext Default =
new GeneratedClassContext(DefaultExecuteMethodName, new GeneratedClassContext(
DefaultExecuteMethodName,
DefaultWriteMethodName, DefaultWriteMethodName,
DefaultWriteLiteralMethodName, DefaultWriteLiteralMethodName,
new GeneratedTagHelperContext()); new GeneratedTagHelperContext());
public GeneratedClassContext(string executeMethodName, public GeneratedClassContext(
string executeMethodName,
string writeMethodName, string writeMethodName,
string writeLiteralMethodName, string writeLiteralMethodName,
GeneratedTagHelperContext generatedTagHelperContext) GeneratedTagHelperContext generatedTagHelperContext)
@ -61,11 +67,16 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
TemplateTypeName = null; TemplateTypeName = null;
DefineSectionMethodName = null; DefineSectionMethodName = null;
WriteAttributeMethodName = DefaultWriteAttributeMethodName; BeginWriteAttributeMethodName = DefaultBeginWriteAttributeMethodName;
WriteAttributeToMethodName = DefaultWriteAttributeToMethodName; BeginWriteAttributeToMethodName = DefaultBeginWriteAttributeToMethodName;
EndWriteAttributeMethodName = DefaultEndWriteAttributeMethodName;
EndWriteAttributeToMethodName = DefaultEndWriteAttributeToMethodName;
WriteAttributeValueMethodName = DefaultWriteAttributeValueMethodName;
WriteAttributeValueToMethodName = DefaultWriteAttributeValueToMethodName;
} }
public GeneratedClassContext(string executeMethodName, public GeneratedClassContext(
string executeMethodName,
string writeMethodName, string writeMethodName,
string writeLiteralMethodName, string writeLiteralMethodName,
string writeToMethodName, string writeToMethodName,
@ -82,7 +93,8 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
TemplateTypeName = templateTypeName; TemplateTypeName = templateTypeName;
} }
public GeneratedClassContext(string executeMethodName, public GeneratedClassContext(
string executeMethodName,
string writeMethodName, string writeMethodName,
string writeLiteralMethodName, string writeLiteralMethodName,
string writeToMethodName, string writeToMethodName,
@ -101,7 +113,8 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
DefineSectionMethodName = defineSectionMethodName; DefineSectionMethodName = defineSectionMethodName;
} }
public GeneratedClassContext(string executeMethodName, public GeneratedClassContext(
string executeMethodName,
string writeMethodName, string writeMethodName,
string writeLiteralMethodName, string writeLiteralMethodName,
string writeToMethodName, string writeToMethodName,
@ -137,8 +150,13 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
public string EndContextMethodName { get; set; } public string EndContextMethodName { get; set; }
public string DefineSectionMethodName { get; set; } public string DefineSectionMethodName { get; set; }
public string TemplateTypeName { get; set; } public string TemplateTypeName { get; set; }
public string WriteAttributeMethodName { get; set; }
public string WriteAttributeToMethodName { get; set; } public string BeginWriteAttributeMethodName { get; set; }
public string BeginWriteAttributeToMethodName { get; set; }
public string EndWriteAttributeMethodName { get; set; }
public string EndWriteAttributeToMethodName { get; set; }
public string WriteAttributeValueMethodName { get; set; }
public string WriteAttributeValueToMethodName { get; set; }
public bool AllowSections public bool AllowSections
{ {

View File

@ -13,7 +13,9 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
/// </summary> /// </summary>
public GeneratedTagHelperContext() public GeneratedTagHelperContext()
{ {
AddHtmlAttributeValuesMethodName = "AddHtmlAttributeValues"; BeginAddHtmlAttributeValuesMethodName = "BeginAddHtmlAttributeValues";
EndAddHtmlAttributeValuesMethodName = "EndAddHtmlAttributeValues";
AddHtmlAttributeValueMethodName = "AddHtmlAttributeValue";
CreateTagHelperMethodName = "CreateTagHelper"; CreateTagHelperMethodName = "CreateTagHelper";
RunnerRunAsyncMethodName = "RunAsync"; RunnerRunAsyncMethodName = "RunAsync";
ScopeManagerBeginMethodName = "Begin"; ScopeManagerBeginMethodName = "Begin";
@ -38,18 +40,48 @@ namespace Microsoft.AspNet.Razor.CodeGenerators
} }
/// <summary> /// <summary>
/// The name of the method used to add unbound, complex tag helper attributes to TagHelperExecutionContexts. /// The name of the method used to begin the addition of unbound, complex tag helper attributes to
/// TagHelperExecutionContexts.
/// </summary> /// </summary>
/// <remarks> /// <remarks>
/// Method signature should be /// Method signature should be
/// <code> /// <code>
/// public void AddHtmlAttributeValues( /// public void BeginAddHtmlAttributeValues(
/// string attributeName,
/// TagHelperExecutionContext executionContext, /// TagHelperExecutionContext executionContext,
/// params Microsoft.AspNet.Mvc.Razor.AttributeValue[] values) /// string attributeName)
/// </code> /// </code>
/// </remarks> /// </remarks>
public string AddHtmlAttributeValuesMethodName { get; set; } public string BeginAddHtmlAttributeValuesMethodName { get; set; }
/// <summary>
/// Method name used to end addition of unbound, complex tag helper attributes to TagHelperExecutionContexts.
/// </summary>
/// <remarks>
/// Method signature should be
/// <code>
/// public void EndAddHtmlAttributeValues(
/// TagHelperExecutionContext executionContext)
/// </code>
/// </remarks>
public string EndAddHtmlAttributeValuesMethodName { get; set; }
/// <summary>
/// Method name used to add individual components of an unbound, complex tag helper attribute to
/// TagHelperExecutionContexts.
/// </summary>
/// <remarks>
/// Method signature:
/// <code>
/// public void AddHtmlAttributeValues(
/// string prefix,
/// int prefixOffset,
/// string value,
/// int valueOffset,
/// int valueLength,
/// bool isLiteral)
/// </code>
/// </remarks>
public string AddHtmlAttributeValueMethodName { get; set; }
/// <summary> /// <summary>
/// The name of the method used to create a tag helper. /// The name of the method used to create a tag helper.

View File

@ -80,6 +80,13 @@ namespace Microsoft.AspNet.Razor.CodeGenerators.Visitors
} }
} }
/// <summary>
/// Gets the method name used to generate <c>WriteAttribute</c> invocations in the rendered page.
/// </summary>
/// <remarks>Defaults to <see cref="GeneratedClassContext.WriteAttributeValueMethodName"/></remarks>
protected virtual string WriteAttributeValueMethodName =>
Context.Host.GeneratedClassContext.WriteAttributeValueMethodName;
protected override void Visit(TagHelperChunk chunk) protected override void Visit(TagHelperChunk chunk)
{ {
TagHelperRenderer.RenderTagHelper(chunk); TagHelperRenderer.RenderTagHelper(chunk);
@ -174,36 +181,44 @@ namespace Microsoft.AspNet.Razor.CodeGenerators.Visitors
var currentRenderingMode = Context.ExpressionRenderingMode; var currentRenderingMode = Context.ExpressionRenderingMode;
var currentTargetWriterName = Context.TargetWriterName; var currentTargetWriterName = Context.TargetWriterName;
Context.TargetWriterName = ValueWriterName; if (!string.IsNullOrEmpty(currentTargetWriterName))
{
Writer.WriteStartMethodInvocation(Context.Host.GeneratedClassContext.WriteAttributeValueToMethodName)
.Write(currentTargetWriterName)
.WriteParameterSeparator();
}
else
{
Writer.WriteStartMethodInvocation(WriteAttributeValueMethodName);
}
Writer.WriteParameterSeparator() Context.TargetWriterName = ValueWriterName;
.WriteLine();
var code = chunk.Children.FirstOrDefault(); var code = chunk.Children.FirstOrDefault();
if (code is ExpressionChunk || code is ExpressionBlockChunk) if (code is ExpressionChunk || code is ExpressionBlockChunk)
{ {
Writer.WriteStartMethodInvocation("Tuple.Create") Writer
.WriteLocationTaggedString(chunk.Prefix) .WriteLocationTaggedString(chunk.Prefix)
.WriteParameterSeparator() .WriteParameterSeparator();
.WriteStartMethodInvocation("Tuple.Create", new string[] { "System.Object", "System.Int32" });
Context.ExpressionRenderingMode = ExpressionRenderingMode.InjectCode; Context.ExpressionRenderingMode = ExpressionRenderingMode.InjectCode;
Accept(code); Accept(code);
Writer.WriteParameterSeparator() Writer
.Write(chunk.Start.AbsoluteIndex.ToString(CultureInfo.CurrentCulture)) .WriteParameterSeparator()
.WriteEndMethodInvocation(endLine: false) .Write(chunk.Start.AbsoluteIndex.ToString(CultureInfo.InvariantCulture))
.WriteParameterSeparator()
.Write(chunk.Association.Length.ToString(CultureInfo.InvariantCulture))
.WriteParameterSeparator() .WriteParameterSeparator()
.WriteBooleanLiteral(value: false) .WriteBooleanLiteral(value: false)
.WriteEndMethodInvocation(endLine: false); .WriteEndMethodInvocation();
} }
else else
{ {
Writer.WriteStartMethodInvocation("Tuple.Create") Writer
.WriteLocationTaggedString(chunk.Prefix) .WriteLocationTaggedString(chunk.Prefix)
.WriteParameterSeparator() .WriteParameterSeparator()
.WriteStartMethodInvocation("Tuple.Create", new string[] { "System.Object", "System.Int32" })
.WriteStartNewObject(Context.Host.GeneratedClassContext.TemplateTypeName); .WriteStartNewObject(Context.Host.GeneratedClassContext.TemplateTypeName);
using (Writer.BuildLambda(endLine: false, parameterNames: ValueWriterName)) using (Writer.BuildLambda(endLine: false, parameterNames: ValueWriterName))
@ -211,13 +226,15 @@ namespace Microsoft.AspNet.Razor.CodeGenerators.Visitors
Accept(chunk.Children); Accept(chunk.Children);
} }
Writer.WriteEndMethodInvocation(false) Writer
.WriteEndMethodInvocation(false)
.WriteParameterSeparator() .WriteParameterSeparator()
.Write(chunk.Start.AbsoluteIndex.ToString(CultureInfo.CurrentCulture)) .Write(chunk.Start.AbsoluteIndex.ToString(CultureInfo.InvariantCulture))
.WriteEndMethodInvocation(endLine: false) .WriteParameterSeparator()
.Write(chunk.Association.Length.ToString(CultureInfo.InvariantCulture))
.WriteParameterSeparator() .WriteParameterSeparator()
.WriteBooleanLiteral(false) .WriteBooleanLiteral(false)
.WriteEndMethodInvocation(false); .WriteEndMethodInvocation();
} }
Context.TargetWriterName = currentTargetWriterName; Context.TargetWriterName = currentTargetWriterName;
@ -239,15 +256,23 @@ namespace Microsoft.AspNet.Razor.CodeGenerators.Visitors
return; return;
} }
Writer.WriteParameterSeparator() if (!string.IsNullOrEmpty(Context.TargetWriterName))
.WriteStartMethodInvocation("Tuple.Create") {
Writer.WriteStartMethodInvocation(Context.Host.GeneratedClassContext.WriteAttributeValueToMethodName)
.Write(Context.TargetWriterName)
.WriteParameterSeparator();
}
else
{
Writer.WriteStartMethodInvocation(WriteAttributeValueMethodName);
}
Writer
.WriteLocationTaggedString(chunk.Prefix) .WriteLocationTaggedString(chunk.Prefix)
.WriteParameterSeparator(); .WriteParameterSeparator();
if (visitChildren) if (visitChildren)
{ {
Writer.WriteStartMethodInvocation("Tuple.Create", new string[] { "System.Object", "System.Int32" });
var currentRenderingMode = Context.ExpressionRenderingMode; var currentRenderingMode = Context.ExpressionRenderingMode;
Context.ExpressionRenderingMode = ExpressionRenderingMode.InjectCode; Context.ExpressionRenderingMode = ExpressionRenderingMode.InjectCode;
@ -255,19 +280,24 @@ namespace Microsoft.AspNet.Razor.CodeGenerators.Visitors
Context.ExpressionRenderingMode = currentRenderingMode; Context.ExpressionRenderingMode = currentRenderingMode;
Writer.WriteParameterSeparator() Writer
.Write(chunk.ValueLocation.AbsoluteIndex.ToString(CultureInfo.CurrentCulture)) .WriteParameterSeparator()
.WriteEndMethodInvocation(false) .Write(chunk.ValueLocation.AbsoluteIndex.ToString(CultureInfo.InvariantCulture))
.WriteParameterSeparator()
.Write(chunk.Association.Length.ToString(CultureInfo.InvariantCulture))
.WriteParameterSeparator() .WriteParameterSeparator()
.WriteBooleanLiteral(false) .WriteBooleanLiteral(false)
.WriteEndMethodInvocation(false); .WriteEndMethodInvocation();
} }
else else
{ {
Writer.WriteLocationTaggedString(chunk.Value) Writer
.WriteLocationTaggedString(chunk.Value)
.WriteParameterSeparator()
.Write(chunk.Association.Length.ToString(CultureInfo.InvariantCulture))
.WriteParameterSeparator() .WriteParameterSeparator()
.WriteBooleanLiteral(true) .WriteBooleanLiteral(true)
.WriteEndMethodInvocation(false); .WriteEndMethodInvocation();
} }
} }
@ -283,24 +313,29 @@ namespace Microsoft.AspNet.Razor.CodeGenerators.Visitors
if (!string.IsNullOrEmpty(Context.TargetWriterName)) if (!string.IsNullOrEmpty(Context.TargetWriterName))
{ {
Writer.WriteStartMethodInvocation(Context.Host.GeneratedClassContext.WriteAttributeToMethodName) Writer.WriteStartMethodInvocation(Context.Host.GeneratedClassContext.BeginWriteAttributeToMethodName)
.Write(Context.TargetWriterName) .Write(Context.TargetWriterName)
.WriteParameterSeparator(); .WriteParameterSeparator();
} }
else else
{ {
Writer.WriteStartMethodInvocation(Context.Host.GeneratedClassContext.WriteAttributeMethodName); Writer.WriteStartMethodInvocation(Context.Host.GeneratedClassContext.BeginWriteAttributeMethodName);
} }
var attributeCount = chunk.Children.Count(c => c is LiteralCodeAttributeChunk || c is DynamicCodeAttributeChunk);
Writer.WriteStringLiteral(chunk.Attribute) Writer.WriteStringLiteral(chunk.Attribute)
.WriteParameterSeparator() .WriteParameterSeparator()
.WriteLocationTaggedString(chunk.Prefix) .WriteLocationTaggedString(chunk.Prefix)
.WriteParameterSeparator() .WriteParameterSeparator()
.WriteLocationTaggedString(chunk.Suffix); .WriteLocationTaggedString(chunk.Suffix)
.WriteParameterSeparator()
.Write(attributeCount.ToString(CultureInfo.InvariantCulture))
.WriteEndMethodInvocation();
Accept(chunk.Children); Accept(chunk.Children);
Writer.WriteEndMethodInvocation(); Writer.WriteMethodInvocation(Context.Host.GeneratedClassContext.EndWriteAttributeMethodName);
} }
protected override void Visit(SectionChunk chunk) protected override void Visit(SectionChunk chunk)

View File

@ -239,8 +239,11 @@ if(true) {
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__PTagHelper = CreateTagHelper<PTagHelper>(); __PTagHelper = CreateTagHelper<PTagHelper>();
__tagHelperExecutionContext.Add(__PTagHelper); __tagHelperExecutionContext.Add(__PTagHelper);
AddHtmlAttributeValues("time", __tagHelperExecutionContext, Tuple.Create(Tuple.Create("", 148), Tuple.Create("Current", 148), true), Tuple.Create(Tuple.Create(" ", 155), Tuple.Create("Time:", 156), true), BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "time", 3);
Tuple.Create(Tuple.Create(" ", 161), Tuple.Create<System.Object, System.Int32>(DateTime.Now, 162), false)); AddHtmlAttributeValue("", 148, "Current", 148, 7, true);
AddHtmlAttributeValue(" ", 155, "Time:", 156, 6, true);
AddHtmlAttributeValue(" ", 161, DateTime.Now, 162, 14, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(139, 529, false); Instrumentation.BeginContext(139, 529, false);
await WriteTagHelperAsync(__tagHelperExecutionContext); await WriteTagHelperAsync(__tagHelperExecutionContext);

View File

@ -25,33 +25,41 @@ namespace TestOutput
Instrumentation.BeginContext(46, 28, true); Instrumentation.BeginContext(46, 28, true);
WriteLiteral(" <a href=\"Foo\" />\r\n <p"); WriteLiteral(" <a href=\"Foo\" />\r\n <p");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("class", Tuple.Create(" class=\"", 74), Tuple.Create("\"", 86), BeginWriteAttribute("class", " class=\"", 74, "\"", 86, 1);
Tuple.Create(Tuple.Create("", 82), Tuple.Create<System.Object, System.Int32>(cls, 82), false)); WriteAttributeValue("", 82, cls, 82, 4, false);
EndWriteAttribute();
Instrumentation.BeginContext(87, 11, true); Instrumentation.BeginContext(87, 11, true);
WriteLiteral(" />\r\n <p"); WriteLiteral(" />\r\n <p");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("class", Tuple.Create(" class=\"", 98), Tuple.Create("\"", 114), Tuple.Create(Tuple.Create("", 106), Tuple.Create("foo", 106), true), BeginWriteAttribute("class", " class=\"", 98, "\"", 114, 2);
Tuple.Create(Tuple.Create(" ", 109), Tuple.Create<System.Object, System.Int32>(cls, 110), false)); WriteAttributeValue("", 106, "foo", 106, 3, true);
WriteAttributeValue(" ", 109, cls, 110, 5, false);
EndWriteAttribute();
Instrumentation.BeginContext(115, 11, true); Instrumentation.BeginContext(115, 11, true);
WriteLiteral(" />\r\n <p"); WriteLiteral(" />\r\n <p");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("class", Tuple.Create(" class=\"", 126), Tuple.Create("\"", 142), BeginWriteAttribute("class", " class=\"", 126, "\"", 142, 2);
Tuple.Create(Tuple.Create("", 134), Tuple.Create<System.Object, System.Int32>(cls, 134), false), Tuple.Create(Tuple.Create(" ", 138), Tuple.Create("foo", 139), true)); WriteAttributeValue("", 134, cls, 134, 4, false);
WriteAttributeValue(" ", 138, "foo", 139, 4, true);
EndWriteAttribute();
Instrumentation.BeginContext(143, 31, true); Instrumentation.BeginContext(143, 31, true);
WriteLiteral(" />\r\n <input type=\"checkbox\""); WriteLiteral(" />\r\n <input type=\"checkbox\"");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("checked", Tuple.Create(" checked=\"", 174), Tuple.Create("\"", 187), BeginWriteAttribute("checked", " checked=\"", 174, "\"", 187, 1);
Tuple.Create(Tuple.Create("", 184), Tuple.Create<System.Object, System.Int32>(ch, 184), false)); WriteAttributeValue("", 184, ch, 184, 3, false);
EndWriteAttribute();
Instrumentation.BeginContext(188, 31, true); Instrumentation.BeginContext(188, 31, true);
WriteLiteral(" />\r\n <input type=\"checkbox\""); WriteLiteral(" />\r\n <input type=\"checkbox\"");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("checked", Tuple.Create(" checked=\"", 219), Tuple.Create("\"", 236), Tuple.Create(Tuple.Create("", 229), Tuple.Create("foo", 229), true), BeginWriteAttribute("checked", " checked=\"", 219, "\"", 236, 2);
Tuple.Create(Tuple.Create(" ", 232), Tuple.Create<System.Object, System.Int32>(ch, 233), false)); WriteAttributeValue("", 229, "foo", 229, 3, true);
WriteAttributeValue(" ", 232, ch, 233, 4, false);
EndWriteAttribute();
Instrumentation.BeginContext(237, 11, true); Instrumentation.BeginContext(237, 11, true);
WriteLiteral(" />\r\n <p"); WriteLiteral(" />\r\n <p");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("class", Tuple.Create(" class=\"", 248), Tuple.Create("\"", 281), BeginWriteAttribute("class", " class=\"", 248, "\"", 281, 1);
Tuple.Create(Tuple.Create("", 256), Tuple.Create<System.Object, System.Int32>(new Template((__razor_attribute_value_writer) => { WriteAttributeValue("", 256, new Template((__razor_attribute_value_writer) => {
#line 10 "ConditionalAttributes.cshtml" #line 10 "ConditionalAttributes.cshtml"
if(cls != null) { if(cls != null) {
@ -72,17 +80,20 @@ WriteTo(__razor_attribute_value_writer, cls);
#line hidden #line hidden
} }
), 256), false)); ), 256, 25, false);
EndWriteAttribute();
Instrumentation.BeginContext(282, 40, true); Instrumentation.BeginContext(282, 40, true);
WriteLiteral(" />\r\n <a href=\"~/Foo\" />\r\n <script"); WriteLiteral(" />\r\n <a href=\"~/Foo\" />\r\n <script");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("src", Tuple.Create(" src=\"", 322), Tuple.Create("\"", 373), BeginWriteAttribute("src", " src=\"", 322, "\"", 373, 1);
Tuple.Create(Tuple.Create("", 328), Tuple.Create<System.Object, System.Int32>(Url.Content("~/Scripts/jquery-1.6.2.min.js"), 328), false)); WriteAttributeValue("", 328, Url.Content("~/Scripts/jquery-1.6.2.min.js"), 328, 45, false);
EndWriteAttribute();
Instrumentation.BeginContext(374, 46, true); Instrumentation.BeginContext(374, 46, true);
WriteLiteral(" type=\"text/javascript\"></script>\r\n <script"); WriteLiteral(" type=\"text/javascript\"></script>\r\n <script");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("src", Tuple.Create(" src=\"", 420), Tuple.Create("\"", 487), BeginWriteAttribute("src", " src=\"", 420, "\"", 487, 1);
Tuple.Create(Tuple.Create("", 426), Tuple.Create<System.Object, System.Int32>(Url.Content("~/Scripts/modernizr-2.0.6-development-only.js"), 426), false)); WriteAttributeValue("", 426, Url.Content("~/Scripts/modernizr-2.0.6-development-only.js"), 426, 61, false);
EndWriteAttribute();
Instrumentation.BeginContext(488, 152, true); Instrumentation.BeginContext(488, 152, true);
WriteLiteral(" type=\"text/javascript\"></script>\r\n <script src=\"http://ajax.aspnetcdn.com/aja" + WriteLiteral(" type=\"text/javascript\"></script>\r\n <script src=\"http://ajax.aspnetcdn.com/aja" +
"x/jquery.ui/1.8.16/jquery-ui.min.js\" type=\"text/javascript\"></script>\r\n"); "x/jquery.ui/1.8.16/jquery-ui.min.js\" type=\"text/javascript\"></script>\r\n");

View File

@ -32,8 +32,10 @@ namespace TestOutput
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__InputTagHelper = CreateTagHelper<InputTagHelper>(); __InputTagHelper = CreateTagHelper<InputTagHelper>();
__tagHelperExecutionContext.Add(__InputTagHelper); __tagHelperExecutionContext.Add(__InputTagHelper);
AddHtmlAttributeValues("unbound", __tagHelperExecutionContext, Tuple.Create(Tuple.Create("", 51), Tuple.Create("prefix", 51), true), BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "unbound", 2);
Tuple.Create(Tuple.Create(" ", 57), Tuple.Create<System.Object, System.Int32>(DateTime.Now, 58), false)); AddHtmlAttributeValue("", 51, "prefix", 51, 6, true);
AddHtmlAttributeValue(" ", 57, DateTime.Now, 58, 14, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(35, 40, false); Instrumentation.BeginContext(35, 40, false);
await WriteTagHelperAsync(__tagHelperExecutionContext); await WriteTagHelperAsync(__tagHelperExecutionContext);
@ -47,8 +49,8 @@ namespace TestOutput
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__InputTagHelper = CreateTagHelper<InputTagHelper>(); __InputTagHelper = CreateTagHelper<InputTagHelper>();
__tagHelperExecutionContext.Add(__InputTagHelper); __tagHelperExecutionContext.Add(__InputTagHelper);
AddHtmlAttributeValues("unbound", __tagHelperExecutionContext, BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "unbound", 2);
Tuple.Create(Tuple.Create("", 95), Tuple.Create<System.Object, System.Int32>(new Template((__razor_attribute_value_writer) => { AddHtmlAttributeValue("", 95, new Template((__razor_attribute_value_writer) => {
#line 5 "DynamicAttributeTagHelpers.cshtml" #line 5 "DynamicAttributeTagHelpers.cshtml"
if (true) { if (true) {
@ -82,7 +84,9 @@ WriteTo(__razor_attribute_value_writer, false);
#line hidden #line hidden
} }
), 95), false), Tuple.Create(Tuple.Create(" ", 139), Tuple.Create("suffix", 140), true)); ), 95, 44, false);
AddHtmlAttributeValue(" ", 139, "suffix", 140, 7, true);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(79, 71, false); Instrumentation.BeginContext(79, 71, false);
await WriteTagHelperAsync(__tagHelperExecutionContext); await WriteTagHelperAsync(__tagHelperExecutionContext);
@ -107,8 +111,11 @@ WriteLiteral(DateTime.Now);
__tagHelperStringValueBuffer = EndTagHelperWritingScope(); __tagHelperStringValueBuffer = EndTagHelperWritingScope();
__InputTagHelper.Bound = __tagHelperStringValueBuffer.GetContent(HtmlEncoder); __InputTagHelper.Bound = __tagHelperStringValueBuffer.GetContent(HtmlEncoder);
__tagHelperExecutionContext.AddTagHelperAttribute("bound", __InputTagHelper.Bound); __tagHelperExecutionContext.AddTagHelperAttribute("bound", __InputTagHelper.Bound);
AddHtmlAttributeValues("unbound", __tagHelperExecutionContext, Tuple.Create(Tuple.Create("", 206), Tuple.Create("prefix", 206), true), BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "unbound", 3);
Tuple.Create(Tuple.Create(" ", 212), Tuple.Create<System.Object, System.Int32>(DateTime.Now, 213), false), Tuple.Create(Tuple.Create(" ", 226), Tuple.Create("suffix", 227), true)); AddHtmlAttributeValue("", 206, "prefix", 206, 6, true);
AddHtmlAttributeValue(" ", 212, DateTime.Now, 213, 14, false);
AddHtmlAttributeValue(" ", 226, "suffix", 227, 7, true);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(154, 83, false); Instrumentation.BeginContext(154, 83, false);
await WriteTagHelperAsync(__tagHelperExecutionContext); await WriteTagHelperAsync(__tagHelperExecutionContext);
@ -166,9 +173,9 @@ WriteLiteral(int.MaxValue);
__tagHelperStringValueBuffer = EndTagHelperWritingScope(); __tagHelperStringValueBuffer = EndTagHelperWritingScope();
__InputTagHelper.Bound = __tagHelperStringValueBuffer.GetContent(HtmlEncoder); __InputTagHelper.Bound = __tagHelperStringValueBuffer.GetContent(HtmlEncoder);
__tagHelperExecutionContext.AddTagHelperAttribute("bound", __InputTagHelper.Bound); __tagHelperExecutionContext.AddTagHelperAttribute("bound", __InputTagHelper.Bound);
AddHtmlAttributeValues("unbound", __tagHelperExecutionContext, BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "unbound", 3);
Tuple.Create(Tuple.Create("", 347), Tuple.Create<System.Object, System.Int32>(long.MinValue, 347), false), AddHtmlAttributeValue("", 347, long.MinValue, 347, 14, false);
Tuple.Create(Tuple.Create(" ", 361), Tuple.Create<System.Object, System.Int32>(new Template((__razor_attribute_value_writer) => { AddHtmlAttributeValue(" ", 361, new Template((__razor_attribute_value_writer) => {
#line 10 "DynamicAttributeTagHelpers.cshtml" #line 10 "DynamicAttributeTagHelpers.cshtml"
if (true) { if (true) {
@ -202,8 +209,9 @@ WriteTo(__razor_attribute_value_writer, false);
#line hidden #line hidden
} }
), 362), false), ), 362, 45, false);
Tuple.Create(Tuple.Create(" ", 406), Tuple.Create<System.Object, System.Int32>(int.MaxValue, 407), false)); AddHtmlAttributeValue(" ", 406, int.MaxValue, 407, 14, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(241, 183, false); Instrumentation.BeginContext(241, 183, false);
await WriteTagHelperAsync(__tagHelperExecutionContext); await WriteTagHelperAsync(__tagHelperExecutionContext);
@ -217,10 +225,13 @@ WriteTo(__razor_attribute_value_writer, false);
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__InputTagHelper = CreateTagHelper<InputTagHelper>(); __InputTagHelper = CreateTagHelper<InputTagHelper>();
__tagHelperExecutionContext.Add(__InputTagHelper); __tagHelperExecutionContext.Add(__InputTagHelper);
AddHtmlAttributeValues("unbound", __tagHelperExecutionContext, BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "unbound", 5);
Tuple.Create(Tuple.Create("", 444), Tuple.Create<System.Object, System.Int32>(long.MinValue, 444), false), AddHtmlAttributeValue("", 444, long.MinValue, 444, 14, false);
Tuple.Create(Tuple.Create(" ", 458), Tuple.Create<System.Object, System.Int32>(DateTime.Now, 459), false), Tuple.Create(Tuple.Create(" ", 472), Tuple.Create("static", 473), true), Tuple.Create(Tuple.Create(" ", 479), Tuple.Create("content", 483), true), AddHtmlAttributeValue(" ", 458, DateTime.Now, 459, 14, false);
Tuple.Create(Tuple.Create(" ", 490), Tuple.Create<System.Object, System.Int32>(int.MaxValue, 491), false)); AddHtmlAttributeValue(" ", 472, "static", 473, 7, true);
AddHtmlAttributeValue(" ", 479, "content", 483, 11, true);
AddHtmlAttributeValue(" ", 490, int.MaxValue, 491, 14, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(428, 80, false); Instrumentation.BeginContext(428, 80, false);
await WriteTagHelperAsync(__tagHelperExecutionContext); await WriteTagHelperAsync(__tagHelperExecutionContext);
@ -234,8 +245,8 @@ WriteTo(__razor_attribute_value_writer, false);
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__InputTagHelper = CreateTagHelper<InputTagHelper>(); __InputTagHelper = CreateTagHelper<InputTagHelper>();
__tagHelperExecutionContext.Add(__InputTagHelper); __tagHelperExecutionContext.Add(__InputTagHelper);
AddHtmlAttributeValues("unbound", __tagHelperExecutionContext, BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "unbound", 1);
Tuple.Create(Tuple.Create("", 528), Tuple.Create<System.Object, System.Int32>(new Template((__razor_attribute_value_writer) => { AddHtmlAttributeValue("", 528, new Template((__razor_attribute_value_writer) => {
#line 14 "DynamicAttributeTagHelpers.cshtml" #line 14 "DynamicAttributeTagHelpers.cshtml"
if (true) { if (true) {
@ -269,7 +280,8 @@ WriteTo(__razor_attribute_value_writer, false);
#line hidden #line hidden
} }
), 528), false)); ), 528, 44, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(512, 64, false); Instrumentation.BeginContext(512, 64, false);
await WriteTagHelperAsync(__tagHelperExecutionContext); await WriteTagHelperAsync(__tagHelperExecutionContext);

View File

@ -20,8 +20,8 @@ namespace TestOutput
Instrumentation.BeginContext(13, 23, true); Instrumentation.BeginContext(13, 23, true);
WriteLiteral("(string link) {\r\n <a"); WriteLiteral("(string link) {\r\n <a");
Instrumentation.EndContext(); Instrumentation.EndContext();
WriteAttribute("href", Tuple.Create(" href=\"", 36), Tuple.Create("\"", 94), BeginWriteAttribute("href", " href=\"", 36, "\"", 94, 1);
Tuple.Create(Tuple.Create("", 43), Tuple.Create<System.Object, System.Int32>(new Template((__razor_attribute_value_writer) => { WriteAttributeValue("", 43, new Template((__razor_attribute_value_writer) => {
#line 2 "InlineBlocks.cshtml" #line 2 "InlineBlocks.cshtml"
if(link != null) { if(link != null) {
@ -57,7 +57,8 @@ WriteTo(__razor_attribute_value_writer, link);
#line hidden #line hidden
} }
), 43), false)); ), 43, 50, false);
EndWriteAttribute();
Instrumentation.BeginContext(95, 6, true); Instrumentation.BeginContext(95, 6, true);
WriteLiteral(" />\r\n}"); WriteLiteral(" />\r\n}");
Instrumentation.EndContext(); Instrumentation.EndContext();

View File

@ -83,8 +83,11 @@ WriteLiteral(DateTime.Now);
__tagHelperStringValueBuffer = EndTagHelperWritingScope(); __tagHelperStringValueBuffer = EndTagHelperWritingScope();
__MyTagHelper.BoundProperty = __tagHelperStringValueBuffer.GetContent(HtmlEncoder); __MyTagHelper.BoundProperty = __tagHelperStringValueBuffer.GetContent(HtmlEncoder);
__tagHelperExecutionContext.AddTagHelperAttribute("boundproperty", __MyTagHelper.BoundProperty); __tagHelperExecutionContext.AddTagHelperAttribute("boundproperty", __MyTagHelper.BoundProperty);
AddHtmlAttributeValues("unboundproperty", __tagHelperExecutionContext, Tuple.Create(Tuple.Create("", 188), Tuple.Create("Current", 188), true), Tuple.Create(Tuple.Create(" ", 195), Tuple.Create("Time:", 196), true), BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "unboundproperty", 3);
Tuple.Create(Tuple.Create(" ", 201), Tuple.Create<System.Object, System.Int32>(DateTime.Now, 202), false)); AddHtmlAttributeValue("", 188, "Current", 188, 7, true);
AddHtmlAttributeValue(" ", 195, "Time:", 196, 6, true);
AddHtmlAttributeValue(" ", 201, DateTime.Now, 202, 14, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
__tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext); __tagHelperExecutionContext.Output = await __tagHelperRunner.RunAsync(__tagHelperExecutionContext);
Instrumentation.BeginContext(114, 245, false); Instrumentation.BeginContext(114, 245, false);
await WriteTagHelperToAsync(__razor_template_writer, __tagHelperExecutionContext); await WriteTagHelperToAsync(__razor_template_writer, __tagHelperExecutionContext);

View File

@ -43,10 +43,11 @@ namespace TestOutput
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__PTagHelper = CreateTagHelper<PTagHelper>(); __PTagHelper = CreateTagHelper<PTagHelper>();
__tagHelperExecutionContext.Add(__PTagHelper); __tagHelperExecutionContext.Add(__PTagHelper);
AddHtmlAttributeValues("class", __tagHelperExecutionContext, BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "class", 1);
Tuple.Create(Tuple.Create("", 109), Tuple.Create<System.Object, System.Int32>(new Template((__razor_attribute_value_writer) => { AddHtmlAttributeValue("", 109, new Template((__razor_attribute_value_writer) => {
} }
), 109), false)); ), 109, 6, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
#line 7 "TransitionsInTagHelperAttributes.cshtml" #line 7 "TransitionsInTagHelperAttributes.cshtml"
__PTagHelper.Age = 1337; __PTagHelper.Age = 1337;
@ -66,8 +67,9 @@ namespace TestOutput
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__PTagHelper = CreateTagHelper<PTagHelper>(); __PTagHelper = CreateTagHelper<PTagHelper>();
__tagHelperExecutionContext.Add(__PTagHelper); __tagHelperExecutionContext.Add(__PTagHelper);
AddHtmlAttributeValues("class", __tagHelperExecutionContext, BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "class", 1);
Tuple.Create(Tuple.Create("", 155), Tuple.Create<System.Object, System.Int32>(@class, 155), false)); AddHtmlAttributeValue("", 155, @class, 155, 9, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
#line 8 "TransitionsInTagHelperAttributes.cshtml" #line 8 "TransitionsInTagHelperAttributes.cshtml"
__PTagHelper.Age = 42; __PTagHelper.Age = 42;
@ -147,8 +149,10 @@ namespace TestOutput
, StartTagHelperWritingScope, EndTagHelperWritingScope); , StartTagHelperWritingScope, EndTagHelperWritingScope);
__PTagHelper = CreateTagHelper<PTagHelper>(); __PTagHelper = CreateTagHelper<PTagHelper>();
__tagHelperExecutionContext.Add(__PTagHelper); __tagHelperExecutionContext.Add(__PTagHelper);
AddHtmlAttributeValues("class", __tagHelperExecutionContext, Tuple.Create(Tuple.Create("", 298), Tuple.Create("custom-", 298), true), BeginAddHtmlAttributeValues(__tagHelperExecutionContext, "class", 2);
Tuple.Create(Tuple.Create("", 305), Tuple.Create<System.Object, System.Int32>(@class, 305), false)); AddHtmlAttributeValue("", 298, "custom-", 298, 7, true);
AddHtmlAttributeValue("", 305, @class, 305, 9, false);
EndAddHtmlAttributeValues(__tagHelperExecutionContext);
#line 12 "TransitionsInTagHelperAttributes.cshtml" #line 12 "TransitionsInTagHelperAttributes.cshtml"
__PTagHelper.Age = 4 * @(@int + 2); __PTagHelper.Age = 4 * @(@int + 2);