This commit is contained in:
Ryan Nowak 2018-04-11 20:52:01 -07:00 коммит произвёл Ryan Nowak
Родитель 79a620a8ad
Коммит e5fd24b345
69 изменённых файлов: 1221 добавлений и 278 удалений

Просмотреть файл

@ -15,6 +15,7 @@
<AssemblyOriginatorKeyFile>$(MSBuildThisFileDirectory)build\Key.snk</AssemblyOriginatorKeyFile>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<AssemblySigningCertName>Microsoft</AssemblySigningCertName>
<LangVersion>7.3</LangVersion>
<!-- Our customizations -->
<SignAssembly>false</SignAssembly>

Просмотреть файл

@ -84,8 +84,6 @@ namespace Microsoft.AspNetCore.Blazor.Razor
public static readonly string GetEventHandlerValue = "Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue";
public static readonly string SetValue = "Microsoft.AspNetCore.Blazor.Components.BindMethods.SetValue";
public static readonly string SetValueHandler = "Microsoft.AspNetCore.Blazor.Components.BindMethods.SetValueHandler";
}
@ -93,10 +91,5 @@ namespace Microsoft.AspNetCore.Blazor.Razor
{
public static readonly string FullTypeName = "Microsoft.AspNetCore.Blazor.Components.EventHandlerAttribute";
}
public static class UIEventHandler
{
public static readonly string FullTypeName = "Microsoft.AspNetCore.Blazor.UIEventHandler";
}
}
}

Просмотреть файл

@ -8,6 +8,7 @@
https://api.nuget.org/v3/index.json;
https://dotnet.myget.org/f/blazor-dev/api/v3/index.json;
</RestoreSources>
<LangVersion>7.3</LangVersion>
</PropertyGroup>
<ItemGroup>

Просмотреть файл

@ -7,6 +7,7 @@
https://api.nuget.org/v3/index.json;
https://dotnet.myget.org/f/blazor-dev/api/v3/index.json;
</RestoreSources>
<LangVersion>7.3</LangVersion>
</PropertyGroup>
<ItemGroup Condition="'$(Framework)' != 'netcoreapp2.0'">

Просмотреть файл

@ -2,6 +2,7 @@
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<LangVersion>7.3</LangVersion>
</PropertyGroup>
</Project>

Просмотреть файл

@ -10,6 +10,7 @@
https://api.nuget.org/v3/index.json;
https://dotnet.myget.org/f/blazor-dev/api/v3/index.json;
</RestoreSources>
<LangVersion>7.3</LangVersion>
</PropertyGroup>
<ItemGroup>

Просмотреть файл

@ -9,6 +9,7 @@
https://api.nuget.org/v3/index.json;
https://dotnet.myget.org/f/blazor-dev/api/v3/index.json;
</RestoreSources>
<LangVersion>7.3</LangVersion>
</PropertyGroup>
<ItemGroup>

Просмотреть файл

@ -3,6 +3,7 @@
using System;
using System.Globalization;
using System.Threading.Tasks;
namespace Microsoft.AspNetCore.Blazor.Components
{
@ -41,6 +42,15 @@ namespace Microsoft.AspNetCore.Blazor.Components
return value;
}
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static MulticastDelegate GetEventHandlerValue<T>(Func<Task> value)
where T : UIEventArgs
{
return value;
}
/// <summary>
/// Not intended to be used directly.
/// </summary>
@ -53,7 +63,16 @@ namespace Microsoft.AspNetCore.Blazor.Components
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static UIEventHandler SetValueHandler(Action<string> setter, string existingValue)
public static MulticastDelegate GetEventHandlerValue<T>(Func<T, Task> value)
where T : UIEventArgs
{
return value;
}
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static Action<UIEventArgs> SetValueHandler(Action<string> setter, string existingValue)
{
return _ => setter((string)((UIChangeEventArgs)_).Value);
}
@ -61,7 +80,7 @@ namespace Microsoft.AspNetCore.Blazor.Components
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static UIEventHandler SetValueHandler(Action<bool> setter, bool existingValue)
public static Action<UIEventArgs> SetValueHandler(Action<bool> setter, bool existingValue)
{
return _ => setter((bool)((UIChangeEventArgs)_).Value);
}
@ -69,7 +88,7 @@ namespace Microsoft.AspNetCore.Blazor.Components
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static UIEventHandler SetValueHandler(Action<int> setter, int existingValue)
public static Action<UIEventArgs> SetValueHandler(Action<int> setter, int existingValue)
{
return _ => setter(int.Parse((string)((UIChangeEventArgs)_).Value));
}
@ -77,23 +96,23 @@ namespace Microsoft.AspNetCore.Blazor.Components
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static UIEventHandler SetValueHandler(Action<DateTime> setter, DateTime existingValue)
public static Action<UIEventArgs> SetValueHandler(Action<DateTime> setter, DateTime existingValue)
{
return _ => SetDateTimeValue(setter, (object)((UIChangeEventArgs)_).Value, null);
return _ => SetDateTimeValue(setter, ((UIChangeEventArgs)_).Value, null);
}
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static UIEventHandler SetValueHandler(Action<DateTime> setter, DateTime existingValue, string format)
public static Action<UIEventArgs> SetValueHandler(Action<DateTime> setter, DateTime existingValue, string format)
{
return _ => SetDateTimeValue(setter, (object)((UIChangeEventArgs)_).Value, format);
return _ => SetDateTimeValue(setter, ((UIChangeEventArgs)_).Value, format);
}
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static UIEventHandler SetValueHandler<T>(Action<T> setter, T existingValue)
public static Action<UIEventArgs> SetValueHandler<T>(Action<T> setter, T existingValue)
{
if (!typeof(T).IsEnum)
{
@ -108,52 +127,6 @@ namespace Microsoft.AspNetCore.Blazor.Components
};
}
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static Action<object> SetValue(Action<string> setter, string existingValue)
=> objValue => setter((string)objValue);
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static Action<object> SetValue(Action<bool> setter, bool existingValue)
=> objValue => setter((bool)objValue);
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static Action<object> SetValue(Action<int> setter, int existingValue)
=> objValue => setter(int.Parse((string)objValue));
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static Action<object> SetValue<T>(Action<T> setter, T existingValue) => objValue =>
{
if (typeof(T).IsEnum)
{
var parsedValue = Enum.Parse(typeof(T), (string)objValue);
setter((T)parsedValue);
}
else
{
throw new ArgumentException($"@bind syntax does not accept values of type {typeof(T).FullName}. To read and write this value type, wrap it in a property of type string with suitable getters and setters.");
}
};
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static Action<object> SetValue(Action<DateTime> setter, DateTime existingValue)
=> objValue => SetDateTimeValue(setter, objValue, null);
/// <summary>
/// Not intended to be used directly.
/// </summary>
public static Action<object> SetValue(Action<DateTime> setter, DateTime existingValue, string format)
=> objValue => SetDateTimeValue(setter, objValue, format);
private static void SetDateTimeValue(Action<DateTime> setter, object objValue, string format)
{
var stringValue = (string)objValue;

Просмотреть файл

@ -175,14 +175,21 @@ namespace Microsoft.AspNetCore.Blazor.Components
Console.Error.WriteLine($"[{ex.GetType().FullName}] {ex.Message}\n{ex.StackTrace}");
}
void IHandleEvent.HandleEvent(UIEventHandler handler, UIEventArgs args)
void IHandleEvent.HandleEvent(EventHandlerInvoker binding, UIEventArgs args)
{
handler(args);
var task = binding.Invoke(args);
// After each event, we synchronously re-render (unless !ShouldRender())
// This just saves the developer the trouble of putting "StateHasChanged();"
// at the end of every event callback.
StateHasChanged();
if (task.Status == TaskStatus.RanToCompletion)
{
return;
}
task.ContinueWith(ContinueAfterLifecycleTask);
}
}
}

Просмотреть файл

@ -0,0 +1,55 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Threading.Tasks;
namespace Microsoft.AspNetCore.Blazor.Components
{
/// <summary>
/// A bound event handler delegate.
/// </summary>
public struct EventHandlerInvoker
{
private readonly MulticastDelegate _delegate;
/// <summary>
/// Creates the new <see cref="EventHandlerInvoker"/>.
/// </summary>
/// <param name="delegate">The delegate to bind.</param>
public EventHandlerInvoker(MulticastDelegate @delegate)
{
_delegate = @delegate;
}
/// <summary>
/// Invokes the delegate associated with this binding.
/// </summary>
/// <param name="e">The <see cref="UIEventArgs"/>.</param>
/// <returns></returns>
public Task Invoke(UIEventArgs e)
{
switch (_delegate)
{
case Action action:
action.Invoke();
return Task.CompletedTask;
case Action<UIEventArgs> actionEventArgs:
actionEventArgs.Invoke(e);
return Task.CompletedTask;
case Func<Task> func:
return func.Invoke();
case Func<UIEventArgs, Task> funcEventArgs:
return funcEventArgs.Invoke(e);
case MulticastDelegate @delegate:
return @delegate.DynamicInvoke(e) as Task ?? Task.CompletedTask;
case null:
return Task.CompletedTask;
}
}
}
}

Просмотреть файл

@ -1,8 +1,6 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.AspNetCore.Blazor.RenderTree;
namespace Microsoft.AspNetCore.Blazor.Components
{
/// <summary>
@ -13,8 +11,8 @@ namespace Microsoft.AspNetCore.Blazor.Components
/// <summary>
/// Notifies the component that one of its event handlers has been triggered.
/// </summary>
/// <param name="handler">The event handler.</param>
/// <param name="binding">The event binding.</param>
/// <param name="args">Arguments for the event handler.</param>
void HandleEvent(UIEventHandler handler, UIEventArgs args);
void HandleEvent(EventHandlerInvoker binding, UIEventArgs args);
}
}

Просмотреть файл

@ -2,7 +2,6 @@
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<LangVersion>7.2</LangVersion>
</PropertyGroup>
</Project>

Просмотреть файл

@ -3,6 +3,7 @@
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Blazor.Components;
using Microsoft.AspNetCore.Blazor.Rendering;
@ -167,7 +168,7 @@ namespace Microsoft.AspNetCore.Blazor.RenderTree
/// <summary>
/// <para>
/// Appends a frame representing an <see cref="UIEventHandler"/>-valued attribute.
/// Appends a frame representing an <see cref="Action{UIEventArgs}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
@ -177,7 +178,41 @@ namespace Microsoft.AspNetCore.Blazor.RenderTree
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public void AddAttribute(int sequence, string name, UIEventHandler value)
public void AddAttribute(int sequence, string name, Action<UIEventArgs> value)
{
AddAttribute(sequence, name, (MulticastDelegate)value);
}
/// <summary>
/// <para>
/// Appends a frame representing a <see cref="Func{Task}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
/// current element is not a component, the frame will be omitted.
/// </para>
/// </summary>
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public void AddAttribute(int sequence, string name, Func<Task> value)
{
AddAttribute(sequence, name, (MulticastDelegate)value);
}
/// <summary>
/// <para>
/// Appends a frame representing a <see cref="Func{UIEventArgs, Task}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
/// current element is not a component, the frame will be omitted.
/// </para>
/// </summary>
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public void AddAttribute(int sequence, string name, Func<UIEventArgs, Task> value)
{
AddAttribute(sequence, name, (MulticastDelegate)value);
}
@ -196,10 +231,10 @@ namespace Microsoft.AspNetCore.Blazor.RenderTree
/// <param name="value">The value of the attribute.</param>
/// <remarks>
/// This method is provided for infrastructure purposes, and is used to be
/// <see cref="UIEventHandlerRenderTreeBuilderExtensions"/> to provide support for delegates of specific
/// <see cref="UIEventArgsRenderTreeBuilderExtensions"/> to provide support for delegates of specific
/// types. For a good programming experience when using a custom delegate type, define an
/// extension method similar to
/// <see cref="UIEventHandlerRenderTreeBuilderExtensions.AddAttribute(RenderTreeBuilder, int, string, UIChangeEventHandler)"/>
/// <see cref="UIEventArgsRenderTreeBuilderExtensions.AddAttribute(RenderTreeBuilder, int, string, Action{UIChangeEventArgs})"/>
/// that calls this method.
/// </remarks>
public void AddAttribute(int sequence, string name, MulticastDelegate value)

Просмотреть файл

@ -195,7 +195,7 @@ namespace Microsoft.AspNetCore.Blazor.RenderTree
internal static RenderTreeFrame Text(int sequence, string textContent)
=> new RenderTreeFrame(sequence, textContent: textContent);
internal static RenderTreeFrame Attribute(int sequence, string name, UIEventHandler value)
internal static RenderTreeFrame Attribute(int sequence, string name, MulticastDelegate value)
=> new RenderTreeFrame(sequence, attributeName: name, attributeValue: value);
internal static RenderTreeFrame Attribute(int sequence, string name, object value)

Просмотреть файл

@ -1,9 +1,9 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using Microsoft.AspNetCore.Blazor.Components;
using Microsoft.AspNetCore.Blazor.RenderTree;
using System;
namespace Microsoft.AspNetCore.Blazor.Rendering
{
@ -73,11 +73,11 @@ namespace Microsoft.AspNetCore.Blazor.Rendering
RenderTreeDiffBuilder.DisposeFrames(batchBuilder, _renderTreeBuilderCurrent.GetFrames());
}
public void DispatchEvent(UIEventHandler handler, UIEventArgs eventArgs)
public void DispatchEvent(EventHandlerInvoker binding, UIEventArgs eventArgs)
{
if (_component is IHandleEvent handleEventComponent)
{
handleEventComponent.HandleEvent(handler, eventArgs);
handleEventComponent.HandleEvent(binding, eventArgs);
}
else
{

Просмотреть файл

@ -5,6 +5,7 @@ using Microsoft.AspNetCore.Blazor.Components;
using Microsoft.AspNetCore.Blazor.RenderTree;
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
namespace Microsoft.AspNetCore.Blazor.Rendering
{
@ -23,8 +24,7 @@ namespace Microsoft.AspNetCore.Blazor.Rendering
private bool _isBatchInProgress;
private int _lastEventHandlerId = 0;
private readonly Dictionary<int, UIEventHandler> _eventHandlersById
= new Dictionary<int, UIEventHandler>();
private readonly Dictionary<int, EventHandlerInvoker> _eventBindings = new Dictionary<int, EventHandlerInvoker>();
/// <summary>
/// Constructs an instance of <see cref="Renderer"/>.
@ -72,14 +72,14 @@ namespace Microsoft.AspNetCore.Blazor.Rendering
/// <param name="eventArgs">Arguments to be passed to the event handler.</param>
protected void DispatchEvent(int componentId, int eventHandlerId, UIEventArgs eventArgs)
{
if (_eventHandlersById.TryGetValue(eventHandlerId, out var handler))
if (_eventBindings.TryGetValue(eventHandlerId, out var binding))
{
// The event handler might request multiple renders in sequence. Capture them
// all in a single batch.
try
{
_isBatchInProgress = true;
GetRequiredComponentState(componentId).DispatchEvent(handler, eventArgs);
GetRequiredComponentState(componentId).DispatchEvent(binding, eventArgs);
}
finally
{
@ -114,32 +114,9 @@ namespace Microsoft.AspNetCore.Blazor.Rendering
{
var id = ++_lastEventHandlerId;
// The attribute value might be a more specialized type like UIKeyboardEventHandler.
// In that case, it won't be a UIEventHandler, and it will go down the MulticastDelegate
// code path (MulticastDelegate is any delegate).
//
// In order to dispatch the event, we need a UIEventHandler, so we're going weakly
// typed here. The user will get a cast exception if they map the wrong type of
// delegate to the event.
if (frame.AttributeValue is UIEventHandler wrapper)
if (frame.AttributeValue is MulticastDelegate @delegate)
{
_eventHandlersById.Add(id, wrapper);
}
// IMPORTANT: we're creating an additional delegate when necessary. This is
// going to get cached in _eventHandlersById, but the render tree diff
// will operate on 'AttributeValue' which means that we'll only create a new
// wrapper delegate when the underlying delegate changes.
//
// TLDR: If the component uses a method group or a non-capturing lambda
// we don't allocate much.
else if (frame.AttributeValue is Action action)
{
_eventHandlersById.Add(id, (UIEventArgs e) => action());
}
else if (frame.AttributeValue is MulticastDelegate @delegate)
{
_eventHandlersById.Add(id, (UIEventArgs e) => @delegate.DynamicInvoke(e));
_eventBindings.Add(id, new EventHandlerInvoker(@delegate));
}
frame = frame.WithAttributeEventHandlerId(id);
@ -218,7 +195,7 @@ namespace Microsoft.AspNetCore.Blazor.Rendering
var count = eventHandlerIds.Count;
for (var i = 0; i < count; i++)
{
_eventHandlersById.Remove(array[i]);
_eventBindings.Remove(array[i]);
}
}
}

Просмотреть файл

@ -2,6 +2,7 @@
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Blazor.RenderTree;
namespace Microsoft.AspNetCore.Blazor
@ -35,11 +36,11 @@ namespace Microsoft.AspNetCore.Blazor
/// </code>
/// </para>
/// </remarks>
public static class UIEventHandlerRenderTreeBuilderExtensions
public static class UIEventArgsRenderTreeBuilderExtensions
{
/// <summary>
/// <para>
/// Appends a frame representing an <see cref="UIChangeEventArgs"/>-valued attribute.
/// Appends a frame representing an <see cref="Action{UIChangeEventArgs}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
@ -50,7 +51,7 @@ namespace Microsoft.AspNetCore.Blazor
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, UIChangeEventHandler value)
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, Action<UIChangeEventArgs> value)
{
if (builder == null)
{
@ -62,7 +63,7 @@ namespace Microsoft.AspNetCore.Blazor
/// <summary>
/// <para>
/// Appends a frame representing an <see cref="UIKeyboardEventHandler"/>-valued attribute.
/// Appends a frame representing an <see cref="Func{UIChangeEventArgs, Task}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
@ -73,7 +74,7 @@ namespace Microsoft.AspNetCore.Blazor
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, UIKeyboardEventHandler value)
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, Func<UIChangeEventArgs, Task> value)
{
if (builder == null)
{
@ -85,7 +86,7 @@ namespace Microsoft.AspNetCore.Blazor
/// <summary>
/// <para>
/// Appends a frame representing an <see cref="UIMouseEventHandler"/>-valued attribute.
/// Appends a frame representing an <see cref="Action{UIKeyboardEventArgs}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
@ -96,7 +97,76 @@ namespace Microsoft.AspNetCore.Blazor
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, UIMouseEventHandler value)
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, Action<UIKeyboardEventArgs> value)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
builder.AddAttribute(sequence, name, (MulticastDelegate)value);
}
/// <summary>
/// <para>
/// Appends a frame representing an <see cref="Func{UIKeyboardEventArgs, Task}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
/// current element is not a component, the frame will be omitted.
/// </para>
/// </summary>
/// <param name="builder">The <see cref="RenderTreeBuilder"/>.</param>
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, Func<UIKeyboardEventArgs, Task> value)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
builder.AddAttribute(sequence, name, (MulticastDelegate)value);
}
/// <summary>
/// <para>
/// Appends a frame representing an <see cref="Action{UIMouseEventArgs}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
/// current element is not a component, the frame will be omitted.
/// </para>
/// </summary>
/// <param name="builder">The <see cref="RenderTreeBuilder"/>.</param>
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, Action<UIMouseEventArgs> value)
{
if (builder == null)
{
throw new ArgumentNullException(nameof(builder));
}
builder.AddAttribute(sequence, name, (MulticastDelegate)value);
}
/// <summary>
/// <para>
/// Appends a frame representing an <see cref="Func{UIMouseEventArgs, Task}"/>-valued attribute.
/// </para>
/// <para>
/// The attribute is associated with the most recently added element. If the value is <c>null</c> and the
/// current element is not a component, the frame will be omitted.
/// </para>
/// </summary>
/// <param name="builder">The <see cref="RenderTreeBuilder"/>.</param>
/// <param name="sequence">An integer that represents the position of the instruction in the source code.</param>
/// <param name="name">The name of the attribute.</param>
/// <param name="value">The value of the attribute.</param>
public static void AddAttribute(this RenderTreeBuilder builder, int sequence, string name, Func<UIMouseEventArgs, Task> value)
{
if (builder == null)
{

Просмотреть файл

@ -1,27 +0,0 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.AspNetCore.Blazor.RenderTree;
namespace Microsoft.AspNetCore.Blazor
{
/// <summary>
/// Handles an <see cref="UIEventArgs"/> event raised for a <see cref="RenderTreeFrame"/>.
/// </summary>
public delegate void UIEventHandler(UIEventArgs e);
/// <summary>
/// Handles an <see cref="UIChangeEventArgs"/> event raised for a <see cref="RenderTreeFrame"/>.
/// </summary>
public delegate void UIChangeEventHandler(UIChangeEventArgs e);
/// <summary>
/// Handles an <see cref="UIKeyboardEventArgs"/> event raised for a <see cref="RenderTreeFrame"/>.
/// </summary>
public delegate void UIKeyboardEventHandler(UIKeyboardEventArgs e);
/// <summary>
/// Handles an <see cref="UIMouseEventArgs"/> event raised for a <see cref="RenderTreeFrame"/>.
/// </summary>
public delegate void UIMouseEventHandler(UIMouseEventArgs e);
}

Просмотреть файл

@ -16,7 +16,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
public void Render_BindToComponent_SpecifiesValue_WithMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -52,7 +52,7 @@ namespace Test
public void Render_BindToComponent_SpecifiesValue_WithoutMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -81,14 +81,14 @@ namespace Test
frames,
frame => AssertFrame.Component(frame, "Test.MyComponent", 3, 0),
frame => AssertFrame.Attribute(frame, "Value", 42, 1),
frame => AssertFrame.Attribute(frame, "ValueChanged", typeof(UIEventHandler), 2));
frame => AssertFrame.Attribute(frame, "ValueChanged", typeof(Action<UIEventArgs>), 2));
}
[Fact]
public void Render_BindToComponent_SpecifiesValueAndChangeEvent_WithMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -124,7 +124,7 @@ namespace Test
public void Render_BindToComponent_SpecifiesValueAndChangeEvent_WithoutMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -153,14 +153,14 @@ namespace Test
frames,
frame => AssertFrame.Component(frame, "Test.MyComponent", 3, 0),
frame => AssertFrame.Attribute(frame, "Value", 42, 1),
frame => AssertFrame.Attribute(frame, "OnChanged", typeof(UIEventHandler), 2));
frame => AssertFrame.Attribute(frame, "OnChanged", typeof(Action<UIEventArgs>), 2));
}
[Fact]
public void Render_BindToElement_WritesAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -187,14 +187,14 @@ namespace Test
frames,
frame => AssertFrame.Element(frame, "div", 3, 0),
frame => AssertFrame.Attribute(frame, "myvalue", "hi", 1),
frame => AssertFrame.Attribute(frame, "myevent", typeof(UIEventHandler), 2));
frame => AssertFrame.Attribute(frame, "myevent", typeof(Action<UIEventArgs>), 2));
}
[Fact]
public void Render_BindToElementWithSuffix_WritesAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -221,14 +221,14 @@ namespace Test
frames,
frame => AssertFrame.Element(frame, "div", 3, 0),
frame => AssertFrame.Attribute(frame, "myvalue", "hi", 1),
frame => AssertFrame.Attribute(frame, "myevent", typeof(UIEventHandler), 2));
frame => AssertFrame.Attribute(frame, "myevent", typeof(Action<UIEventArgs>), 2));
}
[Fact]
public void Render_BindDuplicates_ReportsDiagnostic()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -278,7 +278,7 @@ namespace Test
frames,
frame => AssertFrame.Element(frame, "input", 3, 0),
frame => AssertFrame.Attribute(frame, "value", "42", 1),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 2));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 2));
}
[Fact]
@ -301,7 +301,7 @@ namespace Test
frame => AssertFrame.Element(frame, "input", 4, 0),
frame => AssertFrame.Attribute(frame, "type", "text", 1),
frame => AssertFrame.Attribute(frame, "value", new DateTime(2018, 1, 1).ToString("MM/dd/yyyy"), 2),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 3));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 3));
}
[Fact]
@ -326,7 +326,7 @@ namespace Test
frame => AssertFrame.Element(frame, "input", 4, 0),
frame => AssertFrame.Attribute(frame, "type", "text", 1),
frame => AssertFrame.Attribute(frame, "value", new DateTime(2018, 1, 1).ToString("MM/dd/yyyy"), 2),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 3));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 3));
}
[Fact]
@ -349,7 +349,7 @@ namespace Test
frame => AssertFrame.Element(frame, "input", 4, 0),
frame => AssertFrame.Attribute(frame, "type", "text", 1),
frame => AssertFrame.Attribute(frame, "value", "42", 2),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 3));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 3));
}
[Fact]
@ -371,7 +371,7 @@ namespace Test
frames,
frame => AssertFrame.Element(frame, "input", 3, 0),
frame => AssertFrame.Attribute(frame, "type", "checkbox", 1),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 3));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 3));
}
[Fact]
@ -394,7 +394,7 @@ namespace Test
frame => AssertFrame.Element(frame, "input", 4, 0),
frame => AssertFrame.Attribute(frame, "type", "text", 1),
frame => AssertFrame.Attribute(frame, "value", "42", 2),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 3));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 3));
}
[Fact]
@ -417,7 +417,7 @@ namespace Test
frame => AssertFrame.Element(frame, "input", 4, 0),
frame => AssertFrame.Attribute(frame, "type", "text", 1),
frame => AssertFrame.Attribute(frame, "value", new DateTime(2018, 1, 1).ToString("MM/dd"), 2),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 3));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 3));
}
[Fact] // Additional coverage of OrphanTagHelperLoweringPass
@ -441,7 +441,7 @@ namespace Test
frame => AssertFrame.Attribute(frame, "visible", 1), // This gets reordered in the node writer
frame => AssertFrame.Attribute(frame, "type", "text", 2),
frame => AssertFrame.Attribute(frame, "value", "42", 3),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 4));
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 4));
}
[Fact] // Additional coverage of OrphanTagHelperLoweringPass
@ -465,7 +465,7 @@ namespace Test
frames,
frame => AssertFrame.Element(frame, "div", 7, 0),
frame => AssertFrame.Attribute(frame, "value", "42", 1),
frame => AssertFrame.Attribute(frame, "onchange", typeof(UIEventHandler), 2),
frame => AssertFrame.Attribute(frame, "onchange", typeof(Action<UIEventArgs>), 2),
frame => AssertFrame.Whitespace(frame, 3),
frame => AssertFrame.Element(frame, "span", 2, 4),
frame => AssertFrame.Text(frame, "42", 5),

Просмотреть файл

@ -18,7 +18,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
public void ComponentDiscovery_CanFindComponent_DefinedinCSharp()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -41,7 +41,7 @@ namespace Test
public void ComponentDiscovery_CanFindComponent_WithNamespace_DefinedinCSharp()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test.AnotherNamespace

Просмотреть файл

@ -18,7 +18,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
public void Render_ChildComponent_Simple()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -46,7 +46,7 @@ namespace Test
public void Render_ChildComponent_WithParameters()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -94,7 +94,7 @@ namespace Test
public void Render_ChildComponent_WithExplicitStringParameter()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -124,7 +124,7 @@ namespace Test
public void Render_ChildComponent_WithNonPropertyAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -165,7 +165,7 @@ namespace Test
public void Render_ChildComponent_WithEventHandler(string expression)
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -174,7 +174,7 @@ namespace Test
{
public class MyComponent : BlazorComponent
{
public UIMouseEventHandler OnClick { get; set; }
public Action<UIMouseEventArgs> OnClick { get; set; }
}
}
"));
@ -203,7 +203,7 @@ namespace Test
AssertFrame.Attribute(frame, "OnClick", 1);
// The handler will have been assigned to a lambda
var handler = Assert.IsType<UIMouseEventHandler>(frame.AttributeValue);
var handler = Assert.IsType<Action<UIMouseEventArgs>>(frame.AttributeValue);
Assert.Equal("Test.TestComponent", handler.Target.GetType().FullName);
});
}
@ -212,7 +212,7 @@ namespace Test
public void Render_ChildComponent_WithExplicitEventHandler()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -221,7 +221,7 @@ namespace Test
{
public class MyComponent : BlazorComponent
{
public UIEventHandler OnClick { get; set; }
public Action<UIEventArgs> OnClick { get; set; }
}
}
"));
@ -250,7 +250,7 @@ namespace Test
AssertFrame.Attribute(frame, "OnClick", 1);
// The handler will have been assigned to a lambda
var handler = Assert.IsType<UIEventHandler>(frame.AttributeValue);
var handler = Assert.IsType<Action<UIEventArgs>>(frame.AttributeValue);
Assert.Equal("Test.TestComponent", handler.Target.GetType().FullName);
Assert.Equal("Increment", handler.Method.Name);
});
@ -260,7 +260,7 @@ namespace Test
public void Render_ChildComponent_WithMinimizedBoolAttribute()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -289,7 +289,7 @@ namespace Test
public void Render_ChildComponent_WithChildContent()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -330,7 +330,7 @@ namespace Test
public void Render_ChildComponent_Nested()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;

Просмотреть файл

@ -16,7 +16,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
public void ChildComponent_WithParameters()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -54,7 +54,7 @@ namespace Test
public void ChildComponent_WithExplicitStringParameter()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -81,7 +81,7 @@ namespace Test
public void ChildComponent_WithNonPropertyAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -107,7 +107,7 @@ namespace Test
public void ChildComponent_WithLambdaEventHandler()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -116,7 +116,7 @@ namespace Test
{
public class MyComponent : BlazorComponent
{
public UIEventHandler OnClick { get; set; }
public Action<UIEventArgs> OnClick { get; set; }
}
}
"));
@ -143,7 +143,7 @@ namespace Test
public void ChildComponent_WithExplicitEventHandler()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -152,7 +152,7 @@ namespace Test
{
public class MyComponent : BlazorComponent
{
public UIEventHandler OnClick { get; set; }
public Action<UIEventArgs> OnClick { get; set; }
}
}
"));
@ -180,7 +180,7 @@ namespace Test
public void ChildComponent_WithChildContent()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -257,11 +257,93 @@ namespace Test
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_Action_MethodGroup()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""@OnClick"" />
@functions {
Task OnClick()
{
return Task.CompletedTask;
}
}");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_ActionEventArgs_MethodGroup()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""@OnClick"" />
@functions {
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
}");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_Action_Lambda()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""async (e) => await Task.Delay(10)"" />
");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_ActionEventArgs_Lambda()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""async (e) => await Task.Delay(10)"" />
");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact] // https://github.com/aspnet/Blazor/issues/597
public void Regression_597()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -292,7 +374,7 @@ namespace Test
public void BindToComponent_SpecifiesValue_WithMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -324,7 +406,7 @@ namespace Test
public void BindToComponent_SpecifiesValue_WithoutMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -356,7 +438,7 @@ namespace Test
public void BindToComponent_SpecifiesValueAndChangeEvent_WithMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -387,7 +469,7 @@ namespace Test
public void BindToComponent_SpecifiesValueAndChangeEvent_WithoutMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -418,7 +500,7 @@ namespace Test
public void BindToElement_WritesAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -448,7 +530,7 @@ namespace Test
public void BindToElementWithSuffix_WritesAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;

Просмотреть файл

@ -19,7 +19,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="2.6.1" />
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="2.8.0-beta3" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.5.0" />
<PackageReference Include="xunit" Version="2.3.1" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.3.1" />

Просмотреть файл

@ -32,6 +32,8 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
// so making sure it doesn't happen for each test.
private static readonly CSharpCompilation BaseCompilation;
private static CSharpParseOptions CSharpParseOptions { get; }
static RazorIntegrationTestBase()
{
var referenceAssemblyRoots = new[]
@ -52,6 +54,8 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
Array.Empty<SyntaxTree>(),
referenceAssemblies,
new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary));
CSharpParseOptions = new CSharpParseOptions(LanguageVersion.CSharp7_3);
}
public RazorIntegrationTestBase()
@ -59,6 +63,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
AdditionalSyntaxTrees = new List<SyntaxTree>();
AdditionalRazorItems = new List<RazorProjectItem>();
Configuration = BlazorExtensionInitializer.DefaultConfiguration;
FileSystem = new VirtualRazorProjectFileSystem();
PathSeparator = Path.DirectorySeparatorChar.ToString();
@ -162,7 +167,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
codeDocument = projectEngine.Process(item);
Assert.Empty(codeDocument.GetCSharpDocument().Diagnostics);
var syntaxTree = CSharpSyntaxTree.ParseText(codeDocument.GetCSharpDocument().GeneratedCode, path: item.FilePath);
var syntaxTree = Parse(codeDocument.GetCSharpDocument().GeneratedCode, path: item.FilePath);
AdditionalSyntaxTrees.Add(syntaxTree);
}
@ -192,7 +197,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
Assert.Empty(codeDocument.GetCSharpDocument().Diagnostics);
// Replace the 'declaration' syntax tree
var syntaxTree = CSharpSyntaxTree.ParseText(codeDocument.GetCSharpDocument().GeneratedCode, path: item.FilePath);
var syntaxTree = Parse(codeDocument.GetCSharpDocument().GeneratedCode, path: item.FilePath);
AdditionalSyntaxTrees.RemoveAll(st => st.FilePath == item.FilePath);
AdditionalSyntaxTrees.Add(syntaxTree);
}
@ -241,7 +246,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
var syntaxTrees = new[]
{
CSharpSyntaxTree.ParseText(cSharpResult.Code),
Parse(cSharpResult.Code),
};
var compilation = cSharpResult.BaseCompilation.AddSyntaxTrees(syntaxTrees);
@ -274,7 +279,6 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
Assembly = diagnostics.Any() ? null : Assembly.Load(peStream.ToArray())
};
}
}
protected IComponent CompileToComponent(string cshtmlSource)
@ -303,6 +307,11 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
return (IComponent)Activator.CreateInstance(componentType);
}
protected static CSharpSyntaxTree Parse(string text, string path = null)
{
return (CSharpSyntaxTree)CSharpSyntaxTree.ParseText(text, CSharpParseOptions, path: path);
}
protected static string FullTypeName<T>() => typeof(T).FullName.Replace('+', '.');
protected RenderTreeFrame[] GetRenderTree(IComponent component)

Просмотреть файл

@ -306,7 +306,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
Assert.Equal(1, frame.Sequence);
Assert.NotNull(frame.AttributeValue);
((UIEventHandler)frame.AttributeValue)(null);
((Action<UIEventArgs>)frame.AttributeValue)(null);
Assert.True((bool)handlerWasCalledProperty.GetValue(component));
});
}
@ -346,7 +346,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
AssertFrame.Attribute(frame, "onchange", 2);
// Trigger the change event to show it updates the property
((UIEventHandler)frame.AttributeValue)(new UIChangeEventArgs
((Action<UIEventArgs>)frame.AttributeValue)(new UIChangeEventArgs
{
Value = "Modified value"
});
@ -375,7 +375,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
AssertFrame.Attribute(frame, "onchange", 2);
// Trigger the change event to show it updates the property
((UIEventHandler)frame.AttributeValue)(new UIChangeEventArgs
((Action<UIEventArgs>)frame.AttributeValue)(new UIChangeEventArgs
{
Value = "Modified value"
});
@ -405,7 +405,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
// Trigger the change event to show it updates the property
var newDateValue = new DateTime(2018, 3, 5, 4, 5, 6);
((UIEventHandler)frame.AttributeValue)(new UIChangeEventArgs
((Action<UIEventArgs>)frame.AttributeValue)(new UIChangeEventArgs
{
Value = newDateValue.ToString()
});
@ -435,7 +435,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
AssertFrame.Attribute(frame, "onchange", 2);
// Trigger the change event to show it updates the property
((UIEventHandler)frame.AttributeValue)(new UIChangeEventArgs
((Action<UIEventArgs>)frame.AttributeValue)(new UIChangeEventArgs
{
Value = new DateTime(2018, 3, 5).ToString(testDateFormat)
});
@ -542,7 +542,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
AssertFrame.Attribute(frame, "onchange", 2);
// Trigger the change event to show it updates the property
((UIEventHandler)frame.AttributeValue)(new UIChangeEventArgs
((Action<UIEventArgs>)frame.AttributeValue)(new UIChangeEventArgs
{
Value = false
});
@ -572,7 +572,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
AssertFrame.Attribute(frame, "onchange", 2);
// Trigger the change event to show it updates the property
((UIEventHandler)frame.AttributeValue)(new UIChangeEventArgs
((Action<UIEventArgs>)frame.AttributeValue)(new UIChangeEventArgs
{
Value = MyEnum.SecondValue.ToString()
});

Просмотреть файл

@ -14,7 +14,7 @@ namespace Microsoft.AspNetCore.Blazor.Build.Test
public void ChildComponent_Simple()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -40,7 +40,7 @@ namespace Test
public void ChildComponent_WithParameters()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -78,7 +78,7 @@ namespace Test
public void ChildComponent_WithExplicitStringParameter()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -105,7 +105,7 @@ namespace Test
public void ChildComponent_WithNonPropertyAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -132,7 +132,7 @@ namespace Test
public void ChildComponent_WithLambdaEventHandler()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -141,7 +141,7 @@ namespace Test
{
public class MyComponent : BlazorComponent
{
public UIEventHandler OnClick { get; set; }
public Action<UIEventArgs> OnClick { get; set; }
}
}
"));
@ -168,7 +168,7 @@ namespace Test
public void ChildComponent_WithExplicitEventHandler()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -177,7 +177,7 @@ namespace Test
{
public class MyComponent : BlazorComponent
{
public UIEventHandler OnClick { get; set; }
public Action<UIEventArgs> OnClick { get; set; }
}
}
"));
@ -205,7 +205,7 @@ namespace Test
public void ChildComponent_WithChildContent()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -235,7 +235,7 @@ namespace Test
public void ChildComponent_WithPageDirective()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -366,6 +366,88 @@ namespace Test
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_Action_MethodGroup()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""@OnClick"" />
@functions {
Task OnClick()
{
return Task.CompletedTask;
}
}");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_ActionEventArgs_MethodGroup()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""@OnClick"" />
@functions {
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
}");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_Action_Lambda()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""async (e) => await Task.Delay(10)"" />
");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact]
public void AsyncEventHandler_OnElement_ActionEventArgs_Lambda()
{
// Arrange
// Act
var generated = CompileToCSharp(@"
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<input onclick=""async (e) => await Task.Delay(10)"" />
");
// Assert
AssertDocumentNodeMatchesBaseline(generated.CodeDocument);
AssertCSharpDocumentMatchesBaseline(generated.CodeDocument);
CompileToAssembly(generated);
}
[Fact]
public void ScriptTag_WithErrorSuppressed()
{
@ -421,7 +503,7 @@ namespace Test
public void LeadingWhiteSpace_WithComponent()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -484,7 +566,7 @@ namespace Test
public void TrailingWhiteSpace_WithComponent()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -514,7 +596,7 @@ namespace Test
public void Regression_597()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -545,7 +627,7 @@ namespace Test
public void BindToComponent_SpecifiesValue_WithMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -577,7 +659,7 @@ namespace Test
public void BindToComponent_SpecifiesValue_WithoutMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -609,7 +691,7 @@ namespace Test
public void BindToComponent_SpecifiesValueAndChangeEvent_WithMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -640,7 +722,7 @@ namespace Test
public void BindToComponent_SpecifiesValueAndChangeEvent_WithoutMatchingProperties()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -671,7 +753,7 @@ namespace Test
public void BindToElement_WritesAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -701,7 +783,7 @@ namespace Test
public void BindToElementWithSuffix_WritesAttributes()
{
// Arrange
AdditionalSyntaxTrees.Add(CSharpSyntaxTree.ParseText(@"
AdditionalSyntaxTrees.Add(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;

Просмотреть файл

@ -0,0 +1,37 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
#line 1 "x:\dir\subdir\Test\TestComponent.cshtml"
using System.Threading.Tasks;
#line default
#line hidden
#line 2 "x:\dir\subdir\Test\TestComponent.cshtml"
using Microsoft.AspNetCore.Blazor;
#line default
#line hidden
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 219
private void __RazorDirectiveTokenHelpers__() {
}
#pragma warning restore 219
#pragma warning disable 0414
private static System.Object __o = null;
#pragma warning restore 0414
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
__o = Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>("async (e) => await Task.Delay(10)");
}
#pragma warning restore 1998
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,35 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [12] ) - System
UsingDirective - (18:2,1 [32] ) - System.Collections.Generic
UsingDirective - (53:3,1 [17] ) - System.Linq
UsingDirective - (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
DesignTimeDirective -
DirectiveToken - (14:0,14 [32] ) - "*, Microsoft.AspNetCore.Blazor"
DirectiveToken - (14:0,14 [9] ) - "*, Test"
CSharpCode -
IntermediateToken - - CSharp - #pragma warning disable 0414
CSharpCode -
IntermediateToken - - CSharp - private static System.Object __o = null;
CSharpCode -
IntermediateToken - - CSharp - #pragma warning restore 0414
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - - CSharp - "async (e) => await Task.Delay(10)"
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />
HtmlContent - (120:2,53 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (120:2,53 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n

Просмотреть файл

@ -0,0 +1,10 @@
Source Location: (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml)
|using System.Threading.Tasks|
Generated Location: (222:9,0 [28] )
|using System.Threading.Tasks|
Source Location: (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml)
|using Microsoft.AspNetCore.Blazor|
Generated Location: (335:14,0 [33] )
|using Microsoft.AspNetCore.Blazor|

Просмотреть файл

@ -0,0 +1,46 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
#line 1 "x:\dir\subdir\Test\TestComponent.cshtml"
using System.Threading.Tasks;
#line default
#line hidden
#line 2 "x:\dir\subdir\Test\TestComponent.cshtml"
using Microsoft.AspNetCore.Blazor;
#line default
#line hidden
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 219
private void __RazorDirectiveTokenHelpers__() {
}
#pragma warning restore 219
#pragma warning disable 0414
private static System.Object __o = null;
#pragma warning restore 0414
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
__o = Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(OnClick);
}
#pragma warning restore 1998
#line 4 "x:\dir\subdir\Test\TestComponent.cshtml"
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
#line default
#line hidden
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,37 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [12] ) - System
UsingDirective - (18:2,1 [32] ) - System.Collections.Generic
UsingDirective - (53:3,1 [17] ) - System.Linq
UsingDirective - (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
DesignTimeDirective -
DirectiveToken - (14:0,14 [32] ) - "*, Microsoft.AspNetCore.Blazor"
DirectiveToken - (14:0,14 [9] ) - "*, Test"
CSharpCode -
IntermediateToken - - CSharp - #pragma warning disable 0414
CSharpCode -
IntermediateToken - - CSharp - private static System.Object __o = null;
CSharpCode -
IntermediateToken - - CSharp - #pragma warning restore 0414
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - (84:2,17 [7] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - OnClick
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />
HtmlContent - (95:2,28 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (95:2,28 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
CSharpCode - (109:3,12 [91] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (109:3,12 [91] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - \n Task OnClick(UIMouseEventArgs e) \n {\n return Task.CompletedTask;\n }\n

Просмотреть файл

@ -0,0 +1,30 @@
Source Location: (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml)
|using System.Threading.Tasks|
Generated Location: (222:9,0 [28] )
|using System.Threading.Tasks|
Source Location: (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml)
|using Microsoft.AspNetCore.Blazor|
Generated Location: (335:14,0 [33] )
|using Microsoft.AspNetCore.Blazor|
Source Location: (84:2,17 [7] x:\dir\subdir\Test\TestComponent.cshtml)
|OnClick|
Generated Location: (1110:31,136 [7] )
|OnClick|
Source Location: (109:3,12 [91] x:\dir\subdir\Test\TestComponent.cshtml)
|
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
|
Generated Location: (1233:35,12 [91] )
|
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
|

Просмотреть файл

@ -0,0 +1,37 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
#line 1 "x:\dir\subdir\Test\TestComponent.cshtml"
using System.Threading.Tasks;
#line default
#line hidden
#line 2 "x:\dir\subdir\Test\TestComponent.cshtml"
using Microsoft.AspNetCore.Blazor;
#line default
#line hidden
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 219
private void __RazorDirectiveTokenHelpers__() {
}
#pragma warning restore 219
#pragma warning disable 0414
private static System.Object __o = null;
#pragma warning restore 0414
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
__o = Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>("async (e) => await Task.Delay(10)");
}
#pragma warning restore 1998
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,35 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [12] ) - System
UsingDirective - (18:2,1 [32] ) - System.Collections.Generic
UsingDirective - (53:3,1 [17] ) - System.Linq
UsingDirective - (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
DesignTimeDirective -
DirectiveToken - (14:0,14 [32] ) - "*, Microsoft.AspNetCore.Blazor"
DirectiveToken - (14:0,14 [9] ) - "*, Test"
CSharpCode -
IntermediateToken - - CSharp - #pragma warning disable 0414
CSharpCode -
IntermediateToken - - CSharp - private static System.Object __o = null;
CSharpCode -
IntermediateToken - - CSharp - #pragma warning restore 0414
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - - CSharp - "async (e) => await Task.Delay(10)"
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />
HtmlContent - (120:2,53 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (120:2,53 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n

Просмотреть файл

@ -0,0 +1,10 @@
Source Location: (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml)
|using System.Threading.Tasks|
Generated Location: (222:9,0 [28] )
|using System.Threading.Tasks|
Source Location: (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml)
|using Microsoft.AspNetCore.Blazor|
Generated Location: (335:14,0 [33] )
|using Microsoft.AspNetCore.Blazor|

Просмотреть файл

@ -0,0 +1,46 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
#line 1 "x:\dir\subdir\Test\TestComponent.cshtml"
using System.Threading.Tasks;
#line default
#line hidden
#line 2 "x:\dir\subdir\Test\TestComponent.cshtml"
using Microsoft.AspNetCore.Blazor;
#line default
#line hidden
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 219
private void __RazorDirectiveTokenHelpers__() {
}
#pragma warning restore 219
#pragma warning disable 0414
private static System.Object __o = null;
#pragma warning restore 0414
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
__o = Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(OnClick);
}
#pragma warning restore 1998
#line 4 "x:\dir\subdir\Test\TestComponent.cshtml"
Task OnClick()
{
return Task.CompletedTask;
}
#line default
#line hidden
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,37 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [12] ) - System
UsingDirective - (18:2,1 [32] ) - System.Collections.Generic
UsingDirective - (53:3,1 [17] ) - System.Linq
UsingDirective - (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
DesignTimeDirective -
DirectiveToken - (14:0,14 [32] ) - "*, Microsoft.AspNetCore.Blazor"
DirectiveToken - (14:0,14 [9] ) - "*, Test"
CSharpCode -
IntermediateToken - - CSharp - #pragma warning disable 0414
CSharpCode -
IntermediateToken - - CSharp - private static System.Object __o = null;
CSharpCode -
IntermediateToken - - CSharp - #pragma warning restore 0414
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (29:0,29 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (65:1,34 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - (84:2,17 [7] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - OnClick
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />
HtmlContent - (95:2,28 [2] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (95:2,28 [2] x:\dir\subdir\Test\TestComponent.cshtml) - Html - \n
CSharpCode - (109:3,12 [73] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (109:3,12 [73] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - \n Task OnClick() \n {\n return Task.CompletedTask;\n }\n

Просмотреть файл

@ -0,0 +1,30 @@
Source Location: (1:0,1 [28] x:\dir\subdir\Test\TestComponent.cshtml)
|using System.Threading.Tasks|
Generated Location: (222:9,0 [28] )
|using System.Threading.Tasks|
Source Location: (32:1,1 [33] x:\dir\subdir\Test\TestComponent.cshtml)
|using Microsoft.AspNetCore.Blazor|
Generated Location: (335:14,0 [33] )
|using Microsoft.AspNetCore.Blazor|
Source Location: (84:2,17 [7] x:\dir\subdir\Test\TestComponent.cshtml)
|OnClick|
Generated Location: (1110:31,136 [7] )
|OnClick|
Source Location: (109:3,12 [73] x:\dir\subdir\Test\TestComponent.cshtml)
|
Task OnClick()
{
return Task.CompletedTask;
}
|
Generated Location: (1233:35,12 [73] )
|
Task OnClick()
{
return Task.CompletedTask;
}
|

Просмотреть файл

@ -29,7 +29,7 @@ global::System.Object __typeHelper = "*, TestAssembly";
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
__o = new Microsoft.AspNetCore.Blazor.UIEventHandler(
__o = new System.Action<Microsoft.AspNetCore.Blazor.UIEventArgs>(
#line 3 "x:\dir\subdir\Test\TestComponent.cshtml"
Increment

Просмотреть файл

@ -10,7 +10,7 @@ Generated Location: (586:19,38 [15] )
Source Location: (90:2,23 [9] x:\dir\subdir\Test\TestComponent.cshtml)
|Increment|
Generated Location: (1154:33,23 [9] )
Generated Location: (1166:33,23 [9] )
|Increment|
Source Location: (118:4,12 [100] x:\dir\subdir\Test\TestComponent.cshtml)
@ -20,7 +20,7 @@ Source Location: (118:4,12 [100] x:\dir\subdir\Test\TestComponent.cshtml)
counter++;
}
|
Generated Location: (1471:44,12 [100] )
Generated Location: (1483:44,12 [100] )
|
private int counter;
private void Increment(UIEventArgs e) {

Просмотреть файл

@ -24,7 +24,7 @@ global::System.Object __typeHelper = "*, TestAssembly";
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
__o = new Microsoft.AspNetCore.Blazor.UIEventHandler(
__o = new System.Action<Microsoft.AspNetCore.Blazor.UIEventArgs>(
#line 2 "x:\dir\subdir\Test\TestComponent.cshtml"
(e) => { Increment(); }

Просмотреть файл

@ -5,7 +5,7 @@ Generated Location: (468:14,38 [15] )
Source Location: (55:1,24 [23] x:\dir\subdir\Test\TestComponent.cshtml)
|(e) => { Increment(); }|
Generated Location: (1037:28,24 [23] )
Generated Location: (1049:28,24 [23] )
|(e) => { Increment(); }|
Source Location: (98:3,12 [87] x:\dir\subdir\Test\TestComponent.cshtml)
@ -15,7 +15,7 @@ Source Location: (98:3,12 [87] x:\dir\subdir\Test\TestComponent.cshtml)
counter++;
}
|
Generated Location: (1368:39,12 [87] )
Generated Location: (1380:39,12 [87] )
|
private int counter;
private void Increment() {

Просмотреть файл

@ -0,0 +1,24 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Blazor;
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
builder.OpenElement(0, "input");
builder.AddAttribute(1, "onclick", Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>("async (e) => await Task.Delay(10)"));
builder.CloseElement();
}
#pragma warning restore 1998
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,20 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [14] ) - System
UsingDirective - (18:2,1 [34] ) - System.Collections.Generic
UsingDirective - (53:3,1 [19] ) - System.Linq
UsingDirective - (1:0,1 [30] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [35] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - - CSharp - "async (e) => await Task.Delay(10)"
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />

Просмотреть файл

@ -0,0 +1,33 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Blazor;
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
builder.OpenElement(0, "input");
builder.AddAttribute(1, "onclick", Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(OnClick));
builder.CloseElement();
}
#pragma warning restore 1998
#line 4 "x:\dir\subdir\Test\TestComponent.cshtml"
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
#line default
#line hidden
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,22 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [14] ) - System
UsingDirective - (18:2,1 [34] ) - System.Collections.Generic
UsingDirective - (53:3,1 [19] ) - System.Linq
UsingDirective - (1:0,1 [30] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [35] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - (84:2,17 [7] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - OnClick
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />
CSharpCode - (109:3,12 [91] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (109:3,12 [91] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - \n Task OnClick(UIMouseEventArgs e) \n {\n return Task.CompletedTask;\n }\n

Просмотреть файл

@ -0,0 +1,15 @@
Source Location: (109:3,12 [91] x:\dir\subdir\Test\TestComponent.cshtml)
|
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
|
Generated Location: (922:22,12 [91] )
|
Task OnClick(UIMouseEventArgs e)
{
return Task.CompletedTask;
}
|

Просмотреть файл

@ -0,0 +1,24 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Blazor;
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
builder.OpenElement(0, "input");
builder.AddAttribute(1, "onclick", Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>("async (e) => await Task.Delay(10)"));
builder.CloseElement();
}
#pragma warning restore 1998
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,20 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [14] ) - System
UsingDirective - (18:2,1 [34] ) - System.Collections.Generic
UsingDirective - (53:3,1 [19] ) - System.Linq
UsingDirective - (1:0,1 [30] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [35] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - - CSharp - "async (e) => await Task.Delay(10)"
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />

Просмотреть файл

@ -0,0 +1,33 @@
// <auto-generated/>
#pragma warning disable 1591
namespace Test
{
#line hidden
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Blazor;
public class TestComponent : Microsoft.AspNetCore.Blazor.Components.BlazorComponent
{
#pragma warning disable 1998
protected override void BuildRenderTree(Microsoft.AspNetCore.Blazor.RenderTree.RenderTreeBuilder builder)
{
base.BuildRenderTree(builder);
builder.OpenElement(0, "input");
builder.AddAttribute(1, "onclick", Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(OnClick));
builder.CloseElement();
}
#pragma warning restore 1998
#line 4 "x:\dir\subdir\Test\TestComponent.cshtml"
Task OnClick()
{
return Task.CompletedTask;
}
#line default
#line hidden
}
}
#pragma warning restore 1591

Просмотреть файл

@ -0,0 +1,22 @@
Document -
NamespaceDeclaration - - Test
UsingDirective - (3:1,1 [14] ) - System
UsingDirective - (18:2,1 [34] ) - System.Collections.Generic
UsingDirective - (53:3,1 [19] ) - System.Linq
UsingDirective - (1:0,1 [30] x:\dir\subdir\Test\TestComponent.cshtml) - System.Threading.Tasks
UsingDirective - (32:1,1 [35] x:\dir\subdir\Test\TestComponent.cshtml) - Microsoft.AspNetCore.Blazor
ClassDeclaration - - public - TestComponent - Microsoft.AspNetCore.Blazor.Components.BlazorComponent -
MethodDeclaration - - protected override - void - BuildRenderTree
CSharpCode -
IntermediateToken - - CSharp - base.BuildRenderTree(builder);
HtmlContent -
IntermediateToken - - Html - <input
HtmlAttribute - - =" - "
CSharpExpressionAttributeValue - -
IntermediateToken - - CSharp - Microsoft.AspNetCore.Blazor.Components.BindMethods.GetEventHandlerValue<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>(
IntermediateToken - (84:2,17 [7] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - OnClick
IntermediateToken - - CSharp - )
HtmlContent -
IntermediateToken - - Html - />
CSharpCode - (109:3,12 [73] x:\dir\subdir\Test\TestComponent.cshtml)
IntermediateToken - (109:3,12 [73] x:\dir\subdir\Test\TestComponent.cshtml) - CSharp - \n Task OnClick() \n {\n return Task.CompletedTask;\n }\n

Просмотреть файл

@ -0,0 +1,15 @@
Source Location: (109:3,12 [73] x:\dir\subdir\Test\TestComponent.cshtml)
|
Task OnClick()
{
return Task.CompletedTask;
}
|
Generated Location: (922:22,12 [73] )
|
Task OnClick()
{
return Task.CompletedTask;
}
|

Просмотреть файл

@ -15,7 +15,7 @@ namespace Test
{
base.BuildRenderTree(builder);
builder.OpenComponent<Test.MyComponent>(0);
builder.AddAttribute(1, "OnClick", new Microsoft.AspNetCore.Blazor.UIEventHandler(Increment));
builder.AddAttribute(1, "OnClick", new System.Action<Microsoft.AspNetCore.Blazor.UIEventArgs>(Increment));
builder.CloseComponent();
}
#pragma warning restore 1998

Просмотреть файл

@ -5,7 +5,7 @@ Source Location: (118:4,12 [100] x:\dir\subdir\Test\TestComponent.cshtml)
counter++;
}
|
Generated Location: (866:22,12 [100] )
Generated Location: (878:22,12 [100] )
|
private int counter;
private void Increment(UIEventArgs e) {

Просмотреть файл

@ -14,7 +14,7 @@ namespace Test
{
base.BuildRenderTree(builder);
builder.OpenComponent<Test.MyComponent>(0);
builder.AddAttribute(1, "OnClick", new Microsoft.AspNetCore.Blazor.UIEventHandler(e => { Increment(); }));
builder.AddAttribute(1, "OnClick", new System.Action<Microsoft.AspNetCore.Blazor.UIEventArgs>(e => { Increment(); }));
builder.CloseComponent();
}
#pragma warning restore 1998

Просмотреть файл

@ -5,7 +5,7 @@ Source Location: (96:3,12 [87] x:\dir\subdir\Test\TestComponent.cshtml)
counter++;
}
|
Generated Location: (838:21,12 [87] )
Generated Location: (850:21,12 [87] )
|
private int counter;
private void Increment() {

Просмотреть файл

@ -63,6 +63,23 @@ namespace Microsoft.AspNetCore.Blazor.E2ETest.Tests
Assert.Equal("Current count: 1", countDisplayElement.Text);
}
[Fact]
public void CanTriggerAsyncEventHandlers()
{
// Initial state is stopped
var appElement = MountTestComponent<AsyncEventHandlerComponent>();
var stateElement = appElement.FindElement(By.Id("state"));
Assert.Equal("Stopped", stateElement.Text);
// Clicking 'tick' changes the state, and starts a task
appElement.FindElement(By.Id("tick")).Click();
Assert.Equal("Started", stateElement.Text);
// Clicking 'tock' completes the task, which updates the state
appElement.FindElement(By.Id("tock")).Click();
Assert.Equal("Stopped", stateElement.Text);
}
[Fact]
public void CanTriggerKeyPressEvents()
{

Просмотреть файл

@ -26,10 +26,19 @@ namespace Microsoft.AspNetCore.Blazor.Razor.Extensions
Array.Empty<SyntaxTree>(),
metadataReferences,
new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary));
CSharpParseOptions = new CSharpParseOptions(LanguageVersion.CSharp7_3);
}
protected static Compilation BaseCompilation { get; }
protected static CSharpParseOptions CSharpParseOptions { get; }
protected static CSharpSyntaxTree Parse(string text)
{
return (CSharpSyntaxTree)CSharpSyntaxTree.ParseText(text, CSharpParseOptions);
}
// For simplicity in testing, exclude the built-in components. We'll add more and we
// don't want to update the tests when that happens.
protected static TagHelperDescriptor[] ExcludeBuiltInComponents(TagHelperDescriptorProviderContext context)

Просмотреть файл

@ -15,7 +15,7 @@ namespace Microsoft.AspNetCore.Blazor.Razor.Extensions
public void Excecute_FindsBindTagHelperOnComponentType_CreatesDescriptor()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -128,7 +128,7 @@ namespace Test
public void Excecute_NoMatchedPropertiesOnComponent_IgnoresComponent()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor.Components;
@ -170,7 +170,7 @@ namespace Test
public void Excecute_BindOnElement_CreatesDescriptor()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -303,7 +303,7 @@ namespace Test
public void Execute_BindOnElementWithSuffix_CreatesDescriptor()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -357,7 +357,7 @@ namespace Test
public void Execute_BindOnInputElementWithoutTypeAttribute_CreatesDescriptor()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -412,7 +412,7 @@ namespace Test
public void Execute_BindOnInputElementWithTypeAttribute_CreatesDescriptor()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -479,7 +479,7 @@ namespace Test
public void Execute_BindOnInputElementWithTypeAttributeAndSuffix_CreatesDescriptor()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test

Просмотреть файл

@ -16,7 +16,7 @@ namespace Microsoft.AspNetCore.Blazor.Razor.Extensions
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -129,7 +129,7 @@ namespace Test
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -169,7 +169,7 @@ namespace Test
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -214,7 +214,7 @@ namespace Test
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using Microsoft.AspNetCore.Blazor.Components;
namespace Test
@ -265,7 +265,8 @@ namespace Test
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;
@ -273,7 +274,7 @@ namespace Test
{
public class MyComponent : BlazorComponent
{
public UIEventHandler OnClick { get; set; }
public Action<UIMouseEventArgs> OnClick { get; set; }
}
}
@ -298,7 +299,7 @@ namespace Test
var attribute = Assert.Single(component.BoundAttributes);
Assert.Equal("OnClick", attribute.Name);
Assert.Equal(BlazorApi.UIEventHandler.FullTypeName, attribute.TypeName);
Assert.Equal("System.Action<Microsoft.AspNetCore.Blazor.UIMouseEventArgs>", attribute.TypeName);
Assert.False(attribute.HasIndexer);
Assert.False(attribute.IsBooleanProperty);

Просмотреть файл

@ -15,7 +15,7 @@ namespace Microsoft.AspNetCore.Blazor.Razor.Extensions
public void Excecute_EventHandler_CreatesDescriptor()
{
// Arrange
var compilation = BaseCompilation.AddSyntaxTrees(CSharpSyntaxTree.ParseText(@"
var compilation = BaseCompilation.AddSyntaxTrees(Parse(@"
using System;
using Microsoft.AspNetCore.Blazor;
using Microsoft.AspNetCore.Blazor.Components;

Просмотреть файл

@ -17,7 +17,7 @@
</ItemGroup>
<ItemGroup>
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="2.6.1" />
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="2.8.0-beta3" />
<PackageReference Include="Microsoft.Extensions.DependencyModel" Version="2.0.4" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.5.0" />
<PackageReference Include="xunit" Version="2.3.1" />

Просмотреть файл

@ -168,7 +168,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
{
// Arrange
var builder = new RenderTreeBuilder(new TestRenderer());
UIEventHandler eventHandler = eventInfo => { };
Action<UIEventArgs> eventHandler = eventInfo => { };
// Act
builder.OpenElement(0, "myelement"); // 0: <myelement
@ -498,12 +498,12 @@ namespace Microsoft.AspNetCore.Blazor.Test
}
[Fact]
public void AddAttribute_Element_UIEventHandler_AddsFrame()
public void AddAttribute_Element_EventHandler_AddsFrame()
{
// Arrange
var builder = new RenderTreeBuilder(new TestRenderer());
var value = new UIEventHandler((e) => { });
var value = new Action<UIEventArgs>((e) => { });
// Act
builder.OpenElement(0, "elem");
@ -518,14 +518,14 @@ namespace Microsoft.AspNetCore.Blazor.Test
}
[Fact]
public void AddAttribute_Element_NullUIEventHandler_IgnoresFrame()
public void AddAttribute_Element_NullEventHandler_IgnoresFrame()
{
// Arrange
var builder = new RenderTreeBuilder(new TestRenderer());
// Act
builder.OpenElement(0, "elem");
builder.AddAttribute(1, "attr", (UIEventHandler)null);
builder.AddAttribute(1, "attr", (Action<UIEventArgs>)null);
builder.CloseElement();
// Assert
@ -571,15 +571,15 @@ namespace Microsoft.AspNetCore.Blazor.Test
frame => AssertFrame.Element(frame, "elem", 1, 0));
}
public static TheoryData<UIEventHandler> UIEventHandlerValues => new TheoryData<UIEventHandler>
public static TheoryData<Action<UIEventArgs>> EventHandlerValues => new TheoryData<Action<UIEventArgs>>
{
null,
(e) => { },
};
[Theory]
[MemberData(nameof(UIEventHandlerValues))]
public void AddAttribute_Component_EventHandlerValue_SetsAttributeValue(UIEventHandler value)
[MemberData(nameof(EventHandlerValues))]
public void AddAttribute_Component_EventHandlerValue_SetsAttributeValue(Action<UIEventArgs> value)
{
// Arrange
var builder = new RenderTreeBuilder(new TestRenderer());
@ -688,12 +688,12 @@ namespace Microsoft.AspNetCore.Blazor.Test
}
[Fact]
public void AddAttribute_Element_ObjectUIEventHandler_AddsFrame()
public void AddAttribute_Element_ObjectEventHandler_AddsFrame()
{
// Arrange
var builder = new RenderTreeBuilder(new TestRenderer());
var value = new UIEventHandler((e) => { });
var value = new Action<UIEventArgs>((e) => { });
// Act
builder.OpenElement(0, "elem");
@ -713,7 +713,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
// Arrange
var builder = new RenderTreeBuilder(new TestRenderer());
var value = new UIEventHandler((e) => { });
var value = new Action<UIEventArgs>((e) => { });
// Act
builder.OpenComponent<TestComponent>(0);

Просмотреть файл

@ -421,9 +421,9 @@ namespace Microsoft.AspNetCore.Blazor.Test
public void RecognizesAttributeEventHandlerValuesChanged()
{
// Arrange
UIEventHandler retainedHandler = _ => { };
UIEventHandler removedHandler = _ => { };
UIEventHandler addedHandler = _ => { };
Action<UIEventArgs> retainedHandler = _ => { };
Action<UIEventArgs> removedHandler = _ => { };
Action<UIEventArgs> addedHandler = _ => { };
oldTree.OpenElement(0, "My element");
oldTree.AddAttribute(1, "onfoo", retainedHandler);
oldTree.AddAttribute(2, "onbar", removedHandler);
@ -1159,7 +1159,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
public void PreservesEventHandlerIdsForRetainedEventHandlers()
{
// Arrange
UIEventHandler retainedHandler = _ => { };
Action<UIEventArgs> retainedHandler = _ => { };
oldTree.OpenElement(0, "My element");
oldTree.AddAttribute(1, "ontest", retainedHandler);
oldTree.CloseElement();
@ -1185,7 +1185,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
public void PreservesEventHandlerIdsForRetainedEventHandlers_SlowPath()
{
// Arrange
UIEventHandler retainedHandler = _ => { };
Action<UIEventArgs> retainedHandler = _ => { };
oldTree.OpenElement(0, "My element");
oldTree.AddAttribute(0, "ontest", retainedHandler);
oldTree.CloseElement();

Просмотреть файл

@ -4,6 +4,7 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Blazor.Components;
using Microsoft.AspNetCore.Blazor.Rendering;
using Microsoft.AspNetCore.Blazor.RenderTree;
@ -289,7 +290,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
{
// Arrange: Render a component with an event handler
var renderer = new TestRenderer();
UIEventHandler handler = args => throw new NotImplementedException();
Action<UIEventArgs> handler = args => throw new NotImplementedException();
var component = new TestComponent(builder =>
{
builder.OpenElement(0, "mybutton");
@ -531,7 +532,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
// Arrange
var renderer = new TestRenderer();
var eventCount = 0;
UIEventHandler origEventHandler = args => { eventCount++; };
Action<UIEventArgs> origEventHandler = args => { eventCount++; };
var component = new EventComponent { OnTest = origEventHandler };
var componentId = renderer.AssignComponentId(component);
component.TriggerRender();
@ -568,7 +569,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
// Arrange
var renderer = new TestRenderer();
var eventCount = 0;
UIEventHandler origEventHandler = args => { eventCount++; };
Action<UIEventArgs> origEventHandler = args => { eventCount++; };
var component = new EventComponent { OnTest = origEventHandler };
var componentId = renderer.AssignComponentId(component);
component.TriggerRender();
@ -601,7 +602,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
// Arrange
var renderer = new TestRenderer();
var eventCount = 0;
UIEventHandler origEventHandler = args => { eventCount++; };
Action<UIEventArgs> origEventHandler = args => { eventCount++; };
var component = new ConditionalParentComponent<EventComponent>
{
IncludeChild = true,
@ -650,7 +651,7 @@ namespace Microsoft.AspNetCore.Blazor.Test
// Arrange
var renderer = new TestRenderer();
var eventCount = 0;
UIEventHandler origEventHandler = args => { eventCount++; };
Action<UIEventArgs> origEventHandler = args => { eventCount++; };
var component = new EventComponent { OnTest = origEventHandler };
var componentId = renderer.AssignComponentId(component);
component.TriggerRender();
@ -1011,8 +1012,8 @@ namespace Microsoft.AspNetCore.Blazor.Test
private class EventComponent : AutoRenderComponent, IComponent, IHandleEvent
{
public UIEventHandler OnTest { get; set; }
public UIMouseEventHandler OnClick { get; set; }
public Action<UIEventArgs> OnTest { get; set; }
public Action<UIMouseEventArgs> OnClick { get; set; }
public Action OnClickAction { get; set; }
public bool SkipElement { get; set; }
@ -1044,8 +1045,10 @@ namespace Microsoft.AspNetCore.Blazor.Test
builder.AddContent(6, $"Render count: {++renderCount}");
}
public void HandleEvent(UIEventHandler handler, UIEventArgs args)
=> handler(args);
public void HandleEvent(EventHandlerInvoker binding, UIEventArgs args)
{
binding.Invoke(args);
}
}
private class ConditionalParentComponent<T> : AutoRenderComponent where T : IComponent
@ -1105,9 +1108,9 @@ namespace Microsoft.AspNetCore.Blazor.Test
Render();
}
public void HandleEvent(UIEventHandler handler, UIEventArgs args)
public void HandleEvent(EventHandlerInvoker binding, UIEventArgs args)
{
handler(args);
var task = binding.Invoke(args);
Render();
}
@ -1149,9 +1152,9 @@ namespace Microsoft.AspNetCore.Blazor.Test
public bool CheckboxEnabled;
public string SomeStringProperty;
public void HandleEvent(UIEventHandler handler, UIEventArgs args)
public void HandleEvent(EventHandlerInvoker binding, UIEventArgs args)
{
handler(args);
binding.Invoke(args);
TriggerRender();
}

Просмотреть файл

@ -47,7 +47,7 @@ namespace Microsoft.AspNetCore.Blazor.Test.Helpers
Assert.Equal(attributeValue, frame.AttributeValue);
}
public static void Attribute(RenderTreeFrame frame, string attributeName, UIEventHandler attributeEventHandlerValue, int? sequence = null)
public static void Attribute(RenderTreeFrame frame, string attributeName, Action<UIEventArgs> attributeEventHandlerValue, int? sequence = null)
{
AssertFrame.Attribute(frame, attributeName, sequence);
Assert.Equal(attributeEventHandlerValue, frame.AttributeValue);

Просмотреть файл

@ -0,0 +1,35 @@
@using System.Threading.Tasks
@using Microsoft.AspNetCore.Blazor
<div>
<span id="state">@state</span>
<button id="tick" onclick="@Tick">Tick</button>
<button id="tock" onclick="@Tock">Tock</button>
</div>
@functions
{
TaskCompletionSource<object> _tcs;
string state = "Stopped";
Task Tick(UIMouseEventArgs e)
{
if (_tcs == null)
{
_tcs = new TaskCompletionSource<object>();
state = "Started";
return _tcs.Task.ContinueWith((task) =>
{
state = "Stopped";
_tcs = null;
});
}
return Task.CompletedTask;
}
void Tock(UIMouseEventArgs e)
{
_tcs.TrySetResult(null);
}
}

Просмотреть файл

@ -1,4 +1,4 @@
<Project Sdk="Microsoft.NET.Sdk.Web">
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>

Просмотреть файл

@ -10,6 +10,7 @@
Select test:
<select onchange="mountTestComponent(event.target.value)">
<option value="">Choose...</option>
<option value="BasicTestApp.AsyncEventHandlerComponent">Async event handlers</option>
<option value="BasicTestApp.AddRemoveChildComponents">Add/remove child components</option>
<option value="BasicTestApp.CounterComponent">Counter</option>
<option value="BasicTestApp.CounterComponentUsingChild">Counter using child component</option>