diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index 3acc059820..cb9cb3cdff 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -19,4 +19,4 @@ /src/Servers/ @tratcher @jkotalik @anurse @halter73 /src/Middleware/Rewrite @jkotalik @anurse /src/Middleware/HttpsPolicy @jkotalik @anurse -/src/SignalR/ @mikaelm12 @BrennanConroy @halter73 @anurse +/src/SignalR/ @BrennanConroy @halter73 @anurse diff --git a/eng/ProjectReferences.props b/eng/ProjectReferences.props index 4210405c67..3ac3e8dbf6 100644 --- a/eng/ProjectReferences.props +++ b/eng/ProjectReferences.props @@ -15,6 +15,7 @@ + diff --git a/src/Components/Blazor/Server/src/MonoDebugProxy/BlazorMonoDebugProxyAppBuilderExtensions.cs b/src/Components/Blazor/Server/src/MonoDebugProxy/BlazorMonoDebugProxyAppBuilderExtensions.cs index 7a1edc2d8c..533cd99399 100644 --- a/src/Components/Blazor/Server/src/MonoDebugProxy/BlazorMonoDebugProxyAppBuilderExtensions.cs +++ b/src/Components/Blazor/Server/src/MonoDebugProxy/BlazorMonoDebugProxyAppBuilderExtensions.cs @@ -3,6 +3,8 @@ using System; using System.Collections.Generic; +using System.Diagnostics; +using System.IO; using System.Linq; using System.Net; using System.Net.Http; @@ -89,19 +91,26 @@ namespace Microsoft.AspNetCore.Builder } catch (Exception ex) { - await context.Response.WriteAsync($@" -

Unable to find debuggable browser tab

-

- Could not get a list of browser tabs from {debuggerTabsListUrl}. - Ensure Chrome is running with debugging enabled. -

-

Resolution

+

Unable to find debuggable browser tab

+

+ Could not get a list of browser tabs from {debuggerTabsListUrl}. + Ensure your browser is running with debugging enabled. +

+

Resolution

+

+

If you are using Google Chrome for your development, follow these instructions:

{GetLaunchChromeInstructions(appRootUrl)} -

... then use that new tab for debugging.

-

Underlying exception:

-
{ex}
-"); +

+

+

If you are using Microsoft Edge (Chromium) for your development, follow these instructions:

+ {GetLaunchEdgeInstructions(appRootUrl)} +

+This should launch a new browser window with debugging enabled..

+

Underlying exception:

+
{ex}
+ "); + return; } @@ -144,20 +153,42 @@ namespace Microsoft.AspNetCore.Builder private static string GetLaunchChromeInstructions(string appRootUrl) { + var profilePath = Path.Combine(Path.GetTempPath(), "blazor-edge-debug"); + if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) { - return $@"

Close all Chrome instances, then press Win+R and enter the following:

-

""%programfiles(x86)%\Google\Chrome\Application\chrome.exe"" --remote-debugging-port=9222 {appRootUrl}

"; + return $@"

Press Win+R and enter the following:

+

chrome --remote-debugging-port=9222 --user-data-dir=""{profilePath}"" {appRootUrl}

"; } else if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { - return $@"

Close all Chrome instances, then in a terminal window execute the following:

-

google-chrome --remote-debugging-port=9222 {appRootUrl}

"; + return $@"

In a terminal window execute the following:

+

google-chrome --remote-debugging-port=9222 --user-data-dir={profilePath} {appRootUrl}

"; } else if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX)) { - return $@"

Close all Chrome instances, then in a terminal window execute the following:

-

open /Applications/Google\ Chrome.app --args --remote-debugging-port=9222 {appRootUrl}

"; + return $@"

Execute the following:

+

open /Applications/Google\ Chrome.app --args --remote-debugging-port=9222 --user-data-dir={profilePath} {appRootUrl}

"; + } + else + { + throw new InvalidOperationException("Unknown OS platform"); + } + } + + private static string GetLaunchEdgeInstructions(string appRootUrl) + { + var profilePath = Path.Combine(Path.GetTempPath(), "blazor-chrome-debug"); + + if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) + { + return $@"

Press Win+R and enter the following:

+

msedge --remote-debugging-port=9222 --user-data-dir=""{profilePath}"" {appRootUrl}

"; + } + else if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX)) + { + return $@"

In a terminal window execute the following:

+

open /Applications/Microsoft\ Edge\ Dev.app --args --remote-debugging-port=9222 --user-data-dir={profilePath} {appRootUrl}

"; } else { diff --git a/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/Shared/SurveyPrompt.razor b/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/Shared/SurveyPrompt.razor index 168aafe542..2b7b716c20 100644 --- a/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/Shared/SurveyPrompt.razor +++ b/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/Shared/SurveyPrompt.razor @@ -4,7 +4,7 @@ Please take our - brief survey + brief survey and tell us what you think. diff --git a/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/wwwroot/css/site.css b/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/wwwroot/css/site.css index 22f9ecb710..4e4425c9b3 100644 --- a/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/wwwroot/css/site.css +++ b/src/Components/Blazor/Templates/src/content/BlazorWasm-CSharp/Client/wwwroot/css/site.css @@ -4,6 +4,16 @@ html, body { font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; } +a, .btn-link { + color: #0366d6; +} + +.btn-primary { + color: #fff; + background-color: #1b6ec2; + border-color: #1861ac; +} + app { position: relative; display: flex; @@ -21,10 +31,21 @@ app { } .main .top-row { - background-color: #e6e6e6; + background-color: #f7f7f7; border-bottom: 1px solid #d6d5d5; + justify-content: flex-end; } + .main .top-row > a, .main .top-row .btn-link { + white-space: nowrap; + margin-left: 1.5rem; + } + +.main .top-row a:first-child { + overflow: hidden; + text-overflow: ellipsis; +} + .sidebar { background-image: linear-gradient(180deg, rgb(5, 39, 103) 0%, #3a0647 70%); } @@ -44,38 +65,38 @@ app { top: -2px; } -.nav-item { - font-size: 0.9rem; - padding-bottom: 0.5rem; -} - - .nav-item:first-of-type { - padding-top: 1rem; + .sidebar .nav-item { + font-size: 0.9rem; + padding-bottom: 0.5rem; } - .nav-item:last-of-type { - padding-bottom: 1rem; - } - - .nav-item a { - color: #d7d7d7; - border-radius: 4px; - height: 3rem; - display: flex; - align-items: center; - line-height: 3rem; - } - - .nav-item a.active { - background-color: rgba(255,255,255,0.25); - color: white; + .sidebar .nav-item:first-of-type { + padding-top: 1rem; } - .nav-item a:hover { - background-color: rgba(255,255,255,0.1); - color: white; + .sidebar .nav-item:last-of-type { + padding-bottom: 1rem; } + .sidebar .nav-item a { + color: #d7d7d7; + border-radius: 4px; + height: 3rem; + display: flex; + align-items: center; + line-height: 3rem; + } + + .sidebar .nav-item a.active { + background-color: rgba(255,255,255,0.25); + color: white; + } + + .sidebar .nav-item a:hover { + background-color: rgba(255,255,255,0.1); + color: white; + } + .content { padding-top: 1.1rem; } @@ -116,9 +137,17 @@ app { } @media (max-width: 767.98px) { - .main .top-row { + .main .top-row:not(.auth) { display: none; } + + .main .top-row.auth { + justify-content: space-between; + } + + .main .top-row a, .main .top-row .btn-link { + margin-left: 0; + } } @media (min-width: 768px) { diff --git a/src/Components/Blazor/Validation/src/ComparePropertyAttribute.cs b/src/Components/Blazor/Validation/src/ComparePropertyAttribute.cs new file mode 100644 index 0000000000..3f74ce647f --- /dev/null +++ b/src/Components/Blazor/Validation/src/ComparePropertyAttribute.cs @@ -0,0 +1,34 @@ +// 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. + +namespace System.ComponentModel.DataAnnotations +{ + /// + /// A that compares two properties + /// + [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] + public sealed class ComparePropertyAttribute : CompareAttribute + { + /// + /// Initializes a new instance of . + /// + /// The property to compare with the current property. + public ComparePropertyAttribute(string otherProperty) + : base(otherProperty) + { + } + + /// + protected override ValidationResult IsValid(object value, ValidationContext validationContext) + { + var validationResult = base.IsValid(value, validationContext); + if (validationResult == ValidationResult.Success) + { + return validationResult; + } + + return new ValidationResult(validationResult.ErrorMessage, new[] { validationContext.MemberName }); + } + } +} + diff --git a/src/Components/Blazor/Validation/src/Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.csproj b/src/Components/Blazor/Validation/src/Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.csproj new file mode 100644 index 0000000000..a166d5f1f3 --- /dev/null +++ b/src/Components/Blazor/Validation/src/Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.csproj @@ -0,0 +1,18 @@ + + + + netstandard2.0 + Provides experimental support for validation using DataAnnotations. + true + false + + + + + + + + + + + diff --git a/src/Components/Blazor/Validation/src/ObjectGraphDataAnnotationsValidator.cs b/src/Components/Blazor/Validation/src/ObjectGraphDataAnnotationsValidator.cs new file mode 100644 index 0000000000..df1971e0a2 --- /dev/null +++ b/src/Components/Blazor/Validation/src/ObjectGraphDataAnnotationsValidator.cs @@ -0,0 +1,125 @@ +// 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.Collections.Generic; +using System.ComponentModel.DataAnnotations; +using System.Linq; + +namespace Microsoft.AspNetCore.Components.Forms +{ + public class ObjectGraphDataAnnotationsValidator : ComponentBase + { + private static readonly object ValidationContextValidatorKey = new object(); + private static readonly object ValidatedObjectsKey = new object(); + private ValidationMessageStore _validationMessageStore; + + [CascadingParameter] + internal EditContext EditContext { get; set; } + + protected override void OnInitialized() + { + _validationMessageStore = new ValidationMessageStore(EditContext); + + // Perform object-level validation (starting from the root model) on request + EditContext.OnValidationRequested += (sender, eventArgs) => + { + _validationMessageStore.Clear(); + ValidateObject(EditContext.Model, new HashSet()); + EditContext.NotifyValidationStateChanged(); + }; + + // Perform per-field validation on each field edit + EditContext.OnFieldChanged += (sender, eventArgs) => + ValidateField(EditContext, _validationMessageStore, eventArgs.FieldIdentifier); + } + + internal void ValidateObject(object value, HashSet visited) + { + if (value is null) + { + return; + } + + if (!visited.Add(value)) + { + // Already visited this object. + return; + } + + if (value is IEnumerable enumerable) + { + var index = 0; + foreach (var item in enumerable) + { + ValidateObject(item, visited); + index++; + } + + return; + } + + var validationResults = new List(); + ValidateObject(value, visited, validationResults); + + // Transfer results to the ValidationMessageStore + foreach (var validationResult in validationResults) + { + if (!validationResult.MemberNames.Any()) + { + _validationMessageStore.Add(new FieldIdentifier(value, string.Empty), validationResult.ErrorMessage); + continue; + } + + foreach (var memberName in validationResult.MemberNames) + { + var fieldIdentifier = new FieldIdentifier(value, memberName); + _validationMessageStore.Add(fieldIdentifier, validationResult.ErrorMessage); + } + } + } + + private void ValidateObject(object value, HashSet visited, List validationResults) + { + var validationContext = new ValidationContext(value); + validationContext.Items.Add(ValidationContextValidatorKey, this); + validationContext.Items.Add(ValidatedObjectsKey, visited); + Validator.TryValidateObject(value, validationContext, validationResults, validateAllProperties: true); + } + + internal static bool TryValidateRecursive(object value, ValidationContext validationContext) + { + if (validationContext.Items.TryGetValue(ValidationContextValidatorKey, out var result) && result is ObjectGraphDataAnnotationsValidator validator) + { + var visited = (HashSet)validationContext.Items[ValidatedObjectsKey]; + validator.ValidateObject(value, visited); + + return true; + } + + return false; + } + + private static void ValidateField(EditContext editContext, ValidationMessageStore messages, in FieldIdentifier fieldIdentifier) + { + // DataAnnotations only validates public properties, so that's all we'll look for + var propertyInfo = fieldIdentifier.Model.GetType().GetProperty(fieldIdentifier.FieldName); + if (propertyInfo != null) + { + var propertyValue = propertyInfo.GetValue(fieldIdentifier.Model); + var validationContext = new ValidationContext(fieldIdentifier.Model) + { + MemberName = propertyInfo.Name + }; + var results = new List(); + + Validator.TryValidateProperty(propertyValue, validationContext, results); + messages.Clear(fieldIdentifier); + messages.Add(fieldIdentifier, results.Select(result => result.ErrorMessage)); + + // We have to notify even if there were no messages before and are still no messages now, + // because the "state" that changed might be the completion of some async validation task + editContext.NotifyValidationStateChanged(); + } + } + } +} diff --git a/src/Components/Blazor/Validation/src/ValidateComplexTypeAttribute.cs b/src/Components/Blazor/Validation/src/ValidateComplexTypeAttribute.cs new file mode 100644 index 0000000000..4769d84767 --- /dev/null +++ b/src/Components/Blazor/Validation/src/ValidateComplexTypeAttribute.cs @@ -0,0 +1,30 @@ +// 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.Components.Forms; + +namespace System.ComponentModel.DataAnnotations +{ + /// + /// A that indicates that the property is a complex or collection type that further needs to be validated. + /// + /// By default does not recurse in to complex property types during validation. + /// When used in conjunction with , this property allows the validation system to validate + /// complex or collection type properties. + /// + /// + [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] + public sealed class ValidateComplexTypeAttribute : ValidationAttribute + { + /// + protected override ValidationResult IsValid(object value, ValidationContext validationContext) + { + if (!ObjectGraphDataAnnotationsValidator.TryValidateRecursive(value, validationContext)) + { + throw new InvalidOperationException($"{nameof(ValidateComplexTypeAttribute)} can only used with {nameof(ObjectGraphDataAnnotationsValidator)}."); + } + + return ValidationResult.Success; + } + } +} diff --git a/src/Components/Blazor/Validation/test/Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.Tests.csproj b/src/Components/Blazor/Validation/test/Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.Tests.csproj new file mode 100644 index 0000000000..02e8561536 --- /dev/null +++ b/src/Components/Blazor/Validation/test/Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.Tests.csproj @@ -0,0 +1,11 @@ + + + + $(DefaultNetCoreTargetFramework) + + + + + + + diff --git a/src/Components/Blazor/Validation/test/ObjectGraphDataAnnotationsValidatorTest.cs b/src/Components/Blazor/Validation/test/ObjectGraphDataAnnotationsValidatorTest.cs new file mode 100644 index 0000000000..6703eb35d5 --- /dev/null +++ b/src/Components/Blazor/Validation/test/ObjectGraphDataAnnotationsValidatorTest.cs @@ -0,0 +1,540 @@ +// 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.Collections.Generic; +using System.ComponentModel.DataAnnotations; +using System.Linq; +using Microsoft.AspNetCore.Components.Forms; +using Xunit; + +namespace Microsoft.AspNetCore.Components +{ + public class ObjectGraphDataAnnotationsValidatorTest + { + public class SimpleModel + { + [Required] + public string Name { get; set; } + + [Range(1, 16)] + public int Age { get; set; } + } + + [Fact] + public void ValidateObject_SimpleObject() + { + var model = new SimpleModel + { + Age = 23, + }; + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(() => model.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.Age); + Assert.Single(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateObject_SimpleObject_AllValid() + { + var model = new SimpleModel { Name = "Test", Age = 5 }; + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(() => model.Name); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => model.Age); + Assert.Empty(messages); + + Assert.Empty(editContext.GetValidationMessages()); + } + + public class ModelWithComplexProperty + { + [Required] + public string Property1 { get; set; } + + [ValidateComplexType] + public SimpleModel SimpleModel { get; set; } + } + + [Fact] + public void ValidateObject_NullComplexProperty() + { + var model = new ModelWithComplexProperty(); + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(() => model.Property1); + Assert.Single(messages); + + Assert.Single(editContext.GetValidationMessages()); + } + + [Fact] + public void ValidateObject_ModelWithComplexProperties() + { + var model = new ModelWithComplexProperty { SimpleModel = new SimpleModel() }; + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(() => model.Property1); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.SimpleModel); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => model.SimpleModel.Age); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.SimpleModel.Name); + Assert.Single(messages); + + Assert.Equal(3, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateObject_ModelWithComplexProperties_SomeValid() + { + var model = new ModelWithComplexProperty + { + Property1 = "Value", + SimpleModel = new SimpleModel { Name = "Some Value" }, + }; + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(() => model.Property1); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => model.SimpleModel); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => model.SimpleModel.Age); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.SimpleModel.Name); + Assert.Empty(messages); + + Assert.Single(editContext.GetValidationMessages()); + } + + public class TestValidatableObject : IValidatableObject + { + [Required] + public string Name { get; set; } + + public IEnumerable Validate(ValidationContext validationContext) + { + yield return new ValidationResult("Custom validation error"); + } + } + + public class ModelWithValidatableComplexProperty + { + [Required] + public string Property1 { get; set; } + + [ValidateComplexType] + public TestValidatableObject Property2 { get; set; } = new TestValidatableObject(); + } + + [Fact] + public void ValidateObject_ValidatableComplexProperty() + { + var model = new ModelWithValidatableComplexProperty(); + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(() => model.Property1); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.Property2); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => model.Property2.Name); + Assert.Single(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateObject_ValidatableComplexProperty_ValidatesIValidatableProperty() + { + var model = new ModelWithValidatableComplexProperty + { + Property2 = new TestValidatableObject { Name = "test" }, + }; + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(() => model.Property1); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(new FieldIdentifier(model.Property2, string.Empty)); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.Property2.Name); + Assert.Empty(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateObject_ModelIsIValidatable_PropertyHasError() + { + var model = new TestValidatableObject(); + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(new FieldIdentifier(model, string.Empty)); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => model.Name); + Assert.Single(messages); + + Assert.Single(editContext.GetValidationMessages()); + } + + [Fact] + public void ValidateObject_ModelIsIValidatable_ModelHasError() + { + var model = new TestValidatableObject { Name = "test" }; + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(new FieldIdentifier(model, string.Empty)); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.Name); + Assert.Empty(messages); + + Assert.Single(editContext.GetValidationMessages()); + } + + [Fact] + public void ValidateObject_CollectionModel() + { + var model = new List + { + new SimpleModel(), + new SimpleModel { Name = "test", }, + }; + + var editContext = Validate(model); + + var item = model[0]; + var messages = editContext.GetValidationMessages(new FieldIdentifier(model, "0")); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => item.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => item.Age); + Assert.Single(messages); + + item = model[1]; + messages = editContext.GetValidationMessages(new FieldIdentifier(model, "1")); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => item.Name); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => item.Age); + Assert.Single(messages); + + Assert.Equal(3, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateObject_CollectionValidatableModel() + { + var model = new List + { + new TestValidatableObject(), + new TestValidatableObject { Name = "test", }, + }; + + var editContext = Validate(model); + + var item = model[0]; + var messages = editContext.GetValidationMessages(() => item.Name); + Assert.Single(messages); + + item = model[1]; + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => item.Name); + Assert.Empty(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + } + + private class Level1Validation + { + [ValidateComplexType] + public Level2Validation Level2 { get; set; } + } + + public class Level2Validation + { + [ValidateComplexType] + public SimpleModel Level3 { get; set; } + } + + [Fact] + public void ValidateObject_ManyLevels() + { + var model = new Level1Validation + { + Level2 = new Level2Validation + { + Level3 = new SimpleModel + { + Age = 47, + } + } + }; + + var editContext = Validate(model); + var level3 = model.Level2.Level3; + + var messages = editContext.GetValidationMessages(() => level3.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => level3.Age); + Assert.Single(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + } + + private class Person + { + [Required] + public string Name { get; set; } + + [ValidateComplexType] + public Person Related { get; set; } + } + + [Fact] + public void ValidateObject_RecursiveRelation() + { + var model = new Person { Related = new Person() }; + model.Related.Related = model; + + var editContext = Validate(model); + + var messages = editContext.GetValidationMessages(() => model.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => model.Related.Name); + Assert.Single(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateObject_RecursiveRelation_OverManySteps() + { + var person1 = new Person(); + var person2 = new Person { Name = "Valid name" }; + var person3 = new Person(); + var person4 = new Person(); + + person1.Related = person2; + person2.Related = person3; + person3.Related = person4; + person4.Related = person1; + + var editContext = Validate(person1); + + var messages = editContext.GetValidationMessages(() => person1.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => person2.Name); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => person3.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => person4.Name); + Assert.Single(messages); + + Assert.Equal(3, editContext.GetValidationMessages().Count()); + } + + private class Node + { + [Required] + public string Id { get; set; } + + [ValidateComplexType] + public List Related { get; set; } = new List(); + } + + [Fact] + public void ValidateObject_RecursiveRelation_ViaCollection() + { + var node1 = new Node(); + var node2 = new Node { Id = "Valid Id" }; + var node3 = new Node(); + node1.Related.Add(node2); + node2.Related.Add(node3); + node3.Related.Add(node1); + + var editContext = Validate(node1); + + var messages = editContext.GetValidationMessages(() => node1.Id); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => node2.Id); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => node3.Id); + Assert.Single(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateObject_RecursiveRelation_InCollection() + { + var person1 = new Person(); + var person2 = new Person { Name = "Valid name" }; + var person3 = new Person(); + var person4 = new Person(); + + person1.Related = person2; + person2.Related = person3; + person3.Related = person4; + person4.Related = person1; + + var editContext = Validate(person1); + + var messages = editContext.GetValidationMessages(() => person1.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => person2.Name); + Assert.Empty(messages); + + messages = editContext.GetValidationMessages(() => person3.Name); + Assert.Single(messages); + + messages = editContext.GetValidationMessages(() => person4.Name); + Assert.Single(messages); + + Assert.Equal(3, editContext.GetValidationMessages().Count()); + } + + [Fact] + public void ValidateField_PropertyValid() + { + var model = new SimpleModel { Age = 1 }; + var fieldIdentifier = FieldIdentifier.Create(() => model.Age); + + var editContext = ValidateField(model, fieldIdentifier); + var messages = editContext.GetValidationMessages(fieldIdentifier); + Assert.Empty(messages); + + Assert.Empty(editContext.GetValidationMessages()); + } + + [Fact] + public void ValidateField_PropertyInvalid() + { + var model = new SimpleModel { Age = 42 }; + var fieldIdentifier = FieldIdentifier.Create(() => model.Age); + + var editContext = ValidateField(model, fieldIdentifier); + var messages = editContext.GetValidationMessages(fieldIdentifier); + Assert.Single(messages); + + Assert.Single(editContext.GetValidationMessages()); + } + + [Fact] + public void ValidateField_AfterSubmitValidation() + { + var model = new SimpleModel { Age = 42 }; + var fieldIdentifier = FieldIdentifier.Create(() => model.Age); + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(fieldIdentifier); + Assert.Single(messages); + + Assert.Equal(2, editContext.GetValidationMessages().Count()); + + model.Age = 4; + + editContext.NotifyFieldChanged(fieldIdentifier); + messages = editContext.GetValidationMessages(fieldIdentifier); + Assert.Empty(messages); + + Assert.Single(editContext.GetValidationMessages()); + } + + [Fact] + public void ValidateField_ModelWithComplexProperty() + { + var model = new ModelWithComplexProperty + { + SimpleModel = new SimpleModel { Age = 1 }, + }; + var fieldIdentifier = FieldIdentifier.Create(() => model.SimpleModel.Name); + + var editContext = ValidateField(model, fieldIdentifier); + var messages = editContext.GetValidationMessages(fieldIdentifier); + Assert.Single(messages); + + Assert.Single(editContext.GetValidationMessages()); + } + + [Fact] + public void ValidateField_ModelWithComplexProperty_AfterSubmitValidation() + { + var model = new ModelWithComplexProperty + { + Property1 = "test", + SimpleModel = new SimpleModel { Age = 29, Name = "Test" }, + }; + var fieldIdentifier = FieldIdentifier.Create(() => model.SimpleModel.Age); + + var editContext = Validate(model); + var messages = editContext.GetValidationMessages(fieldIdentifier); + Assert.Single(messages); + + model.SimpleModel.Age = 9; + editContext.NotifyFieldChanged(fieldIdentifier); + + messages = editContext.GetValidationMessages(fieldIdentifier); + Assert.Empty(messages); + Assert.Empty(editContext.GetValidationMessages()); + } + + private static EditContext Validate(object model) + { + var editContext = new EditContext(model); + var validator = new TestObjectGraphDataAnnotationsValidator { EditContext = editContext, }; + validator.OnInitialized(); + + editContext.Validate(); + + return editContext; + } + + private static EditContext ValidateField(object model, in FieldIdentifier field) + { + var editContext = new EditContext(model); + var validator = new TestObjectGraphDataAnnotationsValidator { EditContext = editContext, }; + validator.OnInitialized(); + + editContext.NotifyFieldChanged(field); + + return editContext; + } + + private class TestObjectGraphDataAnnotationsValidator : ObjectGraphDataAnnotationsValidator + { + public new void OnInitialized() => base.OnInitialized(); + } + } +} diff --git a/src/Components/Blazor/testassets/StandaloneApp/wwwroot/css/site.css b/src/Components/Blazor/testassets/StandaloneApp/wwwroot/css/site.css index fa2c7f19b7..c15c2e1556 100644 --- a/src/Components/Blazor/testassets/StandaloneApp/wwwroot/css/site.css +++ b/src/Components/Blazor/testassets/StandaloneApp/wwwroot/css/site.css @@ -1,9 +1,19 @@ -@import url('open-iconic/font/css/open-iconic-bootstrap.min.css'); +@import url('open-iconic/font/css/open-iconic-bootstrap.min.css'); html, body { font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; } +a, .btn-link { + color: #0366d6; +} + +.btn-primary { + color: #fff; + background-color: #1b6ec2; + border-color: #1861ac; +} + app { position: relative; display: flex; @@ -21,10 +31,21 @@ app { } .main .top-row { - background-color: #e6e6e6; + background-color: #f7f7f7; border-bottom: 1px solid #d6d5d5; + justify-content: flex-end; } + .main .top-row > a, .main .top-row .btn-link { + white-space: nowrap; + margin-left: 1.5rem; + } + +.main .top-row a:first-child { + overflow: hidden; + text-overflow: ellipsis; +} + .sidebar { background-image: linear-gradient(180deg, rgb(5, 39, 103) 0%, #3a0647 70%); } @@ -44,38 +65,38 @@ app { top: -2px; } -.nav-item { - font-size: 0.9rem; - padding-bottom: 0.5rem; -} - - .nav-item:first-of-type { - padding-top: 1rem; + .sidebar .nav-item { + font-size: 0.9rem; + padding-bottom: 0.5rem; } - .nav-item:last-of-type { - padding-bottom: 1rem; - } - - .nav-item a { - color: #d7d7d7; - border-radius: 4px; - height: 3rem; - display: flex; - align-items: center; - line-height: 3rem; - } - - .nav-item a.active { - background-color: rgba(255,255,255,0.25); - color: white; + .sidebar .nav-item:first-of-type { + padding-top: 1rem; } - .nav-item a:hover { - background-color: rgba(255,255,255,0.1); - color: white; + .sidebar .nav-item:last-of-type { + padding-bottom: 1rem; } + .sidebar .nav-item a { + color: #d7d7d7; + border-radius: 4px; + height: 3rem; + display: flex; + align-items: center; + line-height: 3rem; + } + + .sidebar .nav-item a.active { + background-color: rgba(255,255,255,0.25); + color: white; + } + + .sidebar .nav-item a:hover { + background-color: rgba(255,255,255,0.1); + color: white; + } + .content { padding-top: 1.1rem; } @@ -96,10 +117,37 @@ app { color: red; } +#blazor-error-ui { + background: lightyellow; + bottom: 0; + box-shadow: 0 -1px 2px rgba(0, 0, 0, 0.2); + display: none; + left: 0; + padding: 0.6rem 1.25rem 0.7rem 1.25rem; + position: fixed; + width: 100%; + z-index: 1000; +} + +#blazor-error-ui .dismiss { + cursor: pointer; + position: absolute; + right: 0.75rem; + top: 0.5rem; +} + @media (max-width: 767.98px) { - .main .top-row { + .main .top-row:not(.auth) { display: none; } + + .main .top-row.auth { + justify-content: space-between; + } + + .main .top-row a, .main .top-row .btn-link { + margin-left: 0; + } } @media (min-width: 768px) { diff --git a/src/Components/Components.sln b/src/Components/Components.sln index 046fc0b7ca..ba0b2476ff 100644 --- a/src/Components/Components.sln +++ b/src/Components/Components.sln @@ -240,6 +240,12 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ignitor", "Ignitor\src\Igni EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ignitor.Test", "Ignitor\test\Ignitor.Test.csproj", "{F31E8118-014E-4CCE-8A48-5282F7B9BB3E}" EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Validation", "Validation", "{FD9BD646-9D50-42ED-A3E1-90558BA0C6B2}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Blazor.DataAnnotations.Validation", "Blazor\Validation\src\Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.csproj", "{B70F90C7-2696-4050-B24E-BF0308F4E059}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.Tests", "Blazor\Validation\test\Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.Tests.csproj", "{A5617A9D-C71E-44DE-936C-27611EB40A02}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -1486,6 +1492,30 @@ Global {F31E8118-014E-4CCE-8A48-5282F7B9BB3E}.Release|x64.Build.0 = Release|Any CPU {F31E8118-014E-4CCE-8A48-5282F7B9BB3E}.Release|x86.ActiveCfg = Release|Any CPU {F31E8118-014E-4CCE-8A48-5282F7B9BB3E}.Release|x86.Build.0 = Release|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Debug|Any CPU.Build.0 = Debug|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Debug|x64.ActiveCfg = Debug|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Debug|x64.Build.0 = Debug|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Debug|x86.ActiveCfg = Debug|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Debug|x86.Build.0 = Debug|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Release|Any CPU.ActiveCfg = Release|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Release|Any CPU.Build.0 = Release|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Release|x64.ActiveCfg = Release|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Release|x64.Build.0 = Release|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Release|x86.ActiveCfg = Release|Any CPU + {B70F90C7-2696-4050-B24E-BF0308F4E059}.Release|x86.Build.0 = Release|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Debug|Any CPU.Build.0 = Debug|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Debug|x64.ActiveCfg = Debug|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Debug|x64.Build.0 = Debug|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Debug|x86.ActiveCfg = Debug|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Debug|x86.Build.0 = Debug|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Release|Any CPU.ActiveCfg = Release|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Release|Any CPU.Build.0 = Release|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Release|x64.ActiveCfg = Release|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Release|x64.Build.0 = Release|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Release|x86.ActiveCfg = Release|Any CPU + {A5617A9D-C71E-44DE-936C-27611EB40A02}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -1596,6 +1626,9 @@ Global {BBF37AF9-8290-4B70-8BA8-0F6017B3B620} = {46E4300C-5726-4108-B9A2-18BB94EB26ED} {CD0EF85C-4187-4515-A355-E5A0D4485F40} = {BDE2397D-C53A-4783-8B3A-1F54F48A6926} {F31E8118-014E-4CCE-8A48-5282F7B9BB3E} = {BDE2397D-C53A-4783-8B3A-1F54F48A6926} + {FD9BD646-9D50-42ED-A3E1-90558BA0C6B2} = {7260DED9-22A9-4E9D-92F4-5E8A4404DEAF} + {B70F90C7-2696-4050-B24E-BF0308F4E059} = {7260DED9-22A9-4E9D-92F4-5E8A4404DEAF} + {A5617A9D-C71E-44DE-936C-27611EB40A02} = {7260DED9-22A9-4E9D-92F4-5E8A4404DEAF} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {CC3C47E1-AD1A-4619-9CD3-E08A0148E5CE} diff --git a/src/Components/Components/ref/Microsoft.AspNetCore.Components.netcoreapp.cs b/src/Components/Components/ref/Microsoft.AspNetCore.Components.netcoreapp.cs index 72adf28aa7..c4a48435b4 100644 --- a/src/Components/Components/ref/Microsoft.AspNetCore.Components.netcoreapp.cs +++ b/src/Components/Components/ref/Microsoft.AspNetCore.Components.netcoreapp.cs @@ -207,7 +207,10 @@ namespace Microsoft.AspNetCore.Components public sealed partial class EventHandlerAttribute : System.Attribute { public EventHandlerAttribute(string attributeName, System.Type eventArgsType) { } + public EventHandlerAttribute(string attributeName, System.Type eventArgsType, bool enableStopPropagation, bool enablePreventDefault) { } public string AttributeName { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } + public bool EnablePreventDefault { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } + public bool EnableStopPropagation { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } public System.Type EventArgsType { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } } public partial interface IComponent diff --git a/src/Components/Components/ref/Microsoft.AspNetCore.Components.netstandard2.0.cs b/src/Components/Components/ref/Microsoft.AspNetCore.Components.netstandard2.0.cs index 72adf28aa7..c4a48435b4 100644 --- a/src/Components/Components/ref/Microsoft.AspNetCore.Components.netstandard2.0.cs +++ b/src/Components/Components/ref/Microsoft.AspNetCore.Components.netstandard2.0.cs @@ -207,7 +207,10 @@ namespace Microsoft.AspNetCore.Components public sealed partial class EventHandlerAttribute : System.Attribute { public EventHandlerAttribute(string attributeName, System.Type eventArgsType) { } + public EventHandlerAttribute(string attributeName, System.Type eventArgsType, bool enableStopPropagation, bool enablePreventDefault) { } public string AttributeName { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } + public bool EnablePreventDefault { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } + public bool EnableStopPropagation { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } public System.Type EventArgsType { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } } } public partial interface IComponent diff --git a/src/Components/Components/src/EventHandlerAttribute.cs b/src/Components/Components/src/EventHandlerAttribute.cs index 767b3c5b2a..67307fb9ef 100644 --- a/src/Components/Components/src/EventHandlerAttribute.cs +++ b/src/Components/Components/src/EventHandlerAttribute.cs @@ -16,7 +16,18 @@ namespace Microsoft.AspNetCore.Components /// /// /// - public EventHandlerAttribute(string attributeName, Type eventArgsType) + public EventHandlerAttribute(string attributeName, Type eventArgsType) : this(attributeName, eventArgsType, false, false) + { + } + + /// + /// Constructs an instance of . + /// + /// + /// + /// + /// + public EventHandlerAttribute(string attributeName, Type eventArgsType, bool enableStopPropagation, bool enablePreventDefault) { if (attributeName == null) { @@ -30,6 +41,8 @@ namespace Microsoft.AspNetCore.Components AttributeName = attributeName; EventArgsType = eventArgsType; + EnableStopPropagation = enableStopPropagation; + EnablePreventDefault = enablePreventDefault; } /// @@ -41,5 +54,15 @@ namespace Microsoft.AspNetCore.Components /// Gets the event argument type. /// public Type EventArgsType { get; } + + /// + /// Gets the event's ability to stop propagation. + /// + public bool EnableStopPropagation { get; } + + /// + /// Gets the event's ability to prevent default event flow. + /// + public bool EnablePreventDefault { get; } } } diff --git a/src/Components/ComponentsNoDeps.slnf b/src/Components/ComponentsNoDeps.slnf index ce01e6468f..09f6a0859f 100644 --- a/src/Components/ComponentsNoDeps.slnf +++ b/src/Components/ComponentsNoDeps.slnf @@ -15,6 +15,8 @@ "Blazor\\Http\\test\\Microsoft.AspNetCore.Blazor.HttpClient.Tests.csproj", "Blazor\\Server\\src\\Microsoft.AspNetCore.Blazor.Server.csproj", "Blazor\\Templates\\src\\Microsoft.AspNetCore.Blazor.Templates.csproj", + "Blazor\\Validation\\src\\Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.csproj", + "Blazor\\Validation\\test\\Microsoft.AspNetCore.Blazor.DataAnnotations.Validation.Tests.csproj", "Blazor\\testassets\\HostedInAspNet.Client\\HostedInAspNet.Client.csproj", "Blazor\\testassets\\HostedInAspNet.Server\\HostedInAspNet.Server.csproj", "Blazor\\testassets\\Microsoft.AspNetCore.Blazor.E2EPerformance\\Microsoft.AspNetCore.Blazor.E2EPerformance.csproj", diff --git a/src/Components/Forms/src/EditContextDataAnnotationsExtensions.cs b/src/Components/Forms/src/EditContextDataAnnotationsExtensions.cs index 9fce473a41..e7f9d5f155 100644 --- a/src/Components/Forms/src/EditContextDataAnnotationsExtensions.cs +++ b/src/Components/Forms/src/EditContextDataAnnotationsExtensions.cs @@ -52,6 +52,12 @@ namespace Microsoft.AspNetCore.Components.Forms messages.Clear(); foreach (var validationResult in validationResults) { + if (!validationResult.MemberNames.Any()) + { + messages.Add(new FieldIdentifier(editContext.Model, fieldName: string.Empty), validationResult.ErrorMessage); + continue; + } + foreach (var memberName in validationResult.MemberNames) { messages.Add(editContext.Field(memberName), validationResult.ErrorMessage); diff --git a/src/Components/Ignitor/src/BlazorClient.cs b/src/Components/Ignitor/src/BlazorClient.cs index df93faa3b3..cddc48e094 100644 --- a/src/Components/Ignitor/src/BlazorClient.cs +++ b/src/Components/Ignitor/src/BlazorClient.cs @@ -13,17 +13,21 @@ using Microsoft.AspNetCore.SignalR.Protocol; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.DependencyInjection.Extensions; using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +#nullable enable namespace Ignitor { public class BlazorClient : IAsyncDisposable { private const string MarkerPattern = ".*?.*?"; + private HubConnection? _hubConnection; public BlazorClient() { CancellationTokenSource = new CancellationTokenSource(); - TaskCompletionSource = new TaskCompletionSource(); + CancellationToken = CancellationTokenSource.Token; + TaskCompletionSource = new TaskCompletionSource(); CancellationTokenSource.Token.Register(() => { @@ -31,7 +35,7 @@ namespace Ignitor }); } - public TimeSpan? DefaultConnectionTimeout { get; set; } = TimeSpan.FromSeconds(10); + public TimeSpan? DefaultConnectionTimeout { get; set; } = TimeSpan.FromSeconds(20); public TimeSpan? DefaultOperationTimeout { get; set; } = TimeSpan.FromMilliseconds(500); /// @@ -44,104 +48,103 @@ namespace Ignitor /// Gets the collections of operation results that are captured when /// is true. /// - public Operations Operations { get; private set; } + public Operations Operations { get; } = new Operations(); - public Func FormatError { get; set; } + public Func? FormatError { get; set; } private CancellationTokenSource CancellationTokenSource { get; } - private CancellationToken CancellationToken => CancellationTokenSource.Token; + private CancellationToken CancellationToken { get; } - private TaskCompletionSource TaskCompletionSource { get; } + private TaskCompletionSource TaskCompletionSource { get; } - private CancellableOperation NextAttachComponentReceived { get; set; } + private CancellableOperation? NextAttachComponentReceived { get; set; } - private CancellableOperation NextBatchReceived { get; set; } + private CancellableOperation? NextBatchReceived { get; set; } - private CancellableOperation NextErrorReceived { get; set; } + private CancellableOperation? NextErrorReceived { get; set; } - private CancellableOperation NextDisconnect { get; set; } + private CancellableOperation? NextDisconnect { get; set; } - private CancellableOperation NextJSInteropReceived { get; set; } + private CancellableOperation? NextJSInteropReceived { get; set; } - private CancellableOperation NextDotNetInteropCompletionReceived { get; set; } + private CancellableOperation? NextDotNetInteropCompletionReceived { get; set; } - public ILoggerProvider LoggerProvider { get; set; } + public ILoggerProvider LoggerProvider { get; set; } = NullLoggerProvider.Instance; public bool ConfirmRenderBatch { get; set; } = true; - public event Action JSInterop; + public event Action? JSInterop; - public event Action RenderBatchReceived; + public event Action? RenderBatchReceived; - public event Action DotNetInteropCompletion; + public event Action? DotNetInteropCompletion; - public event Action OnCircuitError; + public event Action? OnCircuitError; - public string CircuitId { get; set; } + public string? CircuitId { get; private set; } - public ElementHive Hive { get; set; } = new ElementHive(); + public ElementHive Hive { get; } = new ElementHive(); public bool ImplicitWait => DefaultOperationTimeout != null; - public HubConnection HubConnection { get; private set; } + public HubConnection HubConnection => _hubConnection ?? throw new InvalidOperationException("HubConnection has not been initialized."); - public Task PrepareForNextBatch(TimeSpan? timeout) + public Task PrepareForNextBatch(TimeSpan? timeout) { if (NextBatchReceived != null && !NextBatchReceived.Disposed) { throw new InvalidOperationException("Invalid state previous task not completed"); } - NextBatchReceived = new CancellableOperation(timeout); - + NextBatchReceived = new CancellableOperation(timeout, CancellationToken); return NextBatchReceived.Completion.Task; } - public Task PrepareForNextJSInterop(TimeSpan? timeout) + public Task PrepareForNextJSInterop(TimeSpan? timeout) { if (NextJSInteropReceived != null && !NextJSInteropReceived.Disposed) { throw new InvalidOperationException("Invalid state previous task not completed"); } - NextJSInteropReceived = new CancellableOperation(timeout); + NextJSInteropReceived = new CancellableOperation(timeout, CancellationToken); return NextJSInteropReceived.Completion.Task; } - public Task PrepareForNextDotNetInterop(TimeSpan? timeout) + public Task PrepareForNextDotNetInterop(TimeSpan? timeout) { if (NextDotNetInteropCompletionReceived != null && !NextDotNetInteropCompletionReceived.Disposed) { throw new InvalidOperationException("Invalid state previous task not completed"); } - NextDotNetInteropCompletionReceived = new CancellableOperation(timeout); + NextDotNetInteropCompletionReceived = new CancellableOperation(timeout, CancellationToken); return NextDotNetInteropCompletionReceived.Completion.Task; } - public Task PrepareForNextCircuitError(TimeSpan? timeout) + public Task PrepareForNextCircuitError(TimeSpan? timeout) { if (NextErrorReceived != null && !NextErrorReceived.Disposed) { throw new InvalidOperationException("Invalid state previous task not completed"); } - NextErrorReceived = new CancellableOperation(timeout); + NextErrorReceived = new CancellableOperation(timeout, CancellationToken); return NextErrorReceived.Completion.Task; } - public Task PrepareForNextDisconnect(TimeSpan? timeout) + public Task PrepareForNextDisconnect(TimeSpan? timeout) { if (NextDisconnect != null && !NextDisconnect.Disposed) { throw new InvalidOperationException("Invalid state previous task not completed"); } - NextDisconnect = new CancellableOperation(timeout); + NextDisconnect = new CancellableOperation(timeout, CancellationToken); return NextDisconnect.Completion.Task; } @@ -172,44 +175,44 @@ namespace Ignitor return ExpectRenderBatch(() => elementNode.SelectAsync(HubConnection, value)); } - public async Task ExpectRenderBatch(Func action, TimeSpan? timeout = null) + public async Task ExpectRenderBatch(Func action, TimeSpan? timeout = null) { var task = WaitForRenderBatch(timeout); await action(); return await task; } - public async Task ExpectJSInterop(Func action, TimeSpan? timeout = null) + public async Task ExpectJSInterop(Func action, TimeSpan? timeout = null) { var task = WaitForJSInterop(timeout); await action(); return await task; } - public async Task ExpectDotNetInterop(Func action, TimeSpan? timeout = null) + public async Task ExpectDotNetInterop(Func action, TimeSpan? timeout = null) { var task = WaitForDotNetInterop(timeout); await action(); return await task; } - public async Task ExpectCircuitError(Func action, TimeSpan? timeout = null) + public async Task ExpectCircuitError(Func action, TimeSpan? timeout = null) { var task = WaitForCircuitError(timeout); await action(); return await task; } - public async Task ExpectDisconnect(Func action, TimeSpan? timeout = null) + public async Task ExpectDisconnect(Func action, TimeSpan? timeout = null) { var task = WaitForDisconnect(timeout); await action(); return await task; } - public async Task<(string error, Exception exception)> ExpectCircuitErrorAndDisconnect(Func action, TimeSpan? timeout = null) + public async Task<(string? error, Exception? exception)> ExpectCircuitErrorAndDisconnect(Func action, TimeSpan? timeout = null) { - string error = null; + string? error = default; // NOTE: timeout is used for each operation individually. var exception = await ExpectDisconnect(async () => @@ -220,7 +223,7 @@ namespace Ignitor return (error, exception); } - private async Task WaitForRenderBatch(TimeSpan? timeout = null) + private async Task WaitForRenderBatch(TimeSpan? timeout = null) { if (ImplicitWait) { @@ -233,7 +236,7 @@ namespace Ignitor { return await PrepareForNextBatch(timeout ?? DefaultOperationTimeout); } - catch (OperationCanceledException) + catch (TimeoutException) when (FormatError != null) { throw FormatError("Timed out while waiting for batch."); } @@ -242,7 +245,7 @@ namespace Ignitor return null; } - private async Task WaitForJSInterop(TimeSpan? timeout = null) + private async Task WaitForJSInterop(TimeSpan? timeout = null) { if (ImplicitWait) { @@ -255,7 +258,7 @@ namespace Ignitor { return await PrepareForNextJSInterop(timeout ?? DefaultOperationTimeout); } - catch (OperationCanceledException) + catch (TimeoutException) when (FormatError != null) { throw FormatError("Timed out while waiting for JS Interop."); } @@ -264,7 +267,7 @@ namespace Ignitor return null; } - private async Task WaitForDotNetInterop(TimeSpan? timeout = null) + private async Task WaitForDotNetInterop(TimeSpan? timeout = null) { if (ImplicitWait) { @@ -277,7 +280,7 @@ namespace Ignitor { return await PrepareForNextDotNetInterop(timeout ?? DefaultOperationTimeout); } - catch (OperationCanceledException) + catch (TimeoutException) when (FormatError != null) { throw FormatError("Timed out while waiting for .NET interop."); } @@ -286,7 +289,7 @@ namespace Ignitor return null; } - private async Task WaitForCircuitError(TimeSpan? timeout = null) + private async Task WaitForCircuitError(TimeSpan? timeout = null) { if (ImplicitWait) { @@ -299,7 +302,7 @@ namespace Ignitor { return await PrepareForNextCircuitError(timeout ?? DefaultOperationTimeout); } - catch (OperationCanceledException) + catch (TimeoutException) when (FormatError != null) { throw FormatError("Timed out while waiting for circuit error."); } @@ -308,7 +311,7 @@ namespace Ignitor return null; } - private async Task WaitForDisconnect(TimeSpan? timeout = null) + private async Task WaitForDisconnect(TimeSpan? timeout = null) { if (ImplicitWait) { @@ -321,7 +324,7 @@ namespace Ignitor { return await PrepareForNextDisconnect(timeout ?? DefaultOperationTimeout); } - catch (OperationCanceledException) + catch (TimeoutException) when (FormatError != null) { throw FormatError("Timed out while waiting for disconnect."); } @@ -344,7 +347,7 @@ namespace Ignitor } }); - HubConnection = builder.Build(); + _hubConnection = builder.Build(); await HubConnection.StartAsync(CancellationToken); HubConnection.On("JS.AttachComponent", OnAttachComponent); @@ -354,11 +357,6 @@ namespace Ignitor HubConnection.On("JS.Error", OnError); HubConnection.Closed += OnClosedAsync; - if (CaptureOperations) - { - Operations = new Operations(); - } - if (!connectAutomatically) { return true; @@ -366,7 +364,7 @@ namespace Ignitor var descriptors = await GetPrerenderDescriptors(uri); await ExpectRenderBatch( - async () => CircuitId = await HubConnection.InvokeAsync("StartCircuit", uri, uri, descriptors), + async () => CircuitId = await HubConnection.InvokeAsync("StartCircuit", uri, uri, descriptors, CancellationToken), DefaultConnectionTimeout); return CircuitId != null; } @@ -415,9 +413,9 @@ namespace Ignitor NextBatchReceived?.Completion?.TrySetResult(null); } - public Task ConfirmBatch(int batchId, string error = null) + public Task ConfirmBatch(int batchId, string? error = null) { - return HubConnection.InvokeAsync("OnRenderCompleted", batchId, error); + return HubConnection.InvokeAsync("OnRenderCompleted", batchId, error, CancellationToken); } private void OnError(string error) @@ -468,7 +466,14 @@ namespace Ignitor public async Task InvokeDotNetMethod(object callId, string assemblyName, string methodIdentifier, object dotNetObjectId, string argsJson) { - await ExpectDotNetInterop(() => HubConnection.InvokeAsync("BeginInvokeDotNetFromJS", callId?.ToString(), assemblyName, methodIdentifier, dotNetObjectId ?? 0, argsJson)); + await ExpectDotNetInterop(() => HubConnection.InvokeAsync( + "BeginInvokeDotNetFromJS", + callId?.ToString(), + assemblyName, + methodIdentifier, + dotNetObjectId ?? 0, + argsJson, + CancellationToken)); } public async Task GetPrerenderDescriptors(Uri uri) @@ -485,8 +490,11 @@ namespace Ignitor public void Cancel() { - CancellationTokenSource.Cancel(); - CancellationTokenSource.Dispose(); + if (!CancellationTokenSource.IsCancellationRequested) + { + CancellationTokenSource.Cancel(); + CancellationTokenSource.Dispose(); + } } public ElementNode FindElementById(string id) @@ -519,6 +527,7 @@ namespace Ignitor public async ValueTask DisposeAsync() { + Cancel(); if (HubConnection != null) { await HubConnection.DisposeAsync(); @@ -526,3 +535,5 @@ namespace Ignitor } } } + +#nullable restore diff --git a/src/Components/Ignitor/src/CancellableOperation.cs b/src/Components/Ignitor/src/CancellableOperation.cs index dad8cb5587..6e1f217d19 100644 --- a/src/Components/Ignitor/src/CancellableOperation.cs +++ b/src/Components/Ignitor/src/CancellableOperation.cs @@ -5,11 +5,12 @@ using System; using System.Threading; using System.Threading.Tasks; +#nullable enable namespace Ignitor { internal class CancellableOperation { - public CancellableOperation(TimeSpan? timeout) + public CancellableOperation(TimeSpan? timeout, CancellationToken cancellationToken) { Timeout = timeout; @@ -17,25 +18,37 @@ namespace Ignitor Completion.Task.ContinueWith( (task, state) => { - var operation = (CancellableOperation)state; + var operation = (CancellableOperation)state!; operation.Dispose(); }, this, TaskContinuationOptions.ExecuteSynchronously); // We need to execute synchronously to clean-up before anything else continues + + Cancellation = CancellationTokenSource.CreateLinkedTokenSource(cancellationToken); + if (Timeout != null && Timeout != System.Threading.Timeout.InfiniteTimeSpan && Timeout != TimeSpan.MaxValue) { - Cancellation = new CancellationTokenSource(Timeout.Value); - CancellationRegistration = Cancellation.Token.Register( - (self) => - { - var operation = (CancellableOperation)self; - operation.Completion.TrySetCanceled(operation.Cancellation.Token); - operation.Cancellation.Dispose(); - operation.CancellationRegistration.Dispose(); - }, - this); + Cancellation.CancelAfter(Timeout.Value); } + + CancellationRegistration = Cancellation.Token.Register( + (self) => + { + var operation = (CancellableOperation)self!; + + if (cancellationToken.IsCancellationRequested) + { + // The operation was externally canceled before it timed out. + Dispose(); + return; + } + + operation.Completion.TrySetException(new TimeoutException($"The operation timed out after {Timeout}.")); + operation.Cancellation?.Dispose(); + operation.CancellationRegistration.Dispose(); + }, + this); } public TimeSpan? Timeout { get; } @@ -62,3 +75,4 @@ namespace Ignitor } } } +#nullable restore diff --git a/src/Components/Ignitor/src/ComponentState.cs b/src/Components/Ignitor/src/ComponentState.cs index 2acae3af21..28683bee11 100644 --- a/src/Components/Ignitor/src/ComponentState.cs +++ b/src/Components/Ignitor/src/ComponentState.cs @@ -3,6 +3,7 @@ namespace Ignitor { +#nullable enable public class ComponentState { public ComponentState(int componentId) @@ -11,6 +12,7 @@ namespace Ignitor } public int ComponentId { get; } - public IComponent Component { get; } + public IComponent? Component { get; } } +#nullable restore } diff --git a/src/Components/Ignitor/src/ContainerNode.cs b/src/Components/Ignitor/src/ContainerNode.cs index 9e933dee23..24ee50b458 100644 --- a/src/Components/Ignitor/src/ContainerNode.cs +++ b/src/Components/Ignitor/src/ContainerNode.cs @@ -4,6 +4,7 @@ using System; using System.Collections.Generic; +#nullable enable namespace Ignitor { public abstract class ContainerNode : Node @@ -82,3 +83,4 @@ namespace Ignitor } } } +#nullable restore diff --git a/src/Components/Ignitor/src/ElementHive.cs b/src/Components/Ignitor/src/ElementHive.cs index 95c4c02397..3bb37c38ce 100644 --- a/src/Components/Ignitor/src/ElementHive.cs +++ b/src/Components/Ignitor/src/ElementHive.cs @@ -3,7 +3,9 @@ using System; using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; +#nullable enable namespace Ignitor { public class ElementHive @@ -35,7 +37,7 @@ namespace Ignitor } } - public bool TryFindElementById(string id, out ElementNode element) + public bool TryFindElementById(string id, [NotNullWhen(true)] out ElementNode? element) { foreach (var kvp in Components) { @@ -49,7 +51,7 @@ namespace Ignitor element = null; return false; - bool TryGetElementFromChildren(Node node, out ElementNode foundNode) + bool TryGetElementFromChildren(Node node, out ElementNode? foundNode) { if (node is ElementNode elementNode && elementNode.Attributes.TryGetValue("id", out var elementId) && @@ -81,6 +83,7 @@ namespace Ignitor { component = new ComponentNode(componentId); Components.Add(componentId, component); + } ApplyEdits(batch, component, 0, edits); @@ -199,7 +202,7 @@ namespace Ignitor case RenderTreeEditType.StepOut: { - parent = parent.Parent; + parent = parent.Parent ?? throw new InvalidOperationException($"Cannot step out of {parent}"); currentDepth--; childIndexAtCurrentDepth = currentDepth == 0 ? childIndex : 0; // The childIndex is only ever nonzero at zero depth break; @@ -469,3 +472,4 @@ namespace Ignitor } } } +#nullable restore diff --git a/src/Components/Ignitor/src/ElementNode.cs b/src/Components/Ignitor/src/ElementNode.cs index cebcaef323..06126cf42e 100644 --- a/src/Components/Ignitor/src/ElementNode.cs +++ b/src/Components/Ignitor/src/ElementNode.cs @@ -7,6 +7,7 @@ using System.Text.Json; using System.Threading.Tasks; using Microsoft.AspNetCore.SignalR.Client; +#nullable enable namespace Ignitor { public class ElementNode : ContainerNode @@ -87,7 +88,7 @@ namespace Ignitor return DispatchEventCore(connection, Serialize(webEventDescriptor), Serialize(args)); } - public Task ClickAsync(HubConnection connection) + internal Task ClickAsync(HubConnection connection) { if (!Events.TryGetValue("click", out var clickEventDescriptor)) { @@ -129,3 +130,4 @@ namespace Ignitor } } } +#nullable restore diff --git a/src/Components/Ignitor/src/Error.cs b/src/Components/Ignitor/src/Error.cs index e452e5d195..7258ebe885 100644 --- a/src/Components/Ignitor/src/Error.cs +++ b/src/Components/Ignitor/src/Error.cs @@ -1,10 +1,12 @@ // 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. +#nullable enable namespace Ignitor { public class Error { - public string Stack { get; set; } + public string? Stack { get; set; } } } +#nullable restore diff --git a/src/Components/Ignitor/src/IComponent.cs b/src/Components/Ignitor/src/IComponent.cs index ce9b3d324c..54b1c853a6 100644 --- a/src/Components/Ignitor/src/IComponent.cs +++ b/src/Components/Ignitor/src/IComponent.cs @@ -1,6 +1,5 @@ -using System; -using System.Collections.Generic; -using System.Text; +// 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. namespace Ignitor { diff --git a/src/Components/Ignitor/src/Node.cs b/src/Components/Ignitor/src/Node.cs index 07fef1bd4a..04b2559333 100644 --- a/src/Components/Ignitor/src/Node.cs +++ b/src/Components/Ignitor/src/Node.cs @@ -1,10 +1,14 @@ // 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. +#nullable enable + namespace Ignitor { public abstract class Node { - public virtual ContainerNode Parent { get; set; } + public virtual ContainerNode? Parent { get; set; } } } + +#nullable restore diff --git a/src/Components/Ignitor/src/NodeSerializer.cs b/src/Components/Ignitor/src/NodeSerializer.cs index b3984a319f..4d5919ce94 100644 --- a/src/Components/Ignitor/src/NodeSerializer.cs +++ b/src/Components/Ignitor/src/NodeSerializer.cs @@ -4,6 +4,8 @@ using System; using System.IO; +#nullable enable + namespace Ignitor { internal static class NodeSerializer @@ -96,7 +98,7 @@ namespace Ignitor if (attribute.Value != null) { Write("=\""); - Write(attribute.Value.ToString()); + Write(attribute.Value.ToString()!); Write("\""); } } @@ -113,7 +115,7 @@ namespace Ignitor if (properties.Value != null) { Write("=\""); - Write(properties.Value.ToString()); + Write(properties.Value.ToString()!); Write("\""); } } @@ -194,3 +196,4 @@ namespace Ignitor } } } +#nullable restore diff --git a/src/Components/Ignitor/src/Operations.cs b/src/Components/Ignitor/src/Operations.cs index efcb5346fb..e9c525835c 100644 --- a/src/Components/Ignitor/src/Operations.cs +++ b/src/Components/Ignitor/src/Operations.cs @@ -3,6 +3,7 @@ using System.Collections.Concurrent; +#nullable enable namespace Ignitor { public sealed class Operations @@ -18,3 +19,4 @@ namespace Ignitor public ConcurrentQueue JSInteropCalls { get; } = new ConcurrentQueue(); } } +#nullable restore diff --git a/src/Components/Ignitor/src/RenderBatchReader.cs b/src/Components/Ignitor/src/RenderBatchReader.cs index 1581fc7022..85f6c523f0 100644 --- a/src/Components/Ignitor/src/RenderBatchReader.cs +++ b/src/Components/Ignitor/src/RenderBatchReader.cs @@ -4,6 +4,8 @@ using System; using System.Text; +#nullable enable + namespace Ignitor { public static class RenderBatchReader @@ -206,7 +208,7 @@ namespace Ignitor return new ArrayRange(Array.Empty(), 0); } - private static string ReadString(ReadOnlySpan data, string[] strings) + private static string? ReadString(ReadOnlySpan data, string[] strings) { var index = BitConverter.ToInt32(data.Slice(0, 4)); return index >= 0 ? strings[index] : null; @@ -279,3 +281,4 @@ namespace Ignitor } } } +#nullable restore diff --git a/src/Components/Samples/BlazorServerApp/BlazorServerApp.csproj b/src/Components/Samples/BlazorServerApp/BlazorServerApp.csproj index 101fe45c13..2a82b7453a 100644 --- a/src/Components/Samples/BlazorServerApp/BlazorServerApp.csproj +++ b/src/Components/Samples/BlazorServerApp/BlazorServerApp.csproj @@ -12,6 +12,7 @@ + diff --git a/src/Components/Samples/BlazorServerApp/wwwroot/css/site.css b/src/Components/Samples/BlazorServerApp/wwwroot/css/site.css index 17b0a5e617..c15c2e1556 100644 --- a/src/Components/Samples/BlazorServerApp/wwwroot/css/site.css +++ b/src/Components/Samples/BlazorServerApp/wwwroot/css/site.css @@ -30,66 +30,72 @@ app { flex: 1; } -.main .top-row { - background-color: #f7f7f7; - border-bottom: 1px solid #d6d5d5; - justify-content: flex-end; -} + .main .top-row { + background-color: #f7f7f7; + border-bottom: 1px solid #d6d5d5; + justify-content: flex-end; + } -.main .top-row > a { - margin-left: 1.5rem; + .main .top-row > a, .main .top-row .btn-link { + white-space: nowrap; + margin-left: 1.5rem; + } + +.main .top-row a:first-child { + overflow: hidden; + text-overflow: ellipsis; } .sidebar { background-image: linear-gradient(180deg, rgb(5, 39, 103) 0%, #3a0647 70%); } -.sidebar .top-row { - background-color: rgba(0,0,0,0.4); -} + .sidebar .top-row { + background-color: rgba(0,0,0,0.4); + } -.sidebar .navbar-brand { - font-size: 1.1rem; -} + .sidebar .navbar-brand { + font-size: 1.1rem; + } -.sidebar .oi { - width: 2rem; - font-size: 1.1rem; - vertical-align: text-top; - top: -2px; -} + .sidebar .oi { + width: 2rem; + font-size: 1.1rem; + vertical-align: text-top; + top: -2px; + } -.nav-item { - font-size: 0.9rem; - padding-bottom: 0.5rem; -} + .sidebar .nav-item { + font-size: 0.9rem; + padding-bottom: 0.5rem; + } -.nav-item:first-of-type { - padding-top: 1rem; -} + .sidebar .nav-item:first-of-type { + padding-top: 1rem; + } -.nav-item:last-of-type { - padding-bottom: 1rem; -} + .sidebar .nav-item:last-of-type { + padding-bottom: 1rem; + } -.nav-item a { - color: #d7d7d7; - border-radius: 4px; - height: 3rem; - display: flex; - align-items: center; - line-height: 3rem; -} + .sidebar .nav-item a { + color: #d7d7d7; + border-radius: 4px; + height: 3rem; + display: flex; + align-items: center; + line-height: 3rem; + } -.nav-item a.active { - background-color: rgba(255,255,255,0.25); - color: white; -} + .sidebar .nav-item a.active { + background-color: rgba(255,255,255,0.25); + color: white; + } -.nav-item a:hover { - background-color: rgba(255,255,255,0.1); - color: white; -} + .sidebar .nav-item a:hover { + background-color: rgba(255,255,255,0.1); + color: white; + } .content { padding-top: 1.1rem; @@ -131,9 +137,17 @@ app { } @media (max-width: 767.98px) { - .main .top-row { + .main .top-row:not(.auth) { display: none; } + + .main .top-row.auth { + justify-content: space-between; + } + + .main .top-row a, .main .top-row .btn-link { + margin-left: 0; + } } @media (min-width: 768px) { diff --git a/src/Components/Server/src/BlazorPack/BlazorPackHubProtocol.cs b/src/Components/Server/src/BlazorPack/BlazorPackHubProtocol.cs index 32034b556e..6d726262a4 100644 --- a/src/Components/Server/src/BlazorPack/BlazorPackHubProtocol.cs +++ b/src/Components/Server/src/BlazorPack/BlazorPackHubProtocol.cs @@ -12,6 +12,7 @@ using MessagePack; using Microsoft.AspNetCore.Connections; using Microsoft.AspNetCore.Internal; using Microsoft.AspNetCore.SignalR; +using Microsoft.AspNetCore.SignalR.Internal; using Microsoft.AspNetCore.SignalR.Protocol; namespace Microsoft.AspNetCore.Components.Server.BlazorPack @@ -19,6 +20,7 @@ namespace Microsoft.AspNetCore.Components.Server.BlazorPack /// /// Implements the SignalR Hub Protocol using MessagePack with limited type support. /// + [NonDefaultHubProtocol] internal sealed class BlazorPackHubProtocol : IHubProtocol { internal const string ProtocolName = "blazorpack"; @@ -78,7 +80,7 @@ namespace Microsoft.AspNetCore.Components.Server.BlazorPack message = PingMessage.Instance; return true; case HubProtocolConstants.CloseMessageType: - message = CreateCloseMessage(ref reader); + message = CreateCloseMessage(ref reader, itemCount); return true; default: // Future protocol changes can add message types, old clients can ignore them @@ -196,10 +198,23 @@ namespace Microsoft.AspNetCore.Components.Server.BlazorPack return ApplyHeaders(headers, new CancelInvocationMessage(invocationId)); } - private static CloseMessage CreateCloseMessage(ref MessagePackReader reader) + private static CloseMessage CreateCloseMessage(ref MessagePackReader reader, int itemCount) { var error = ReadString(ref reader, "error"); - return new CloseMessage(error); + var allowReconnect = false; + + if (itemCount > 2) + { + allowReconnect = ReadBoolean(ref reader, "allowReconnect"); + } + + // An empty string is still an error + if (error == null && !allowReconnect) + { + return CloseMessage.Empty; + } + + return new CloseMessage(error, allowReconnect); } private static Dictionary ReadHeaders(ref MessagePackReader reader) @@ -515,7 +530,7 @@ namespace Microsoft.AspNetCore.Components.Server.BlazorPack private void WriteCloseMessage(CloseMessage message, ref MessagePackWriter writer) { - writer.WriteArrayHeader(2); + writer.WriteArrayHeader(3); writer.Write(HubProtocolConstants.CloseMessageType); if (string.IsNullOrEmpty(message.Error)) { @@ -525,6 +540,8 @@ namespace Microsoft.AspNetCore.Components.Server.BlazorPack { writer.Write(message.Error); } + + writer.Write(message.AllowReconnect); } private void WritePingMessage(PingMessage _, ref MessagePackWriter writer) @@ -559,6 +576,17 @@ namespace Microsoft.AspNetCore.Components.Server.BlazorPack return destination; } + [MethodImpl(MethodImplOptions.AggressiveInlining)] + private static bool ReadBoolean(ref MessagePackReader reader, string field) + { + if (reader.End || reader.NextMessagePackType != MessagePackType.Boolean) + { + ThrowInvalidDataException(field, "Boolean"); + } + + return reader.ReadBoolean(); + } + [MethodImpl(MethodImplOptions.AggressiveInlining)] private static int ReadInt32(ref MessagePackReader reader, string field) { diff --git a/src/Components/Server/src/BlazorPack/NonDefaultHubProtocolAttribute.cs b/src/Components/Server/src/BlazorPack/NonDefaultHubProtocolAttribute.cs new file mode 100644 index 0000000000..141d8b3194 --- /dev/null +++ b/src/Components/Server/src/BlazorPack/NonDefaultHubProtocolAttribute.cs @@ -0,0 +1,13 @@ +// 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; + +namespace Microsoft.AspNetCore.SignalR.Internal +{ + // Tells SignalR not to add the IHubProtocol with this attribute to all hubs by default + [AttributeUsage(AttributeTargets.Class, AllowMultiple = false, Inherited = true)] + internal class NonDefaultHubProtocolAttribute : Attribute + { + } +} diff --git a/src/Components/Server/src/Circuits/CircuitHost.cs b/src/Components/Server/src/Circuits/CircuitHost.cs index a6a7850e81..02deaf9370 100644 --- a/src/Components/Server/src/Circuits/CircuitHost.cs +++ b/src/Components/Server/src/Circuits/CircuitHost.cs @@ -225,7 +225,7 @@ namespace Microsoft.AspNetCore.Components.Server.Circuits Log.ConnectionUp(_logger, CircuitId, Client.ConnectionId); Renderer.Dispatcher.AssertAccess(); - + List exceptions = null; for (var i = 0; i < _circuitHandlers.Length; i++) @@ -254,7 +254,7 @@ namespace Microsoft.AspNetCore.Components.Server.Circuits Log.ConnectionDown(_logger, CircuitId, Client.ConnectionId); Renderer.Dispatcher.AssertAccess(); - + List exceptions = null; for (var i = 0; i < _circuitHandlers.Length; i++) @@ -545,7 +545,7 @@ namespace Microsoft.AspNetCore.Components.Server.Circuits else { return $"There was an unhandled exception on the current circuit, so this circuit will be terminated. For more details turn on " + - $"detailed exceptions in '{typeof(CircuitOptions).Name}.{nameof(CircuitOptions.DetailedErrors)}'. {additionalInformation}"; + $"detailed exceptions by setting 'DetailedErrors: true' in 'appSettings.Development.json' or set '{typeof(CircuitOptions).Name}.{nameof(CircuitOptions.DetailedErrors)}'. {additionalInformation}"; } } diff --git a/src/Components/Web.JS/dist/Release/blazor.server.js b/src/Components/Web.JS/dist/Release/blazor.server.js index 754717e8b8..00204cecb0 100644 --- a/src/Components/Web.JS/dist/Release/blazor.server.js +++ b/src/Components/Web.JS/dist/Release/blazor.server.js @@ -1,4 +1,4 @@ -!function(e){var t={};function n(r){if(t[r])return t[r].exports;var o=t[r]={i:r,l:!1,exports:{}};return e[r].call(o.exports,o,o.exports,n),o.l=!0,o.exports}n.m=e,n.c=t,n.d=function(e,t,r){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:r})},n.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var o in e)n.d(r,o,function(t){return e[t]}.bind(null,o));return r},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,"a",t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p="",n(n.s=50)}([function(e,t,n){"use strict";var r;n.d(t,"a",function(){return r}),function(e){e[e.Trace=0]="Trace",e[e.Debug=1]="Debug",e[e.Information=2]="Information",e[e.Warning=3]="Warning",e[e.Error=4]="Error",e[e.Critical=5]="Critical",e[e.None=6]="None"}(r||(r={}))},function(e,t,n){"use strict";(function(e){n.d(t,"e",function(){return s}),n.d(t,"a",function(){return c}),n.d(t,"c",function(){return u}),n.d(t,"g",function(){return l}),n.d(t,"i",function(){return f}),n.d(t,"j",function(){return h}),n.d(t,"f",function(){return p}),n.d(t,"d",function(){return d}),n.d(t,"b",function(){return g}),n.d(t,"h",function(){return y});var r=n(0),o=n(7),i=function(e,t,n,r){return new(n||(n=Promise))(function(o,i){function a(e){try{c(r.next(e))}catch(e){i(e)}}function s(e){try{c(r.throw(e))}catch(e){i(e)}}function c(e){e.done?o(e.value):new n(function(t){t(e.value)}).then(a,s)}c((r=r.apply(e,t||[])).next())})},a=function(e,t){var n,r,o,i,a={label:0,sent:function(){if(1&o[0])throw o[1];return o[1]},trys:[],ops:[]};return i={next:s(0),throw:s(1),return:s(2)},"function"==typeof Symbol&&(i[Symbol.iterator]=function(){return this}),i;function s(i){return function(s){return function(i){if(n)throw new TypeError("Generator is already executing.");for(;a;)try{if(n=1,r&&(o=2&i[0]?r.return:i[0]?r.throw||((o=r.return)&&o.call(r),0):r.next)&&!(o=o.call(r,i[1])).done)return o;switch(r=0,o&&(i=[2&i[0],o.value]),i[0]){case 0:case 1:o=i;break;case 4:return a.label++,{value:i[1],done:!1};case 5:a.label++,r=i[1],i=[0];continue;case 7:i=a.ops.pop(),a.trys.pop();continue;default:if(!(o=(o=a.trys).length>0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]-1&&this.subject.observers.splice(e,1),0===this.subject.observers.length&&this.subject.cancelCallback&&this.subject.cancelCallback().catch(function(e){})},e}(),g=function(){function e(e){this.minimumLogLevel=e,this.outputConsole=console}return e.prototype.log=function(e,t){if(e>=this.minimumLogLevel)switch(e){case r.a.Critical:case r.a.Error:this.outputConsole.error("["+(new Date).toISOString()+"] "+r.a[e]+": "+t);break;case r.a.Warning:this.outputConsole.warn("["+(new Date).toISOString()+"] "+r.a[e]+": "+t);break;case r.a.Information:this.outputConsole.info("["+(new Date).toISOString()+"] "+r.a[e]+": "+t);break;default:this.outputConsole.log("["+(new Date).toISOString()+"] "+r.a[e]+": "+t)}},e}();function y(){var e="X-SignalR-User-Agent";return u.isNode&&(e="User-Agent"),[e,v(s,b(),w(),m())]}function v(e,t,n,r){var o="Microsoft SignalR/",i=e.split(".");return o+=i[0]+"."+i[1],o+=" ("+e+"; ",o+=t&&""!==t?t+"; ":"Unknown OS; ",o+=""+n,o+=r?"; "+r:"; Unknown Runtime Version",o+=")"}function b(){if(!u.isNode)return"";switch(e.platform){case"win32":return"Windows NT";case"darwin":return"macOS";case"linux":return"Linux";default:return e.platform}}function m(){if(u.isNode)return e.versions.node}function w(){return u.isNode?"NodeJS":"Browser"}}).call(this,n(15))},function(e,t,n){"use strict";n.r(t);var r,o=n(3),i=n(4),a=n(0),s=(r=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])},function(e,t){function n(){this.constructor=e}r(e,t),e.prototype=null===t?Object.create(t):(n.prototype=t.prototype,new n)}),c=Object.assign||function(e){for(var t,n=1,r=arguments.length;n0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]=200&&s.status<300?n(new i.b(s.status,s.statusText,s.response||s.responseText)):r(new o.b(s.statusText,s.status))},s.onerror=function(){t.logger.log(a.a.Warning,"Error from HTTP request. "+s.status+": "+s.statusText+"."),r(new o.b(s.statusText,s.status))},s.ontimeout=function(){t.logger.log(a.a.Warning,"Timeout from HTTP request."),r(new o.c)},s.send(e.content||"")}):Promise.reject(new Error("No url defined.")):Promise.reject(new Error("No method defined."))},t}(i.a),y=function(){var e=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])};return function(t,n){function r(){this.constructor=t}e(t,n),t.prototype=null===n?Object.create(n):(r.prototype=n.prototype,new r)}}(),v=function(e){function t(t){var n=e.call(this)||this;return"undefined"!=typeof fetch?n.httpClient=new f(t):"undefined"!=typeof XMLHttpRequest?n.httpClient=new g(t):n.httpClient=new p.a(t),n}return y(t,e),t.prototype.send=function(e){return e.abortSignal&&e.abortSignal.aborted?Promise.reject(new o.a):e.method?e.url?this.httpClient.send(e):Promise.reject(new Error("No url defined.")):Promise.reject(new Error("No method defined."))},t.prototype.getCookieString=function(e){return this.httpClient.getCookieString(e)},t}(i.a),b=n(45);!function(e){e[e.Invocation=1]="Invocation",e[e.StreamItem=2]="StreamItem",e[e.Completion=3]="Completion",e[e.StreamInvocation=4]="StreamInvocation",e[e.CancelInvocation=5]="CancelInvocation",e[e.Ping=6]="Ping",e[e.Close=7]="Close"}(h||(h={}));var m,w=n(1),E=function(){function e(){this.observers=[]}return e.prototype.next=function(e){for(var t=0,n=this.observers;t0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0?[2,Promise.reject(new Error("Unable to connect to the server with any of the available transports. "+i.join(" ")))]:[2,Promise.reject(new Error("None of the transports supported by the client are supported by the server."))]}})})},e.prototype.constructTransport=function(e){switch(e){case k.WebSockets:if(!this.options.WebSocket)throw new Error("'WebSocket' is not supported in your environment.");return new F(this.httpClient,this.accessTokenFactory,this.logger,this.options.logMessageContent||!1,this.options.WebSocket);case k.ServerSentEvents:if(!this.options.EventSource)throw new Error("'EventSource' is not supported in your environment.");return new B(this.httpClient,this.accessTokenFactory,this.logger,this.options.logMessageContent||!1,this.options.EventSource);case k.LongPolling:return new M(this.httpClient,this.accessTokenFactory,this.logger,this.options.logMessageContent||!1);default:throw new Error("Unknown transport: "+e+".")}},e.prototype.startTransport=function(e,t){var n=this;return this.transport.onreceive=this.onreceive,this.transport.onclose=function(e){return n.stopConnection(e)},this.transport.connect(e,t)},e.prototype.resolveTransportOrError=function(e,t,n){var r=k[e.transport];if(null==r)return this.logger.log(a.a.Debug,"Skipping transport '"+e.transport+"' because it is not supported by this client."),new Error("Skipping transport '"+e.transport+"' because it is not supported by this client.");if(!function(e,t){return!e||0!=(t&e)}(t,r))return this.logger.log(a.a.Debug,"Skipping transport '"+k[r]+"' because it was disabled by the client."),new Error("'"+k[r]+"' is disabled by the client.");if(!(e.transferFormats.map(function(e){return I[e]}).indexOf(n)>=0))return this.logger.log(a.a.Debug,"Skipping transport '"+k[r]+"' because it does not support the requested transfer format '"+I[n]+"'."),new Error("'"+k[r]+"' does not support "+I[n]+".");if(r===k.WebSockets&&!this.options.WebSocket||r===k.ServerSentEvents&&!this.options.EventSource)return this.logger.log(a.a.Debug,"Skipping transport '"+k[r]+"' because it is not supported in your environment.'"),new Error("'"+k[r]+"' is not supported in your environment.");this.logger.log(a.a.Debug,"Selecting transport '"+k[r]+"'.");try{return this.constructTransport(r)}catch(e){return e}},e.prototype.isITransport=function(e){return e&&"object"==typeof e&&"connect"in e},e.prototype.stopConnection=function(e){if(this.logger.log(a.a.Debug,"HttpConnection.stopConnection("+e+") called while in state "+this.connectionState+"."),this.transport=void 0,e=this.stopError||e,this.stopError=void 0,"Disconnected"!==this.connectionState)if("Connecting "!==this.connectionState){if("Disconnecting"===this.connectionState&&this.stopPromiseResolver(),e?this.logger.log(a.a.Error,"Connection disconnected with error '"+e+"'."):this.logger.log(a.a.Information,"Connection disconnected."),this.connectionId=void 0,this.connectionState="Disconnected",this.onclose&&this.connectionStarted){this.connectionStarted=!1;try{this.onclose(e)}catch(t){this.logger.log(a.a.Error,"HttpConnection.onclose("+e+") threw error '"+t+"'.")}}}else this.logger.log(a.a.Warning,"Call to HttpConnection.stopConnection("+e+") was ignored because the connection hasn't yet left the in the connecting state.");else this.logger.log(a.a.Debug,"Call to HttpConnection.stopConnection("+e+") was ignored because the connection is already in the disconnected state.")},e.prototype.resolveUrl=function(e){if(0===e.lastIndexOf("https://",0)||0===e.lastIndexOf("http://",0))return e;if(!w.c.isBrowser||!window.document)throw new Error("Cannot resolve '"+e+"'.");var t=window.document.createElement("a");return t.href=e,this.logger.log(a.a.Information,"Normalizing '"+e+"' to '"+t.href+"'."),t.href},e.prototype.resolveNegotiateUrl=function(e){var t=e.indexOf("?"),n=e.substring(0,-1===t?e.length:t);return"/"!==n[n.length-1]&&(n+="/"),n+="negotiate",-1===(n+=-1===t?"":e.substring(t)).indexOf("negotiateVersion")&&(n+=-1===t?"?":"&",n+="negotiateVersion="+this.negotiateVersion),n},e}();var K=function(){function e(e){this.transport=e,this.buffer=[],this.executing=!0,this.sendBufferedData=new V,this.transportResult=new V,this.sendLoopPromise=this.sendLoop()}return e.prototype.send=function(e){return this.bufferData(e),this.transportResult||(this.transportResult=new V),this.transportResult.promise},e.prototype.stop=function(){return this.executing=!1,this.sendBufferedData.resolve(),this.sendLoopPromise},e.prototype.bufferData=function(e){if(this.buffer.length&&typeof this.buffer[0]!=typeof e)throw new Error("Expected data to be of type "+typeof this.buffer+" but was of type "+typeof e);this.buffer.push(e),this.sendBufferedData.resolve()},e.prototype.sendLoop=function(){return H(this,void 0,void 0,function(){var t,n,r;return q(this,function(o){switch(o.label){case 0:return[4,this.sendBufferedData.promise];case 1:if(o.sent(),!this.executing)return this.transportResult&&this.transportResult.reject("Connection stopped."),[3,6];this.sendBufferedData=new V,t=this.transportResult,this.transportResult=void 0,n="string"==typeof this.buffer[0]?this.buffer.join(""):e.concatBuffers(this.buffer),this.buffer.length=0,o.label=2;case 2:return o.trys.push([2,4,,5]),[4,this.transport.send(n)];case 3:return o.sent(),t.resolve(),[3,5];case 4:return r=o.sent(),t.reject(r),[3,5];case 5:return[3,0];case 6:return[2]}})})},e.concatBuffers=function(e){for(var t=e.map(function(e){return e.byteLength}).reduce(function(e,t){return e+t}),n=new Uint8Array(t),r=0,o=0,i=e;o0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]-1&&this.subject.observers.splice(e,1),0===this.subject.observers.length&&this.subject.cancelCallback&&this.subject.cancelCallback().catch(function(e){})},e}(),g=function(){function e(e){this.minimumLogLevel=e,this.outputConsole=console}return e.prototype.log=function(e,t){if(e>=this.minimumLogLevel)switch(e){case r.a.Critical:case r.a.Error:this.outputConsole.error("["+(new Date).toISOString()+"] "+r.a[e]+": "+t);break;case r.a.Warning:this.outputConsole.warn("["+(new Date).toISOString()+"] "+r.a[e]+": "+t);break;case r.a.Information:this.outputConsole.info("["+(new Date).toISOString()+"] "+r.a[e]+": "+t);break;default:this.outputConsole.log("["+(new Date).toISOString()+"] "+r.a[e]+": "+t)}},e}();function y(){var e="X-SignalR-User-Agent";return u.isNode&&(e="User-Agent"),[e,v(s,b(),w(),m())]}function v(e,t,n,r){var o="Microsoft SignalR/",i=e.split(".");return o+=i[0]+"."+i[1],o+=" ("+e+"; ",o+=t&&""!==t?t+"; ":"Unknown OS; ",o+=""+n,o+=r?"; "+r:"; Unknown Runtime Version",o+=")"}function b(){if(!u.isNode)return"";switch(e.platform){case"win32":return"Windows NT";case"darwin":return"macOS";case"linux":return"Linux";default:return e.platform}}function m(){if(u.isNode)return e.versions.node}function w(){return u.isNode?"NodeJS":"Browser"}}).call(this,n(15))},function(e,t,n){"use strict";n.r(t);var r,o=n(3),i=n(4),a=n(0),s=(r=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])},function(e,t){function n(){this.constructor=e}r(e,t),e.prototype=null===t?Object.create(t):(n.prototype=t.prototype,new n)}),c=Object.assign||function(e){for(var t,n=1,r=arguments.length;n0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]=200&&s.status<300?n(new i.b(s.status,s.statusText,s.response||s.responseText)):r(new o.b(s.statusText,s.status))},s.onerror=function(){t.logger.log(a.a.Warning,"Error from HTTP request. "+s.status+": "+s.statusText+"."),r(new o.b(s.statusText,s.status))},s.ontimeout=function(){t.logger.log(a.a.Warning,"Timeout from HTTP request."),r(new o.c)},s.send(e.content||"")}):Promise.reject(new Error("No url defined.")):Promise.reject(new Error("No method defined."))},t}(i.a),y=function(){var e=Object.setPrototypeOf||{__proto__:[]}instanceof Array&&function(e,t){e.__proto__=t}||function(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n])};return function(t,n){function r(){this.constructor=t}e(t,n),t.prototype=null===n?Object.create(n):(r.prototype=n.prototype,new r)}}(),v=function(e){function t(t){var n=e.call(this)||this;return"undefined"!=typeof fetch?n.httpClient=new f(t):"undefined"!=typeof XMLHttpRequest?n.httpClient=new g(t):n.httpClient=new p.a(t),n}return y(t,e),t.prototype.send=function(e){return e.abortSignal&&e.abortSignal.aborted?Promise.reject(new o.a):e.method?e.url?this.httpClient.send(e):Promise.reject(new Error("No url defined.")):Promise.reject(new Error("No method defined."))},t.prototype.getCookieString=function(e){return this.httpClient.getCookieString(e)},t}(i.a),b=n(45);!function(e){e[e.Invocation=1]="Invocation",e[e.StreamItem=2]="StreamItem",e[e.Completion=3]="Completion",e[e.StreamInvocation=4]="StreamInvocation",e[e.CancelInvocation=5]="CancelInvocation",e[e.Ping=6]="Ping",e[e.Close=7]="Close"}(h||(h={}));var m,w=n(1),E=function(){function e(){this.observers=[]}return e.prototype.next=function(e){for(var t=0,n=this.observers;t0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0?[2,Promise.reject(new Error("Unable to connect to the server with any of the available transports. "+i.join(" ")))]:[2,Promise.reject(new Error("None of the transports supported by the client are supported by the server."))]}})})},e.prototype.constructTransport=function(e){switch(e){case k.WebSockets:if(!this.options.WebSocket)throw new Error("'WebSocket' is not supported in your environment.");return new F(this.httpClient,this.accessTokenFactory,this.logger,this.options.logMessageContent||!1,this.options.WebSocket);case k.ServerSentEvents:if(!this.options.EventSource)throw new Error("'EventSource' is not supported in your environment.");return new B(this.httpClient,this.accessTokenFactory,this.logger,this.options.logMessageContent||!1,this.options.EventSource);case k.LongPolling:return new M(this.httpClient,this.accessTokenFactory,this.logger,this.options.logMessageContent||!1);default:throw new Error("Unknown transport: "+e+".")}},e.prototype.startTransport=function(e,t){var n=this;return this.transport.onreceive=this.onreceive,this.transport.onclose=function(e){return n.stopConnection(e)},this.transport.connect(e,t)},e.prototype.resolveTransportOrError=function(e,t,n){var r=k[e.transport];if(null==r)return this.logger.log(a.a.Debug,"Skipping transport '"+e.transport+"' because it is not supported by this client."),new Error("Skipping transport '"+e.transport+"' because it is not supported by this client.");if(!function(e,t){return!e||0!=(t&e)}(t,r))return this.logger.log(a.a.Debug,"Skipping transport '"+k[r]+"' because it was disabled by the client."),new Error("'"+k[r]+"' is disabled by the client.");if(!(e.transferFormats.map(function(e){return I[e]}).indexOf(n)>=0))return this.logger.log(a.a.Debug,"Skipping transport '"+k[r]+"' because it does not support the requested transfer format '"+I[n]+"'."),new Error("'"+k[r]+"' does not support "+I[n]+".");if(r===k.WebSockets&&!this.options.WebSocket||r===k.ServerSentEvents&&!this.options.EventSource)return this.logger.log(a.a.Debug,"Skipping transport '"+k[r]+"' because it is not supported in your environment.'"),new Error("'"+k[r]+"' is not supported in your environment.");this.logger.log(a.a.Debug,"Selecting transport '"+k[r]+"'.");try{return this.constructTransport(r)}catch(e){return e}},e.prototype.isITransport=function(e){return e&&"object"==typeof e&&"connect"in e},e.prototype.stopConnection=function(e){if(this.logger.log(a.a.Debug,"HttpConnection.stopConnection("+e+") called while in state "+this.connectionState+"."),this.transport=void 0,e=this.stopError||e,this.stopError=void 0,"Disconnected"!==this.connectionState){if("Connecting "===this.connectionState)throw this.logger.log(a.a.Warning,"Call to HttpConnection.stopConnection("+e+") was ignored because the connection is still in the connecting state."),new Error("HttpConnection.stopConnection("+e+") was called while the connection is still in the connecting state.");if("Disconnecting"===this.connectionState&&this.stopPromiseResolver(),e?this.logger.log(a.a.Error,"Connection disconnected with error '"+e+"'."):this.logger.log(a.a.Information,"Connection disconnected."),this.connectionId=void 0,this.connectionState="Disconnected",this.onclose&&this.connectionStarted){this.connectionStarted=!1;try{this.onclose(e)}catch(t){this.logger.log(a.a.Error,"HttpConnection.onclose("+e+") threw error '"+t+"'.")}}}else this.logger.log(a.a.Debug,"Call to HttpConnection.stopConnection("+e+") was ignored because the connection is already in the disconnected state.")},e.prototype.resolveUrl=function(e){if(0===e.lastIndexOf("https://",0)||0===e.lastIndexOf("http://",0))return e;if(!w.c.isBrowser||!window.document)throw new Error("Cannot resolve '"+e+"'.");var t=window.document.createElement("a");return t.href=e,this.logger.log(a.a.Information,"Normalizing '"+e+"' to '"+t.href+"'."),t.href},e.prototype.resolveNegotiateUrl=function(e){var t=e.indexOf("?"),n=e.substring(0,-1===t?e.length:t);return"/"!==n[n.length-1]&&(n+="/"),n+="negotiate",-1===(n+=-1===t?"":e.substring(t)).indexOf("negotiateVersion")&&(n+=-1===t?"?":"&",n+="negotiateVersion="+this.negotiateVersion),n},e}();var K=function(){function e(e){this.transport=e,this.buffer=[],this.executing=!0,this.sendBufferedData=new V,this.transportResult=new V,this.sendLoopPromise=this.sendLoop()}return e.prototype.send=function(e){return this.bufferData(e),this.transportResult||(this.transportResult=new V),this.transportResult.promise},e.prototype.stop=function(){return this.executing=!1,this.sendBufferedData.resolve(),this.sendLoopPromise},e.prototype.bufferData=function(e){if(this.buffer.length&&typeof this.buffer[0]!=typeof e)throw new Error("Expected data to be of type "+typeof this.buffer+" but was of type "+typeof e);this.buffer.push(e),this.sendBufferedData.resolve()},e.prototype.sendLoop=function(){return H(this,void 0,void 0,function(){var t,n,r;return q(this,function(o){switch(o.label){case 0:return[4,this.sendBufferedData.promise];case 1:if(o.sent(),!this.executing)return this.transportResult&&this.transportResult.reject("Connection stopped."),[3,6];this.sendBufferedData=new V,t=this.transportResult,this.transportResult=void 0,n="string"==typeof this.buffer[0]?this.buffer.join(""):e.concatBuffers(this.buffer),this.buffer.length=0,o.label=2;case 2:return o.trys.push([2,4,,5]),[4,this.transport.send(n)];case 3:return o.sent(),t.resolve(),[3,5];case 4:return r=o.sent(),t.reject(r),[3,5];case 5:return[3,0];case 6:return[2]}})})},e.concatBuffers=function(e){for(var t=e.map(function(e){return e.byteLength}).reduce(function(e,t){return e+t}),n=new Uint8Array(t),r=0,o=0,i=e;o * @license MIT */ -function r(e,t){if(e===t)return 0;for(var n=e.length,r=t.length,o=0,i=Math.min(n,r);o=0;u--)if(l[u]!==f[u])return!1;for(u=l.length-1;u>=0;u--)if(c=l[u],!b(e[c],t[c],n,r))return!1;return!0}(e,t,n,a))}return n?e===t:e==t}function m(e){return"[object Arguments]"==Object.prototype.toString.call(e)}function w(e,t){if(!e||!t)return!1;if("[object RegExp]"==Object.prototype.toString.call(t))return t.test(e);try{if(e instanceof t)return!0}catch(e){}return!Error.isPrototypeOf(t)&&!0===t.call({},e)}function E(e,t,n,r){var o;if("function"!=typeof t)throw new TypeError('"block" argument must be a function');"string"==typeof n&&(r=n,n=null),o=function(e){var t;try{e()}catch(e){t=e}return t}(t),r=(n&&n.name?" ("+n.name+").":".")+(r?" "+r:"."),e&&!o&&y(o,n,"Missing expected exception"+r);var a="string"==typeof r,s=!e&&o&&!n;if((!e&&i.isError(o)&&a&&w(o,n)||s)&&y(o,n,"Got unwanted exception"+r),e&&o&&n&&!w(o,n)||!e&&o)throw o}f.AssertionError=function(e){var t;this.name="AssertionError",this.actual=e.actual,this.expected=e.expected,this.operator=e.operator,e.message?(this.message=e.message,this.generatedMessage=!1):(this.message=d(g((t=this).actual),128)+" "+t.operator+" "+d(g(t.expected),128),this.generatedMessage=!0);var n=e.stackStartFunction||y;if(Error.captureStackTrace)Error.captureStackTrace(this,n);else{var r=new Error;if(r.stack){var o=r.stack,i=p(n),a=o.indexOf("\n"+i);if(a>=0){var s=o.indexOf("\n",a+1);o=o.substring(s+1)}this.stack=o}}},i.inherits(f.AssertionError,Error),f.fail=y,f.ok=v,f.equal=function(e,t,n){e!=t&&y(e,t,n,"==",f.equal)},f.notEqual=function(e,t,n){e==t&&y(e,t,n,"!=",f.notEqual)},f.deepEqual=function(e,t,n){b(e,t,!1)||y(e,t,n,"deepEqual",f.deepEqual)},f.deepStrictEqual=function(e,t,n){b(e,t,!0)||y(e,t,n,"deepStrictEqual",f.deepStrictEqual)},f.notDeepEqual=function(e,t,n){b(e,t,!1)&&y(e,t,n,"notDeepEqual",f.notDeepEqual)},f.notDeepStrictEqual=function e(t,n,r){b(t,n,!0)&&y(t,n,r,"notDeepStrictEqual",e)},f.strictEqual=function(e,t,n){e!==t&&y(e,t,n,"===",f.strictEqual)},f.notStrictEqual=function(e,t,n){e===t&&y(e,t,n,"!==",f.notStrictEqual)},f.throws=function(e,t,n){E(!0,e,t,n)},f.doesNotThrow=function(e,t,n){E(!1,e,t,n)},f.ifError=function(e){if(e)throw e};var S=Object.keys||function(e){var t=[];for(var n in e)a.call(e,n)&&t.push(n);return t}}).call(this,n(10))},function(e,t){e.exports=function(e){return e&&"object"==typeof e&&"function"==typeof e.copy&&"function"==typeof e.fill&&"function"==typeof e.readUInt8}},function(e,t){"function"==typeof Object.create?e.exports=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})}:e.exports=function(e,t){e.super_=t;var n=function(){};n.prototype=t.prototype,e.prototype=new n,e.prototype.constructor=e}},function(e,t,n){e.exports=n(11)},function(e,t){var n={}.toString;e.exports=Array.isArray||function(e){return"[object Array]"==n.call(e)}},function(e,t){},function(e,t,n){"use strict";var r=n(16).Buffer,o=n(61);e.exports=function(){function e(){!function(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}(this,e),this.head=null,this.tail=null,this.length=0}return e.prototype.push=function(e){var t={data:e,next:null};this.length>0?this.tail.next=t:this.head=t,this.tail=t,++this.length},e.prototype.unshift=function(e){var t={data:e,next:this.head};0===this.length&&(this.tail=t),this.head=t,++this.length},e.prototype.shift=function(){if(0!==this.length){var e=this.head.data;return 1===this.length?this.head=this.tail=null:this.head=this.head.next,--this.length,e}},e.prototype.clear=function(){this.head=this.tail=null,this.length=0},e.prototype.join=function(e){if(0===this.length)return"";for(var t=this.head,n=""+t.data;t=t.next;)n+=e+t.data;return n},e.prototype.concat=function(e){if(0===this.length)return r.alloc(0);if(1===this.length)return this.head.data;for(var t,n,o,i=r.allocUnsafe(e>>>0),a=this.head,s=0;a;)t=a.data,n=i,o=s,t.copy(n,o),s+=a.data.length,a=a.next;return i},e}(),o&&o.inspect&&o.inspect.custom&&(e.exports.prototype[o.inspect.custom]=function(){var e=o.inspect({length:this.length});return this.constructor.name+" "+e})},function(e,t){},function(e,t,n){var r=n(6),o=r.Buffer;function i(e,t){for(var n in e)t[n]=e[n]}function a(e,t,n){return o(e,t,n)}o.from&&o.alloc&&o.allocUnsafe&&o.allocUnsafeSlow?e.exports=r:(i(r,t),t.Buffer=a),i(o,a),a.from=function(e,t,n){if("number"==typeof e)throw new TypeError("Argument must not be a number");return o(e,t,n)},a.alloc=function(e,t,n){if("number"!=typeof e)throw new TypeError("Argument must be a number");var r=o(e);return void 0!==t?"string"==typeof n?r.fill(t,n):r.fill(t):r.fill(0),r},a.allocUnsafe=function(e){if("number"!=typeof e)throw new TypeError("Argument must be a number");return o(e)},a.allocUnsafeSlow=function(e){if("number"!=typeof e)throw new TypeError("Argument must be a number");return r.SlowBuffer(e)}},function(e,t,n){(function(e){var r=void 0!==e&&e||"undefined"!=typeof self&&self||window,o=Function.prototype.apply;function i(e,t){this._id=e,this._clearFn=t}t.setTimeout=function(){return new i(o.call(setTimeout,r,arguments),clearTimeout)},t.setInterval=function(){return new i(o.call(setInterval,r,arguments),clearInterval)},t.clearTimeout=t.clearInterval=function(e){e&&e.close()},i.prototype.unref=i.prototype.ref=function(){},i.prototype.close=function(){this._clearFn.call(r,this._id)},t.enroll=function(e,t){clearTimeout(e._idleTimeoutId),e._idleTimeout=t},t.unenroll=function(e){clearTimeout(e._idleTimeoutId),e._idleTimeout=-1},t._unrefActive=t.active=function(e){clearTimeout(e._idleTimeoutId);var t=e._idleTimeout;t>=0&&(e._idleTimeoutId=setTimeout(function(){e._onTimeout&&e._onTimeout()},t))},n(64),t.setImmediate="undefined"!=typeof self&&self.setImmediate||void 0!==e&&e.setImmediate||this&&this.setImmediate,t.clearImmediate="undefined"!=typeof self&&self.clearImmediate||void 0!==e&&e.clearImmediate||this&&this.clearImmediate}).call(this,n(10))},function(e,t,n){(function(e,t){!function(e,n){"use strict";if(!e.setImmediate){var r,o,i,a,s,c=1,u={},l=!1,f=e.document,h=Object.getPrototypeOf&&Object.getPrototypeOf(e);h=h&&h.setTimeout?h:e,"[object process]"==={}.toString.call(e.process)?r=function(e){t.nextTick(function(){d(e)})}:!function(){if(e.postMessage&&!e.importScripts){var t=!0,n=e.onmessage;return e.onmessage=function(){t=!1},e.postMessage("","*"),e.onmessage=n,t}}()?e.MessageChannel?((i=new MessageChannel).port1.onmessage=function(e){d(e.data)},r=function(e){i.port2.postMessage(e)}):f&&"onreadystatechange"in f.createElement("script")?(o=f.documentElement,r=function(e){var t=f.createElement("script");t.onreadystatechange=function(){d(e),t.onreadystatechange=null,o.removeChild(t),t=null},o.appendChild(t)}):r=function(e){setTimeout(d,0,e)}:(a="setImmediate$"+Math.random()+"$",s=function(t){t.source===e&&"string"==typeof t.data&&0===t.data.indexOf(a)&&d(+t.data.slice(a.length))},e.addEventListener?e.addEventListener("message",s,!1):e.attachEvent("onmessage",s),r=function(t){e.postMessage(a+t,"*")}),h.setImmediate=function(e){"function"!=typeof e&&(e=new Function(""+e));for(var t=new Array(arguments.length-1),n=0;n0?this._transform(null,t,n):n()},e.exports.decoder=c,e.exports.encoder=s},function(e,t,n){(t=e.exports=n(37)).Stream=t,t.Readable=t,t.Writable=n(42),t.Duplex=n(11),t.Transform=n(43),t.PassThrough=n(68)},function(e,t,n){"use strict";e.exports=i;var r=n(43),o=n(21);function i(e){if(!(this instanceof i))return new i(e);r.call(this,e)}o.inherits=n(17),o.inherits(i,r),i.prototype._transform=function(e,t,n){n(null,e)}},function(e,t,n){var r=n(22);function o(e){Error.call(this),Error.captureStackTrace&&Error.captureStackTrace(this,this.constructor),this.name=this.constructor.name,this.message=e||"unable to decode"}n(36).inherits(o,Error),e.exports=function(e){return function(e){e instanceof r||(e=r().append(e));var t=i(e);if(t)return e.consume(t.bytesConsumed),t.value;throw new o};function t(e,t,n){return t>=n+e}function n(e,t){return{value:e,bytesConsumed:t}}function i(e,r){r=void 0===r?0:r;var o=e.length-r;if(o<=0)return null;var i,l,f,h=e.readUInt8(r),p=0;if(!function(e,t){var n=function(e){switch(e){case 196:return 2;case 197:return 3;case 198:return 5;case 199:return 3;case 200:return 4;case 201:return 6;case 202:return 5;case 203:return 9;case 204:return 2;case 205:return 3;case 206:return 5;case 207:return 9;case 208:return 2;case 209:return 3;case 210:return 5;case 211:return 9;case 212:return 3;case 213:return 4;case 214:return 6;case 215:return 10;case 216:return 18;case 217:return 2;case 218:return 3;case 219:return 5;case 222:return 3;default:return-1}}(e);return!(-1!==n&&t=0;f--)p+=e.readUInt8(r+f+1)*Math.pow(2,8*(7-f));return n(p,9);case 208:return n(p=e.readInt8(r+1),2);case 209:return n(p=e.readInt16BE(r+1),3);case 210:return n(p=e.readInt32BE(r+1),5);case 211:return n(p=function(e,t){var n=128==(128&e[t]);if(n)for(var r=1,o=t+7;o>=t;o--){var i=(255^e[o])+r;e[o]=255&i,r=i>>8}var a=e.readUInt32BE(t+0),s=e.readUInt32BE(t+4);return(4294967296*a+s)*(n?-1:1)}(e.slice(r+1,r+9),0),9);case 202:return n(p=e.readFloatBE(r+1),5);case 203:return n(p=e.readDoubleBE(r+1),9);case 217:return t(i=e.readUInt8(r+1),o,2)?n(p=e.toString("utf8",r+2,r+2+i),2+i):null;case 218:return t(i=e.readUInt16BE(r+1),o,3)?n(p=e.toString("utf8",r+3,r+3+i),3+i):null;case 219:return t(i=e.readUInt32BE(r+1),o,5)?n(p=e.toString("utf8",r+5,r+5+i),5+i):null;case 196:return t(i=e.readUInt8(r+1),o,2)?n(p=e.slice(r+2,r+2+i),2+i):null;case 197:return t(i=e.readUInt16BE(r+1),o,3)?n(p=e.slice(r+3,r+3+i),3+i):null;case 198:return t(i=e.readUInt32BE(r+1),o,5)?n(p=e.slice(r+5,r+5+i),5+i):null;case 220:return o<3?null:(i=e.readUInt16BE(r+1),a(e,r,i,3));case 221:return o<5?null:(i=e.readUInt32BE(r+1),a(e,r,i,5));case 222:return i=e.readUInt16BE(r+1),s(e,r,i,3);case 223:throw new Error("map too big to decode in JS");case 212:return c(e,r,1);case 213:return c(e,r,2);case 214:return c(e,r,4);case 215:return c(e,r,8);case 216:return c(e,r,16);case 199:return i=e.readUInt8(r+1),l=e.readUInt8(r+2),t(i,o,3)?u(e,r,l,i,3):null;case 200:return i=e.readUInt16BE(r+1),l=e.readUInt8(r+3),t(i,o,4)?u(e,r,l,i,4):null;case 201:return i=e.readUInt32BE(r+1),l=e.readUInt8(r+5),t(i,o,6)?u(e,r,l,i,6):null}if(144==(240&h))return a(e,r,i=15&h,1);if(128==(240&h))return s(e,r,i=15&h,1);if(160==(224&h))return t(i=31&h,o,1)?n(p=e.toString("utf8",r+1,r+i+1),i+1):null;if(h>=224)return n(p=h-256,1);if(h<128)return n(h,1);throw new Error("not implemented yet")}function a(e,t,r,o){var a,s=[],c=0;for(t+=o,a=0;ai)&&((n=r.allocUnsafe(9))[0]=203,n.writeDoubleBE(e,1)),n}e.exports=function(e,t,n,i){function s(c,u){var l,f,h;if(void 0===c)throw new Error("undefined is not encodable in msgpack!");if(null===c)(l=r.allocUnsafe(1))[0]=192;else if(!0===c)(l=r.allocUnsafe(1))[0]=195;else if(!1===c)(l=r.allocUnsafe(1))[0]=194;else if("string"==typeof c)(f=r.byteLength(c))<32?((l=r.allocUnsafe(1+f))[0]=160|f,f>0&&l.write(c,1)):f<=255&&!n?((l=r.allocUnsafe(2+f))[0]=217,l[1]=f,l.write(c,2)):f<=65535?((l=r.allocUnsafe(3+f))[0]=218,l.writeUInt16BE(f,1),l.write(c,3)):((l=r.allocUnsafe(5+f))[0]=219,l.writeUInt32BE(f,1),l.write(c,5));else if(c&&(c.readUInt32LE||c instanceof Uint8Array))c instanceof Uint8Array&&(c=r.from(c)),c.length<=255?((l=r.allocUnsafe(2))[0]=196,l[1]=c.length):c.length<=65535?((l=r.allocUnsafe(3))[0]=197,l.writeUInt16BE(c.length,1)):((l=r.allocUnsafe(5))[0]=198,l.writeUInt32BE(c.length,1)),l=o([l,c]);else if(Array.isArray(c))c.length<16?(l=r.allocUnsafe(1))[0]=144|c.length:c.length<65536?((l=r.allocUnsafe(3))[0]=220,l.writeUInt16BE(c.length,1)):((l=r.allocUnsafe(5))[0]=221,l.writeUInt32BE(c.length,1)),l=c.reduce(function(e,t){return e.append(s(t,!0)),e},o().append(l));else{if(!i&&"function"==typeof c.getDate)return function(e){var t,n=1*e,i=Math.floor(n/1e3),a=1e6*(n-1e3*i);if(a||i>4294967295){(t=new r(10))[0]=215,t[1]=-1;var s=4*a,c=i/Math.pow(2,32),u=s+c&4294967295,l=4294967295&i;t.writeInt32BE(u,2),t.writeInt32BE(l,6)}else(t=new r(6))[0]=214,t[1]=-1,t.writeUInt32BE(Math.floor(n/1e3),2);return o().append(t)}(c);if("object"==typeof c)l=function(t){var n,i,a=-1,s=[];for(n=0;n>8),s.push(255&a)):(s.push(201),s.push(a>>24),s.push(a>>16&255),s.push(a>>8&255),s.push(255&a));return o().append(r.from(s)).append(i)}(c)||function(e){var t,n,i=[],a=0;for(t in e)e.hasOwnProperty(t)&&void 0!==e[t]&&"function"!=typeof e[t]&&(++a,i.push(s(t,!0)),i.push(s(e[t],!0)));a<16?(n=r.allocUnsafe(1))[0]=128|a:((n=r.allocUnsafe(3))[0]=222,n.writeUInt16BE(a,1));return i.unshift(n),i.reduce(function(e,t){return e.append(t)},o())}(c);else if("number"==typeof c){if((h=c)!==Math.floor(h))return a(c,t);if(c>=0)if(c<128)(l=r.allocUnsafe(1))[0]=c;else if(c<256)(l=r.allocUnsafe(2))[0]=204,l[1]=c;else if(c<65536)(l=r.allocUnsafe(3))[0]=205,l.writeUInt16BE(c,1);else if(c<=4294967295)(l=r.allocUnsafe(5))[0]=206,l.writeUInt32BE(c,1);else{if(!(c<=9007199254740991))return a(c,!0);(l=r.allocUnsafe(9))[0]=207,function(e,t){for(var n=7;n>=0;n--)e[n+1]=255&t,t/=256}(l,c)}else if(c>=-32)(l=r.allocUnsafe(1))[0]=256+c;else if(c>=-128)(l=r.allocUnsafe(2))[0]=208,l.writeInt8(c,1);else if(c>=-32768)(l=r.allocUnsafe(3))[0]=209,l.writeInt16BE(c,1);else if(c>-214748365)(l=r.allocUnsafe(5))[0]=210,l.writeInt32BE(c,1);else{if(!(c>=-9007199254740991))return a(c,!0);(l=r.allocUnsafe(9))[0]=211,function(e,t,n){var r=n<0;r&&(n=Math.abs(n));var o=n%4294967296,i=n/4294967296;if(e.writeUInt32BE(Math.floor(i),t+0),e.writeUInt32BE(o,t+4),r)for(var a=1,s=t+7;s>=t;s--){var c=(255^e[s])+a;e[s]=255&c,a=c>>8}}(l,1,c)}}}if(!l)throw new Error("not implemented yet");return u?l:l.slice()}return s}},function(e,t,n){"use strict";var r=this&&this.__awaiter||function(e,t,n,r){return new(n||(n=Promise))(function(o,i){function a(e){try{c(r.next(e))}catch(e){i(e)}}function s(e){try{c(r.throw(e))}catch(e){i(e)}}function c(e){e.done?o(e.value):new n(function(t){t(e.value)}).then(a,s)}c((r=r.apply(e,t||[])).next())})},o=this&&this.__generator||function(e,t){var n,r,o,i,a={label:0,sent:function(){if(1&o[0])throw o[1];return o[1]},trys:[],ops:[]};return i={next:s(0),throw:s(1),return:s(2)},"function"==typeof Symbol&&(i[Symbol.iterator]=function(){return this}),i;function s(i){return function(s){return function(i){if(n)throw new TypeError("Generator is already executing.");for(;a;)try{if(n=1,r&&(o=2&i[0]?r.return:i[0]?r.throw||((o=r.return)&&o.call(r),0):r.next)&&!(o=o.call(r,i[1])).done)return o;switch(r=0,o&&(i=[2&i[0],o.value]),i[0]){case 0:case 1:o=i;break;case 4:return a.label++,{value:i[1],done:!1};case 5:a.label++,r=i[1],i=[0];continue;case 7:i=a.ops.pop(),a.trys.pop();continue;default:if(!(o=(o=a.trys).length>0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]this.nextBatchId?this.fatalError?(this.logger.log(s.LogLevel.Debug,"Received a new batch "+e+" but errored out on a previous batch "+(this.nextBatchId-1)),[4,n.send("OnRenderCompleted",this.nextBatchId-1,this.fatalError.toString())]):[3,4]:[3,5];case 3:return o.sent(),[2];case 4:return this.logger.log(s.LogLevel.Debug,"Waiting for batch "+this.nextBatchId+". Batch "+e+" not processed."),[2];case 5:return o.trys.push([5,7,,8]),this.nextBatchId++,this.logger.log(s.LogLevel.Debug,"Applying batch "+e+"."),i.renderBatch(this.browserRendererId,new a.OutOfProcessRenderBatch(t)),[4,this.completeBatch(n,e)];case 6:return o.sent(),[3,8];case 7:throw r=o.sent(),this.fatalError=r.toString(),this.logger.log(s.LogLevel.Error,"There was an error applying batch "+e+"."),n.send("OnRenderCompleted",e,r.toString()),r;case 8:return[2]}})})},e.prototype.getLastBatchid=function(){return this.nextBatchId-1},e.prototype.completeBatch=function(e,t){return r(this,void 0,void 0,function(){return o(this,function(n){switch(n.label){case 0:return n.trys.push([0,2,,3]),[4,e.send("OnRenderCompleted",t,null)];case 1:return n.sent(),[3,3];case 2:return n.sent(),this.logger.log(s.LogLevel.Warning,"Failed to deliver completion notification for render '"+t+"'."),[3,3];case 3:return[2]}})})},e}();t.RenderQueue=c},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(73),o=Math.pow(2,32),i=Math.pow(2,21)-1,a=function(){function e(e){this.batchData=e;var t=new l(e);this.arrayRangeReader=new f(e),this.arrayBuilderSegmentReader=new h(e),this.diffReader=new s(e),this.editReader=new c(e,t),this.frameReader=new u(e,t)}return e.prototype.updatedComponents=function(){return p(this.batchData,this.batchData.length-20)},e.prototype.referenceFrames=function(){return p(this.batchData,this.batchData.length-16)},e.prototype.disposedComponentIds=function(){return p(this.batchData,this.batchData.length-12)},e.prototype.disposedEventHandlerIds=function(){return p(this.batchData,this.batchData.length-8)},e.prototype.updatedComponentsEntry=function(e,t){var n=e+4*t;return p(this.batchData,n)},e.prototype.referenceFramesEntry=function(e,t){return e+20*t},e.prototype.disposedComponentIdsEntry=function(e,t){var n=e+4*t;return p(this.batchData,n)},e.prototype.disposedEventHandlerIdsEntry=function(e,t){var n=e+8*t;return g(this.batchData,n)},e}();t.OutOfProcessRenderBatch=a;var s=function(){function e(e){this.batchDataUint8=e}return e.prototype.componentId=function(e){return p(this.batchDataUint8,e)},e.prototype.edits=function(e){return e+4},e.prototype.editsEntry=function(e,t){return e+16*t},e}(),c=function(){function e(e,t){this.batchDataUint8=e,this.stringReader=t}return e.prototype.editType=function(e){return p(this.batchDataUint8,e)},e.prototype.siblingIndex=function(e){return p(this.batchDataUint8,e+4)},e.prototype.newTreeIndex=function(e){return p(this.batchDataUint8,e+8)},e.prototype.moveToSiblingIndex=function(e){return p(this.batchDataUint8,e+8)},e.prototype.removedAttributeName=function(e){var t=p(this.batchDataUint8,e+12);return this.stringReader.readString(t)},e}(),u=function(){function e(e,t){this.batchDataUint8=e,this.stringReader=t}return e.prototype.frameType=function(e){return p(this.batchDataUint8,e)},e.prototype.subtreeLength=function(e){return p(this.batchDataUint8,e+4)},e.prototype.elementReferenceCaptureId=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.componentId=function(e){return p(this.batchDataUint8,e+8)},e.prototype.elementName=function(e){var t=p(this.batchDataUint8,e+8);return this.stringReader.readString(t)},e.prototype.textContent=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.markupContent=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.attributeName=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.attributeValue=function(e){var t=p(this.batchDataUint8,e+8);return this.stringReader.readString(t)},e.prototype.attributeEventHandlerId=function(e){return g(this.batchDataUint8,e+12)},e}(),l=function(){function e(e){this.batchDataUint8=e,this.stringTableStartIndex=p(e,e.length-4)}return e.prototype.readString=function(e){if(-1===e)return null;var t,n=p(this.batchDataUint8,this.stringTableStartIndex+4*e),o=function(e,t){for(var n=0,r=0,o=0;o<4;o++){var i=e[t+o];if(n|=(127&i)<>>0)}function g(e,t){var n=d(e,t+4);if(n>i)throw new Error("Cannot read uint64 with high order part "+n+", because the result would exceed Number.MAX_SAFE_INTEGER.");return n*o+d(e,t)}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r="function"==typeof TextDecoder?new TextDecoder("utf-8"):null;t.decodeUtf8=r?r.decode.bind(r):function(e){var t=0,n=e.length,r=[],o=[];for(;t65535&&(u-=65536,r.push(u>>>10&1023|55296),u=56320|1023&u),r.push(u)}r.length>1024&&(o.push(String.fromCharCode.apply(null,r)),r.length=0)}return o.push(String.fromCharCode.apply(null,r)),o.join("")}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(18),o=function(){function e(){}return e.prototype.log=function(e,t){},e.instance=new e,e}();t.NullLogger=o;var i=function(){function e(e){this.minimumLogLevel=e}return e.prototype.log=function(e,t){if(e>=this.minimumLogLevel)switch(e){case r.LogLevel.Critical:case r.LogLevel.Error:console.error("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t);break;case r.LogLevel.Warning:console.warn("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t);break;case r.LogLevel.Information:console.info("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t);break;default:console.log("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t)}},e}();t.ConsoleLogger=i},function(e,t,n){"use strict";var r=this&&this.__awaiter||function(e,t,n,r){return new(n||(n=Promise))(function(o,i){function a(e){try{c(r.next(e))}catch(e){i(e)}}function s(e){try{c(r.throw(e))}catch(e){i(e)}}function c(e){e.done?o(e.value):new n(function(t){t(e.value)}).then(a,s)}c((r=r.apply(e,t||[])).next())})},o=this&&this.__generator||function(e,t){var n,r,o,i,a={label:0,sent:function(){if(1&o[0])throw o[1];return o[1]},trys:[],ops:[]};return i={next:s(0),throw:s(1),return:s(2)},"function"==typeof Symbol&&(i[Symbol.iterator]=function(){return this}),i;function s(i){return function(s){return function(i){if(n)throw new TypeError("Generator is already executing.");for(;a;)try{if(n=1,r&&(o=2&i[0]?r.return:i[0]?r.throw||((o=r.return)&&o.call(r),0):r.next)&&!(o=o.call(r,i[1])).done)return o;switch(r=0,o&&(i=[2&i[0],o.value]),i[0]){case 0:case 1:o=i;break;case 4:return a.label++,{value:i[1],done:!1};case 5:a.label++,r=i[1],i=[0];continue;case 7:i=a.ops.pop(),a.trys.pop();continue;default:if(!(o=(o=a.trys).length>0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]reloading the page if you're unable to reconnect.",this.message.querySelector("a").addEventListener("click",function(){return location.reload()})},e.prototype.rejected=function(){this.button.style.display="none",this.reloadParagraph.style.display="none",this.message.innerHTML="Could not reconnect to the server. Reload the page to restore functionality.",this.message.querySelector("a").addEventListener("click",function(){return location.reload()})},e}();t.DefaultReconnectDisplay=a},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=function(){function e(e){this.dialog=e}return e.prototype.show=function(){this.removeClasses(),this.dialog.classList.add(e.ShowClassName)},e.prototype.hide=function(){this.removeClasses(),this.dialog.classList.add(e.HideClassName)},e.prototype.failed=function(){this.removeClasses(),this.dialog.classList.add(e.FailedClassName)},e.prototype.rejected=function(){this.removeClasses(),this.dialog.classList.add(e.RejectedClassName)},e.prototype.removeClasses=function(){this.dialog.classList.remove(e.ShowClassName,e.HideClassName,e.FailedClassName,e.RejectedClassName)},e.ShowClassName="components-reconnect-show",e.HideClassName="components-reconnect-hide",e.FailedClassName="components-reconnect-failed",e.RejectedClassName="components-reconnect-rejected",e}();t.UserSpecifiedDisplay=r},function(e,t,n){"use strict";n.r(t);var r=n(6),o=n(12),i=n(2),a=function(){function e(){}return e.write=function(e){var t=e.byteLength||e.length,n=[];do{var r=127&t;(t>>=7)>0&&(r|=128),n.push(r)}while(t>0);t=e.byteLength||e.length;var o=new Uint8Array(n.length+t);return o.set(n,0),o.set(e,n.length),o.buffer},e.parse=function(e){for(var t=[],n=new Uint8Array(e),r=[0,7,14,21,28],o=0;o7)throw new Error("Messages bigger than 2GB are not supported.");if(!(n.byteLength>=o+i+a))throw new Error("Incomplete message.");t.push(n.slice?n.slice(o+i,o+i+a):n.subarray(o+i,o+i+a)),o=o+i+a}return t},e}();var s=new Uint8Array([145,i.MessageType.Ping]),c=function(){function e(){this.name="messagepack",this.version=1,this.transferFormat=i.TransferFormat.Binary,this.errorResult=1,this.voidResult=2,this.nonVoidResult=3}return e.prototype.parseMessages=function(e,t){if(!(e instanceof r.Buffer||(n=e,n&&"undefined"!=typeof ArrayBuffer&&(n instanceof ArrayBuffer||n.constructor&&"ArrayBuffer"===n.constructor.name))))throw new Error("Invalid input for MessagePack hub protocol. Expected an ArrayBuffer or Buffer.");var n;null===t&&(t=i.NullLogger.instance);for(var o=[],s=0,c=a.parse(e);s=0;u--)if(l[u]!==f[u])return!1;for(u=l.length-1;u>=0;u--)if(c=l[u],!b(e[c],t[c],n,r))return!1;return!0}(e,t,n,a))}return n?e===t:e==t}function m(e){return"[object Arguments]"==Object.prototype.toString.call(e)}function w(e,t){if(!e||!t)return!1;if("[object RegExp]"==Object.prototype.toString.call(t))return t.test(e);try{if(e instanceof t)return!0}catch(e){}return!Error.isPrototypeOf(t)&&!0===t.call({},e)}function E(e,t,n,r){var o;if("function"!=typeof t)throw new TypeError('"block" argument must be a function');"string"==typeof n&&(r=n,n=null),o=function(e){var t;try{e()}catch(e){t=e}return t}(t),r=(n&&n.name?" ("+n.name+").":".")+(r?" "+r:"."),e&&!o&&y(o,n,"Missing expected exception"+r);var a="string"==typeof r,s=!e&&o&&!n;if((!e&&i.isError(o)&&a&&w(o,n)||s)&&y(o,n,"Got unwanted exception"+r),e&&o&&n&&!w(o,n)||!e&&o)throw o}f.AssertionError=function(e){var t;this.name="AssertionError",this.actual=e.actual,this.expected=e.expected,this.operator=e.operator,e.message?(this.message=e.message,this.generatedMessage=!1):(this.message=d(g((t=this).actual),128)+" "+t.operator+" "+d(g(t.expected),128),this.generatedMessage=!0);var n=e.stackStartFunction||y;if(Error.captureStackTrace)Error.captureStackTrace(this,n);else{var r=new Error;if(r.stack){var o=r.stack,i=p(n),a=o.indexOf("\n"+i);if(a>=0){var s=o.indexOf("\n",a+1);o=o.substring(s+1)}this.stack=o}}},i.inherits(f.AssertionError,Error),f.fail=y,f.ok=v,f.equal=function(e,t,n){e!=t&&y(e,t,n,"==",f.equal)},f.notEqual=function(e,t,n){e==t&&y(e,t,n,"!=",f.notEqual)},f.deepEqual=function(e,t,n){b(e,t,!1)||y(e,t,n,"deepEqual",f.deepEqual)},f.deepStrictEqual=function(e,t,n){b(e,t,!0)||y(e,t,n,"deepStrictEqual",f.deepStrictEqual)},f.notDeepEqual=function(e,t,n){b(e,t,!1)&&y(e,t,n,"notDeepEqual",f.notDeepEqual)},f.notDeepStrictEqual=function e(t,n,r){b(t,n,!0)&&y(t,n,r,"notDeepStrictEqual",e)},f.strictEqual=function(e,t,n){e!==t&&y(e,t,n,"===",f.strictEqual)},f.notStrictEqual=function(e,t,n){e===t&&y(e,t,n,"!==",f.notStrictEqual)},f.throws=function(e,t,n){E(!0,e,t,n)},f.doesNotThrow=function(e,t,n){E(!1,e,t,n)},f.ifError=function(e){if(e)throw e};var S=Object.keys||function(e){var t=[];for(var n in e)a.call(e,n)&&t.push(n);return t}}).call(this,n(10))},function(e,t){e.exports=function(e){return e&&"object"==typeof e&&"function"==typeof e.copy&&"function"==typeof e.fill&&"function"==typeof e.readUInt8}},function(e,t){"function"==typeof Object.create?e.exports=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})}:e.exports=function(e,t){e.super_=t;var n=function(){};n.prototype=t.prototype,e.prototype=new n,e.prototype.constructor=e}},function(e,t,n){e.exports=n(11)},function(e,t){var n={}.toString;e.exports=Array.isArray||function(e){return"[object Array]"==n.call(e)}},function(e,t){},function(e,t,n){"use strict";var r=n(16).Buffer,o=n(61);e.exports=function(){function e(){!function(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}(this,e),this.head=null,this.tail=null,this.length=0}return e.prototype.push=function(e){var t={data:e,next:null};this.length>0?this.tail.next=t:this.head=t,this.tail=t,++this.length},e.prototype.unshift=function(e){var t={data:e,next:this.head};0===this.length&&(this.tail=t),this.head=t,++this.length},e.prototype.shift=function(){if(0!==this.length){var e=this.head.data;return 1===this.length?this.head=this.tail=null:this.head=this.head.next,--this.length,e}},e.prototype.clear=function(){this.head=this.tail=null,this.length=0},e.prototype.join=function(e){if(0===this.length)return"";for(var t=this.head,n=""+t.data;t=t.next;)n+=e+t.data;return n},e.prototype.concat=function(e){if(0===this.length)return r.alloc(0);if(1===this.length)return this.head.data;for(var t,n,o,i=r.allocUnsafe(e>>>0),a=this.head,s=0;a;)t=a.data,n=i,o=s,t.copy(n,o),s+=a.data.length,a=a.next;return i},e}(),o&&o.inspect&&o.inspect.custom&&(e.exports.prototype[o.inspect.custom]=function(){var e=o.inspect({length:this.length});return this.constructor.name+" "+e})},function(e,t){},function(e,t,n){var r=n(6),o=r.Buffer;function i(e,t){for(var n in e)t[n]=e[n]}function a(e,t,n){return o(e,t,n)}o.from&&o.alloc&&o.allocUnsafe&&o.allocUnsafeSlow?e.exports=r:(i(r,t),t.Buffer=a),i(o,a),a.from=function(e,t,n){if("number"==typeof e)throw new TypeError("Argument must not be a number");return o(e,t,n)},a.alloc=function(e,t,n){if("number"!=typeof e)throw new TypeError("Argument must be a number");var r=o(e);return void 0!==t?"string"==typeof n?r.fill(t,n):r.fill(t):r.fill(0),r},a.allocUnsafe=function(e){if("number"!=typeof e)throw new TypeError("Argument must be a number");return o(e)},a.allocUnsafeSlow=function(e){if("number"!=typeof e)throw new TypeError("Argument must be a number");return r.SlowBuffer(e)}},function(e,t,n){(function(e){var r=void 0!==e&&e||"undefined"!=typeof self&&self||window,o=Function.prototype.apply;function i(e,t){this._id=e,this._clearFn=t}t.setTimeout=function(){return new i(o.call(setTimeout,r,arguments),clearTimeout)},t.setInterval=function(){return new i(o.call(setInterval,r,arguments),clearInterval)},t.clearTimeout=t.clearInterval=function(e){e&&e.close()},i.prototype.unref=i.prototype.ref=function(){},i.prototype.close=function(){this._clearFn.call(r,this._id)},t.enroll=function(e,t){clearTimeout(e._idleTimeoutId),e._idleTimeout=t},t.unenroll=function(e){clearTimeout(e._idleTimeoutId),e._idleTimeout=-1},t._unrefActive=t.active=function(e){clearTimeout(e._idleTimeoutId);var t=e._idleTimeout;t>=0&&(e._idleTimeoutId=setTimeout(function(){e._onTimeout&&e._onTimeout()},t))},n(64),t.setImmediate="undefined"!=typeof self&&self.setImmediate||void 0!==e&&e.setImmediate||this&&this.setImmediate,t.clearImmediate="undefined"!=typeof self&&self.clearImmediate||void 0!==e&&e.clearImmediate||this&&this.clearImmediate}).call(this,n(10))},function(e,t,n){(function(e,t){!function(e,n){"use strict";if(!e.setImmediate){var r,o,i,a,s,c=1,u={},l=!1,f=e.document,h=Object.getPrototypeOf&&Object.getPrototypeOf(e);h=h&&h.setTimeout?h:e,"[object process]"==={}.toString.call(e.process)?r=function(e){t.nextTick(function(){d(e)})}:!function(){if(e.postMessage&&!e.importScripts){var t=!0,n=e.onmessage;return e.onmessage=function(){t=!1},e.postMessage("","*"),e.onmessage=n,t}}()?e.MessageChannel?((i=new MessageChannel).port1.onmessage=function(e){d(e.data)},r=function(e){i.port2.postMessage(e)}):f&&"onreadystatechange"in f.createElement("script")?(o=f.documentElement,r=function(e){var t=f.createElement("script");t.onreadystatechange=function(){d(e),t.onreadystatechange=null,o.removeChild(t),t=null},o.appendChild(t)}):r=function(e){setTimeout(d,0,e)}:(a="setImmediate$"+Math.random()+"$",s=function(t){t.source===e&&"string"==typeof t.data&&0===t.data.indexOf(a)&&d(+t.data.slice(a.length))},e.addEventListener?e.addEventListener("message",s,!1):e.attachEvent("onmessage",s),r=function(t){e.postMessage(a+t,"*")}),h.setImmediate=function(e){"function"!=typeof e&&(e=new Function(""+e));for(var t=new Array(arguments.length-1),n=0;n0?this._transform(null,t,n):n()},e.exports.decoder=c,e.exports.encoder=s},function(e,t,n){(t=e.exports=n(37)).Stream=t,t.Readable=t,t.Writable=n(42),t.Duplex=n(11),t.Transform=n(43),t.PassThrough=n(68)},function(e,t,n){"use strict";e.exports=i;var r=n(43),o=n(21);function i(e){if(!(this instanceof i))return new i(e);r.call(this,e)}o.inherits=n(17),o.inherits(i,r),i.prototype._transform=function(e,t,n){n(null,e)}},function(e,t,n){var r=n(22);function o(e){Error.call(this),Error.captureStackTrace&&Error.captureStackTrace(this,this.constructor),this.name=this.constructor.name,this.message=e||"unable to decode"}n(36).inherits(o,Error),e.exports=function(e){return function(e){e instanceof r||(e=r().append(e));var t=i(e);if(t)return e.consume(t.bytesConsumed),t.value;throw new o};function t(e,t,n){return t>=n+e}function n(e,t){return{value:e,bytesConsumed:t}}function i(e,r){r=void 0===r?0:r;var o=e.length-r;if(o<=0)return null;var i,l,f,h=e.readUInt8(r),p=0;if(!function(e,t){var n=function(e){switch(e){case 196:return 2;case 197:return 3;case 198:return 5;case 199:return 3;case 200:return 4;case 201:return 6;case 202:return 5;case 203:return 9;case 204:return 2;case 205:return 3;case 206:return 5;case 207:return 9;case 208:return 2;case 209:return 3;case 210:return 5;case 211:return 9;case 212:return 3;case 213:return 4;case 214:return 6;case 215:return 10;case 216:return 18;case 217:return 2;case 218:return 3;case 219:return 5;case 222:return 3;default:return-1}}(e);return!(-1!==n&&t=0;f--)p+=e.readUInt8(r+f+1)*Math.pow(2,8*(7-f));return n(p,9);case 208:return n(p=e.readInt8(r+1),2);case 209:return n(p=e.readInt16BE(r+1),3);case 210:return n(p=e.readInt32BE(r+1),5);case 211:return n(p=function(e,t){var n=128==(128&e[t]);if(n)for(var r=1,o=t+7;o>=t;o--){var i=(255^e[o])+r;e[o]=255&i,r=i>>8}var a=e.readUInt32BE(t+0),s=e.readUInt32BE(t+4);return(4294967296*a+s)*(n?-1:1)}(e.slice(r+1,r+9),0),9);case 202:return n(p=e.readFloatBE(r+1),5);case 203:return n(p=e.readDoubleBE(r+1),9);case 217:return t(i=e.readUInt8(r+1),o,2)?n(p=e.toString("utf8",r+2,r+2+i),2+i):null;case 218:return t(i=e.readUInt16BE(r+1),o,3)?n(p=e.toString("utf8",r+3,r+3+i),3+i):null;case 219:return t(i=e.readUInt32BE(r+1),o,5)?n(p=e.toString("utf8",r+5,r+5+i),5+i):null;case 196:return t(i=e.readUInt8(r+1),o,2)?n(p=e.slice(r+2,r+2+i),2+i):null;case 197:return t(i=e.readUInt16BE(r+1),o,3)?n(p=e.slice(r+3,r+3+i),3+i):null;case 198:return t(i=e.readUInt32BE(r+1),o,5)?n(p=e.slice(r+5,r+5+i),5+i):null;case 220:return o<3?null:(i=e.readUInt16BE(r+1),a(e,r,i,3));case 221:return o<5?null:(i=e.readUInt32BE(r+1),a(e,r,i,5));case 222:return i=e.readUInt16BE(r+1),s(e,r,i,3);case 223:throw new Error("map too big to decode in JS");case 212:return c(e,r,1);case 213:return c(e,r,2);case 214:return c(e,r,4);case 215:return c(e,r,8);case 216:return c(e,r,16);case 199:return i=e.readUInt8(r+1),l=e.readUInt8(r+2),t(i,o,3)?u(e,r,l,i,3):null;case 200:return i=e.readUInt16BE(r+1),l=e.readUInt8(r+3),t(i,o,4)?u(e,r,l,i,4):null;case 201:return i=e.readUInt32BE(r+1),l=e.readUInt8(r+5),t(i,o,6)?u(e,r,l,i,6):null}if(144==(240&h))return a(e,r,i=15&h,1);if(128==(240&h))return s(e,r,i=15&h,1);if(160==(224&h))return t(i=31&h,o,1)?n(p=e.toString("utf8",r+1,r+i+1),i+1):null;if(h>=224)return n(p=h-256,1);if(h<128)return n(h,1);throw new Error("not implemented yet")}function a(e,t,r,o){var a,s=[],c=0;for(t+=o,a=0;ai)&&((n=r.allocUnsafe(9))[0]=203,n.writeDoubleBE(e,1)),n}e.exports=function(e,t,n,i){function s(c,u){var l,f,h;if(void 0===c)throw new Error("undefined is not encodable in msgpack!");if(null===c)(l=r.allocUnsafe(1))[0]=192;else if(!0===c)(l=r.allocUnsafe(1))[0]=195;else if(!1===c)(l=r.allocUnsafe(1))[0]=194;else if("string"==typeof c)(f=r.byteLength(c))<32?((l=r.allocUnsafe(1+f))[0]=160|f,f>0&&l.write(c,1)):f<=255&&!n?((l=r.allocUnsafe(2+f))[0]=217,l[1]=f,l.write(c,2)):f<=65535?((l=r.allocUnsafe(3+f))[0]=218,l.writeUInt16BE(f,1),l.write(c,3)):((l=r.allocUnsafe(5+f))[0]=219,l.writeUInt32BE(f,1),l.write(c,5));else if(c&&(c.readUInt32LE||c instanceof Uint8Array))c instanceof Uint8Array&&(c=r.from(c)),c.length<=255?((l=r.allocUnsafe(2))[0]=196,l[1]=c.length):c.length<=65535?((l=r.allocUnsafe(3))[0]=197,l.writeUInt16BE(c.length,1)):((l=r.allocUnsafe(5))[0]=198,l.writeUInt32BE(c.length,1)),l=o([l,c]);else if(Array.isArray(c))c.length<16?(l=r.allocUnsafe(1))[0]=144|c.length:c.length<65536?((l=r.allocUnsafe(3))[0]=220,l.writeUInt16BE(c.length,1)):((l=r.allocUnsafe(5))[0]=221,l.writeUInt32BE(c.length,1)),l=c.reduce(function(e,t){return e.append(s(t,!0)),e},o().append(l));else{if(!i&&"function"==typeof c.getDate)return function(e){var t,n=1*e,i=Math.floor(n/1e3),a=1e6*(n-1e3*i);if(a||i>4294967295){(t=new r(10))[0]=215,t[1]=-1;var s=4*a,c=i/Math.pow(2,32),u=s+c&4294967295,l=4294967295&i;t.writeInt32BE(u,2),t.writeInt32BE(l,6)}else(t=new r(6))[0]=214,t[1]=-1,t.writeUInt32BE(Math.floor(n/1e3),2);return o().append(t)}(c);if("object"==typeof c)l=function(t){var n,i,a=-1,s=[];for(n=0;n>8),s.push(255&a)):(s.push(201),s.push(a>>24),s.push(a>>16&255),s.push(a>>8&255),s.push(255&a));return o().append(r.from(s)).append(i)}(c)||function(e){var t,n,i=[],a=0;for(t in e)e.hasOwnProperty(t)&&void 0!==e[t]&&"function"!=typeof e[t]&&(++a,i.push(s(t,!0)),i.push(s(e[t],!0)));a<16?(n=r.allocUnsafe(1))[0]=128|a:((n=r.allocUnsafe(3))[0]=222,n.writeUInt16BE(a,1));return i.unshift(n),i.reduce(function(e,t){return e.append(t)},o())}(c);else if("number"==typeof c){if((h=c)!==Math.floor(h))return a(c,t);if(c>=0)if(c<128)(l=r.allocUnsafe(1))[0]=c;else if(c<256)(l=r.allocUnsafe(2))[0]=204,l[1]=c;else if(c<65536)(l=r.allocUnsafe(3))[0]=205,l.writeUInt16BE(c,1);else if(c<=4294967295)(l=r.allocUnsafe(5))[0]=206,l.writeUInt32BE(c,1);else{if(!(c<=9007199254740991))return a(c,!0);(l=r.allocUnsafe(9))[0]=207,function(e,t){for(var n=7;n>=0;n--)e[n+1]=255&t,t/=256}(l,c)}else if(c>=-32)(l=r.allocUnsafe(1))[0]=256+c;else if(c>=-128)(l=r.allocUnsafe(2))[0]=208,l.writeInt8(c,1);else if(c>=-32768)(l=r.allocUnsafe(3))[0]=209,l.writeInt16BE(c,1);else if(c>-214748365)(l=r.allocUnsafe(5))[0]=210,l.writeInt32BE(c,1);else{if(!(c>=-9007199254740991))return a(c,!0);(l=r.allocUnsafe(9))[0]=211,function(e,t,n){var r=n<0;r&&(n=Math.abs(n));var o=n%4294967296,i=n/4294967296;if(e.writeUInt32BE(Math.floor(i),t+0),e.writeUInt32BE(o,t+4),r)for(var a=1,s=t+7;s>=t;s--){var c=(255^e[s])+a;e[s]=255&c,a=c>>8}}(l,1,c)}}}if(!l)throw new Error("not implemented yet");return u?l:l.slice()}return s}},function(e,t,n){"use strict";var r=this&&this.__awaiter||function(e,t,n,r){return new(n||(n=Promise))(function(o,i){function a(e){try{c(r.next(e))}catch(e){i(e)}}function s(e){try{c(r.throw(e))}catch(e){i(e)}}function c(e){e.done?o(e.value):new n(function(t){t(e.value)}).then(a,s)}c((r=r.apply(e,t||[])).next())})},o=this&&this.__generator||function(e,t){var n,r,o,i,a={label:0,sent:function(){if(1&o[0])throw o[1];return o[1]},trys:[],ops:[]};return i={next:s(0),throw:s(1),return:s(2)},"function"==typeof Symbol&&(i[Symbol.iterator]=function(){return this}),i;function s(i){return function(s){return function(i){if(n)throw new TypeError("Generator is already executing.");for(;a;)try{if(n=1,r&&(o=2&i[0]?r.return:i[0]?r.throw||((o=r.return)&&o.call(r),0):r.next)&&!(o=o.call(r,i[1])).done)return o;switch(r=0,o&&(i=[2&i[0],o.value]),i[0]){case 0:case 1:o=i;break;case 4:return a.label++,{value:i[1],done:!1};case 5:a.label++,r=i[1],i=[0];continue;case 7:i=a.ops.pop(),a.trys.pop();continue;default:if(!(o=(o=a.trys).length>0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]this.nextBatchId?this.fatalError?(this.logger.log(s.LogLevel.Debug,"Received a new batch "+e+" but errored out on a previous batch "+(this.nextBatchId-1)),[4,n.send("OnRenderCompleted",this.nextBatchId-1,this.fatalError.toString())]):[3,4]:[3,5];case 3:return o.sent(),[2];case 4:return this.logger.log(s.LogLevel.Debug,"Waiting for batch "+this.nextBatchId+". Batch "+e+" not processed."),[2];case 5:return o.trys.push([5,7,,8]),this.nextBatchId++,this.logger.log(s.LogLevel.Debug,"Applying batch "+e+"."),i.renderBatch(this.browserRendererId,new a.OutOfProcessRenderBatch(t)),[4,this.completeBatch(n,e)];case 6:return o.sent(),[3,8];case 7:throw r=o.sent(),this.fatalError=r.toString(),this.logger.log(s.LogLevel.Error,"There was an error applying batch "+e+"."),n.send("OnRenderCompleted",e,r.toString()),r;case 8:return[2]}})})},e.prototype.getLastBatchid=function(){return this.nextBatchId-1},e.prototype.completeBatch=function(e,t){return r(this,void 0,void 0,function(){return o(this,function(n){switch(n.label){case 0:return n.trys.push([0,2,,3]),[4,e.send("OnRenderCompleted",t,null)];case 1:return n.sent(),[3,3];case 2:return n.sent(),this.logger.log(s.LogLevel.Warning,"Failed to deliver completion notification for render '"+t+"'."),[3,3];case 3:return[2]}})})},e}();t.RenderQueue=c},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(73),o=Math.pow(2,32),i=Math.pow(2,21)-1,a=function(){function e(e){this.batchData=e;var t=new l(e);this.arrayRangeReader=new f(e),this.arrayBuilderSegmentReader=new h(e),this.diffReader=new s(e),this.editReader=new c(e,t),this.frameReader=new u(e,t)}return e.prototype.updatedComponents=function(){return p(this.batchData,this.batchData.length-20)},e.prototype.referenceFrames=function(){return p(this.batchData,this.batchData.length-16)},e.prototype.disposedComponentIds=function(){return p(this.batchData,this.batchData.length-12)},e.prototype.disposedEventHandlerIds=function(){return p(this.batchData,this.batchData.length-8)},e.prototype.updatedComponentsEntry=function(e,t){var n=e+4*t;return p(this.batchData,n)},e.prototype.referenceFramesEntry=function(e,t){return e+20*t},e.prototype.disposedComponentIdsEntry=function(e,t){var n=e+4*t;return p(this.batchData,n)},e.prototype.disposedEventHandlerIdsEntry=function(e,t){var n=e+8*t;return g(this.batchData,n)},e}();t.OutOfProcessRenderBatch=a;var s=function(){function e(e){this.batchDataUint8=e}return e.prototype.componentId=function(e){return p(this.batchDataUint8,e)},e.prototype.edits=function(e){return e+4},e.prototype.editsEntry=function(e,t){return e+16*t},e}(),c=function(){function e(e,t){this.batchDataUint8=e,this.stringReader=t}return e.prototype.editType=function(e){return p(this.batchDataUint8,e)},e.prototype.siblingIndex=function(e){return p(this.batchDataUint8,e+4)},e.prototype.newTreeIndex=function(e){return p(this.batchDataUint8,e+8)},e.prototype.moveToSiblingIndex=function(e){return p(this.batchDataUint8,e+8)},e.prototype.removedAttributeName=function(e){var t=p(this.batchDataUint8,e+12);return this.stringReader.readString(t)},e}(),u=function(){function e(e,t){this.batchDataUint8=e,this.stringReader=t}return e.prototype.frameType=function(e){return p(this.batchDataUint8,e)},e.prototype.subtreeLength=function(e){return p(this.batchDataUint8,e+4)},e.prototype.elementReferenceCaptureId=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.componentId=function(e){return p(this.batchDataUint8,e+8)},e.prototype.elementName=function(e){var t=p(this.batchDataUint8,e+8);return this.stringReader.readString(t)},e.prototype.textContent=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.markupContent=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.attributeName=function(e){var t=p(this.batchDataUint8,e+4);return this.stringReader.readString(t)},e.prototype.attributeValue=function(e){var t=p(this.batchDataUint8,e+8);return this.stringReader.readString(t)},e.prototype.attributeEventHandlerId=function(e){return g(this.batchDataUint8,e+12)},e}(),l=function(){function e(e){this.batchDataUint8=e,this.stringTableStartIndex=p(e,e.length-4)}return e.prototype.readString=function(e){if(-1===e)return null;var t,n=p(this.batchDataUint8,this.stringTableStartIndex+4*e),o=function(e,t){for(var n=0,r=0,o=0;o<4;o++){var i=e[t+o];if(n|=(127&i)<>>0)}function g(e,t){var n=d(e,t+4);if(n>i)throw new Error("Cannot read uint64 with high order part "+n+", because the result would exceed Number.MAX_SAFE_INTEGER.");return n*o+d(e,t)}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r="function"==typeof TextDecoder?new TextDecoder("utf-8"):null;t.decodeUtf8=r?r.decode.bind(r):function(e){var t=0,n=e.length,r=[],o=[];for(;t65535&&(u-=65536,r.push(u>>>10&1023|55296),u=56320|1023&u),r.push(u)}r.length>1024&&(o.push(String.fromCharCode.apply(null,r)),r.length=0)}return o.push(String.fromCharCode.apply(null,r)),o.join("")}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(18),o=function(){function e(){}return e.prototype.log=function(e,t){},e.instance=new e,e}();t.NullLogger=o;var i=function(){function e(e){this.minimumLogLevel=e}return e.prototype.log=function(e,t){if(e>=this.minimumLogLevel)switch(e){case r.LogLevel.Critical:case r.LogLevel.Error:console.error("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t);break;case r.LogLevel.Warning:console.warn("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t);break;case r.LogLevel.Information:console.info("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t);break;default:console.log("["+(new Date).toISOString()+"] "+r.LogLevel[e]+": "+t)}},e}();t.ConsoleLogger=i},function(e,t,n){"use strict";var r=this&&this.__awaiter||function(e,t,n,r){return new(n||(n=Promise))(function(o,i){function a(e){try{c(r.next(e))}catch(e){i(e)}}function s(e){try{c(r.throw(e))}catch(e){i(e)}}function c(e){e.done?o(e.value):new n(function(t){t(e.value)}).then(a,s)}c((r=r.apply(e,t||[])).next())})},o=this&&this.__generator||function(e,t){var n,r,o,i,a={label:0,sent:function(){if(1&o[0])throw o[1];return o[1]},trys:[],ops:[]};return i={next:s(0),throw:s(1),return:s(2)},"function"==typeof Symbol&&(i[Symbol.iterator]=function(){return this}),i;function s(i){return function(s){return function(i){if(n)throw new TypeError("Generator is already executing.");for(;a;)try{if(n=1,r&&(o=2&i[0]?r.return:i[0]?r.throw||((o=r.return)&&o.call(r),0):r.next)&&!(o=o.call(r,i[1])).done)return o;switch(r=0,o&&(i=[2&i[0],o.value]),i[0]){case 0:case 1:o=i;break;case 4:return a.label++,{value:i[1],done:!1};case 5:a.label++,r=i[1],i=[0];continue;case 7:i=a.ops.pop(),a.trys.pop();continue;default:if(!(o=(o=a.trys).length>0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]0&&o[o.length-1])&&(6===i[0]||2===i[0])){a=0;continue}if(3===i[0]&&(!o||i[1]>o[0]&&i[1]reloading the page if you're unable to reconnect.",this.message.querySelector("a").addEventListener("click",function(){return location.reload()})},e.prototype.rejected=function(){this.button.style.display="none",this.reloadParagraph.style.display="none",this.message.innerHTML="Could not reconnect to the server. Reload the page to restore functionality.",this.message.querySelector("a").addEventListener("click",function(){return location.reload()})},e}();t.DefaultReconnectDisplay=a},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=function(){function e(e){this.dialog=e}return e.prototype.show=function(){this.removeClasses(),this.dialog.classList.add(e.ShowClassName)},e.prototype.hide=function(){this.removeClasses(),this.dialog.classList.add(e.HideClassName)},e.prototype.failed=function(){this.removeClasses(),this.dialog.classList.add(e.FailedClassName)},e.prototype.rejected=function(){this.removeClasses(),this.dialog.classList.add(e.RejectedClassName)},e.prototype.removeClasses=function(){this.dialog.classList.remove(e.ShowClassName,e.HideClassName,e.FailedClassName,e.RejectedClassName)},e.ShowClassName="components-reconnect-show",e.HideClassName="components-reconnect-hide",e.FailedClassName="components-reconnect-failed",e.RejectedClassName="components-reconnect-rejected",e}();t.UserSpecifiedDisplay=r},function(e,t,n){"use strict";n.r(t);var r=n(6),o=n(12),i=n(2),a=function(){function e(){}return e.write=function(e){var t=e.byteLength||e.length,n=[];do{var r=127&t;(t>>=7)>0&&(r|=128),n.push(r)}while(t>0);t=e.byteLength||e.length;var o=new Uint8Array(n.length+t);return o.set(n,0),o.set(e,n.length),o.buffer},e.parse=function(e){for(var t=[],n=new Uint8Array(e),r=[0,7,14,21,28],o=0;o7)throw new Error("Messages bigger than 2GB are not supported.");if(!(n.byteLength>=o+i+a))throw new Error("Incomplete message.");t.push(n.slice?n.slice(o+i,o+i+a):n.subarray(o+i,o+i+a)),o=o+i+a}return t},e}();var s=new Uint8Array([145,i.MessageType.Ping]),c=function(){function e(){this.name="messagepack",this.version=1,this.transferFormat=i.TransferFormat.Binary,this.errorResult=1,this.voidResult=2,this.nonVoidResult=3}return e.prototype.parseMessages=function(e,t){if(!(e instanceof r.Buffer||(n=e,n&&"undefined"!=typeof ArrayBuffer&&(n instanceof ArrayBuffer||n.constructor&&"ArrayBuffer"===n.constructor.name))))throw new Error("Invalid input for MessagePack hub protocol. Expected an ArrayBuffer or Buffer.");var n;null===t&&(t=i.NullLogger.instance);for(var o=[],s=0,c=a.parse(e);s=3?e[2]:void 0,error:e[1],type:i.MessageType.Close}},e.prototype.createPingMessage=function(e){if(e.length<1)throw new Error("Invalid payload for Ping message.");return{type:i.MessageType.Ping}},e.prototype.createInvocationMessage=function(e,t){if(t.length<5)throw new Error("Invalid payload for Invocation message.");var n=t[2];return n?{arguments:t[4],headers:e,invocationId:n,streamIds:[],target:t[3],type:i.MessageType.Invocation}:{arguments:t[4],headers:e,streamIds:[],target:t[3],type:i.MessageType.Invocation}},e.prototype.createStreamItemMessage=function(e,t){if(t.length<4)throw new Error("Invalid payload for StreamItem message.");return{headers:e,invocationId:t[2],item:t[3],type:i.MessageType.StreamItem}},e.prototype.createCompletionMessage=function(e,t){if(t.length<4)throw new Error("Invalid payload for Completion message.");var n,r,o=t[3];if(o!==this.voidResult&&t.length<5)throw new Error("Invalid payload for Completion message.");switch(o){case this.errorResult:n=t[4];break;case this.nonVoidResult:r=t[4]}return{error:n,headers:e,invocationId:t[2],result:r,type:i.MessageType.Completion}},e.prototype.writeInvocation=function(e){var t=o().encode([i.MessageType.Invocation,e.headers||{},e.invocationId||null,e.target,e.arguments,e.streamIds]);return a.write(t.slice())},e.prototype.writeStreamInvocation=function(e){var t=o().encode([i.MessageType.StreamInvocation,e.headers||{},e.invocationId,e.target,e.arguments,e.streamIds]);return a.write(t.slice())},e.prototype.writeStreamItem=function(e){var t=o().encode([i.MessageType.StreamItem,e.headers||{},e.invocationId,e.item]);return a.write(t.slice())},e.prototype.writeCompletion=function(e){var t,n=o(),r=e.error?this.errorResult:e.result?this.nonVoidResult:this.voidResult;switch(r){case this.errorResult:t=n.encode([i.MessageType.Completion,e.headers||{},e.invocationId,r,e.error]);break;case this.voidResult:t=n.encode([i.MessageType.Completion,e.headers||{},e.invocationId,r]);break;case this.nonVoidResult:t=n.encode([i.MessageType.Completion,e.headers||{},e.invocationId,r,e.result])}return a.write(t.slice())},e.prototype.writeCancelInvocation=function(e){var t=o().encode([i.MessageType.CancelInvocation,e.headers||{},e.invocationId]);return a.write(t.slice())},e.prototype.readHeaders=function(e){var t=e[1];if("object"!=typeof t)throw new Error("Invalid headers.");return t},e}();n.d(t,"VERSION",function(){return u}),n.d(t,"MessagePackHubProtocol",function(){return c});var u="5.0.0-dev"}]); \ No newline at end of file diff --git a/src/Components/Web.JS/dist/Release/blazor.webassembly.js b/src/Components/Web.JS/dist/Release/blazor.webassembly.js index 0f4669cb09..74a77ddcbe 100644 --- a/src/Components/Web.JS/dist/Release/blazor.webassembly.js +++ b/src/Components/Web.JS/dist/Release/blazor.webassembly.js @@ -1 +1 @@ -!function(e){var t={};function n(r){if(t[r])return t[r].exports;var o=t[r]={i:r,l:!1,exports:{}};return e[r].call(o.exports,o,o.exports,n),o.l=!0,o.exports}n.m=e,n.c=t,n.d=function(e,t,r){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:r})},n.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var o in e)n.d(r,o,function(t){return e[t]}.bind(null,o));return r},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,"a",t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p="",n(n.s=46)}([,,,,,function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0}),n(25),n(9);var r=n(26),o=n(14),a={},i=!1;function l(e,t,n){var o=a[e];o||(o=a[e]=new r.BrowserRenderer(e)),o.attachRootComponentToLogicalElement(n,t)}t.attachRootComponentToLogicalElement=l,t.attachRootComponentToElement=function(e,t,n){var r=document.querySelector(e);if(!r)throw new Error("Could not find any element matching selector '"+e+"'.");l(n||0,o.toLogicalElement(r,!0),t)},t.renderBatch=function(e,t){var n=a[e];if(!n)throw new Error("There is no browser renderer with ID "+e+".");for(var r=t.arrayRangeReader,o=t.updatedComponents(),l=r.values(o),u=r.count(o),s=t.referenceFrames(),c=r.values(s),f=t.diffReader,d=0;d0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&!t)throw new Error("New logical elements must start empty, or allowExistingContents must be true");return e[r]=[],e}function l(e,t,n){var a=e;if(e instanceof Comment&&(s(a)&&s(a).length>0))throw new Error("Not implemented: inserting non-empty logical container");if(u(a))throw new Error("Not implemented: moving existing logical children");var i=s(t);if(n0;)e(r,0);var a=r;a.parentNode.removeChild(a)},t.getLogicalParent=u,t.getLogicalSiblingEnd=function(e){return e[a]||null},t.getLogicalChild=function(e,t){return s(e)[t]},t.isSvgElement=function(e){return"http://www.w3.org/2000/svg"===c(e).namespaceURI},t.getLogicalChildrenArray=s,t.permuteLogicalChildren=function(e,t){var n=s(e);t.forEach(function(e){e.moveRangeStart=n[e.fromSiblingIndex],e.moveRangeEnd=function e(t){if(t instanceof Element)return t;var n=f(t);if(n)return n.previousSibling;var r=u(t);return r instanceof Element?r.lastChild:e(r)}(e.moveRangeStart)}),t.forEach(function(t){var r=t.moveToBeforeMarker=document.createComment("marker"),o=n[t.toSiblingIndex+1];o?o.parentNode.insertBefore(r,o):d(r,e)}),t.forEach(function(e){for(var t=e.moveToBeforeMarker,n=t.parentNode,r=e.moveRangeStart,o=e.moveRangeEnd,a=r;a;){var i=a.nextSibling;if(n.insertBefore(a,t),a===o)break;a=i}n.removeChild(t)}),t.forEach(function(e){n[e.toSiblingIndex]=e.moveRangeStart})},t.getClosestDomElement=c},,,,,function(e,t,n){"use strict";var r;!function(e){window.DotNet=e;var t=[],n={},r={},o=1,a=null;function i(e){t.push(e)}function l(e,t,n,r){var o=s();if(o.invokeDotNetFromJS){var a=JSON.stringify(r,h),i=o.invokeDotNetFromJS(e,t,n,a);return i?f(i):null}throw new Error("The current dispatcher does not support synchronous calls from JS to .NET. Use invokeMethodAsync instead.")}function u(e,t,r,a){if(e&&r)throw new Error("For instance method calls, assemblyName should be null. Received '"+e+"'.");var i=o++,l=new Promise(function(e,t){n[i]={resolve:e,reject:t}});try{var u=JSON.stringify(a,h);s().beginInvokeDotNetFromJS(i,e,t,r,u)}catch(e){c(i,!1,e)}return l}function s(){if(null!==a)return a;throw new Error("No .NET call dispatcher has been set.")}function c(e,t,r){if(!n.hasOwnProperty(e))throw new Error("There is no pending async call with ID "+e+".");var o=n[e];delete n[e],t?o.resolve(r):o.reject(r)}function f(e){return e?JSON.parse(e,function(e,n){return t.reduce(function(t,n){return n(e,t)},n)}):null}function d(e){return e instanceof Error?e.message+"\n"+e.stack:e?e.toString():"null"}function p(e){if(r.hasOwnProperty(e))return r[e];var t,n=window,o="window";if(e.split(".").forEach(function(e){if(!(e in n))throw new Error("Could not find '"+e+"' in '"+o+"'.");t=n,n=n[e],o+="."+e}),n instanceof Function)return n=n.bind(t),r[e]=n,n;throw new Error("The value '"+o+"' is not a function.")}e.attachDispatcher=function(e){a=e},e.attachReviver=i,e.invokeMethod=function(e,t){for(var n=[],r=2;r0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]-1?a.substring(0,l):"",s=l>-1?a.substring(l+1):a,c=t.monoPlatform.findMethod(e,u,s,i);t.monoPlatform.callMethod(c,null,r)},callMethod:function(e,n,r){if(r.length>4)throw new Error("Currently, MonoPlatform supports passing a maximum of 4 arguments from JS to .NET. You tried to pass "+r.length+".");var o=Module.stackSave();try{for(var a=Module.stackAlloc(r.length),l=Module.stackAlloc(4),u=0;u>2,r=Module.HEAPU32[n+1];if(r>y)throw new Error("Cannot read uint64 with high order part "+r+", because the result would exceed Number.MAX_SAFE_INTEGER.");return r*v+Module.HEAPU32[n]},readFloatField:function(e,t){return Module.getValue(e+(t||0),"float")},readObjectField:function(e,t){return Module.getValue(e+(t||0),"i32")},readStringField:function(e,n){var r=Module.getValue(e+(n||0),"i32");return 0===r?null:t.monoPlatform.toJavaScriptString(r)},readStructField:function(e,t){return e+(t||0)}};var w=document.createElement("a");function E(e){return e+12}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(33),o=window.chrome&&navigator.userAgent.indexOf("Edge")<0,a=!1;function i(){return a&&o}t.hasDebuggingEnabled=i,t.attachDebuggerHotkey=function(e){a=e.some(function(e){return/\.pdb$/.test(r.getFileNameFromUrl(e))});var t=navigator.platform.match(/^Mac/i)?"Cmd":"Alt";i()&&console.info("Debugging hotkey: Shift+"+t+"+D (when application has focus)"),document.addEventListener("keydown",function(e){var t;e.shiftKey&&(e.metaKey||e.altKey)&&"KeyD"===e.code&&(a?o?((t=document.createElement("a")).href="_framework/debug?url="+encodeURIComponent(location.href),t.target="_blank",t.rel="noopener noreferrer",t.click()):console.error("Currently, only Chrome is supported for debugging."):console.error("Cannot start debugging, because the application was not compiled with debugging enabled."))})}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(9),o=function(){function e(e){this.batchAddress=e,this.arrayRangeReader=a,this.arrayBuilderSegmentReader=i,this.diffReader=l,this.editReader=u,this.frameReader=s}return e.prototype.updatedComponents=function(){return r.platform.readStructField(this.batchAddress,0)},e.prototype.referenceFrames=function(){return r.platform.readStructField(this.batchAddress,a.structLength)},e.prototype.disposedComponentIds=function(){return r.platform.readStructField(this.batchAddress,2*a.structLength)},e.prototype.disposedEventHandlerIds=function(){return r.platform.readStructField(this.batchAddress,3*a.structLength)},e.prototype.updatedComponentsEntry=function(e,t){return c(e,t,l.structLength)},e.prototype.referenceFramesEntry=function(e,t){return c(e,t,s.structLength)},e.prototype.disposedComponentIdsEntry=function(e,t){var n=c(e,t,4);return r.platform.readInt32Field(n)},e.prototype.disposedEventHandlerIdsEntry=function(e,t){var n=c(e,t,8);return r.platform.readUint64Field(n)},e}();t.SharedMemoryRenderBatch=o;var a={structLength:8,values:function(e){return r.platform.readObjectField(e,0)},count:function(e){return r.platform.readInt32Field(e,4)}},i={structLength:12,values:function(e){var t=r.platform.readObjectField(e,0),n=r.platform.getObjectFieldsBaseAddress(t);return r.platform.readObjectField(n,0)},offset:function(e){return r.platform.readInt32Field(e,4)},count:function(e){return r.platform.readInt32Field(e,8)}},l={structLength:4+i.structLength,componentId:function(e){return r.platform.readInt32Field(e,0)},edits:function(e){return r.platform.readStructField(e,4)},editsEntry:function(e,t){return c(e,t,u.structLength)}},u={structLength:20,editType:function(e){return r.platform.readInt32Field(e,0)},siblingIndex:function(e){return r.platform.readInt32Field(e,4)},newTreeIndex:function(e){return r.platform.readInt32Field(e,8)},moveToSiblingIndex:function(e){return r.platform.readInt32Field(e,8)},removedAttributeName:function(e){return r.platform.readStringField(e,16)}},s={structLength:36,frameType:function(e){return r.platform.readInt16Field(e,4)},subtreeLength:function(e){return r.platform.readInt32Field(e,8)},elementReferenceCaptureId:function(e){return r.platform.readStringField(e,16)},componentId:function(e){return r.platform.readInt32Field(e,12)},elementName:function(e){return r.platform.readStringField(e,16)},textContent:function(e){return r.platform.readStringField(e,16)},markupContent:function(e){return r.platform.readStringField(e,16)},attributeName:function(e){return r.platform.readStringField(e,16)},attributeValue:function(e){return r.platform.readStringField(e,24)},attributeEventHandlerId:function(e){return r.platform.readUint64Field(e,8)}};function c(e,t,n){return r.platform.getArrayEntryPtr(e,t,n)}}]); \ No newline at end of file +!function(e){var t={};function n(r){if(t[r])return t[r].exports;var o=t[r]={i:r,l:!1,exports:{}};return e[r].call(o.exports,o,o.exports,n),o.l=!0,o.exports}n.m=e,n.c=t,n.d=function(e,t,r){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:r})},n.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var o in e)n.d(r,o,function(t){return e[t]}.bind(null,o));return r},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,"a",t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p="",n(n.s=46)}([,,,,,function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0}),n(25),n(9);var r=n(26),o=n(14),a={},i=!1;function l(e,t,n){var o=a[e];o||(o=a[e]=new r.BrowserRenderer(e)),o.attachRootComponentToLogicalElement(n,t)}t.attachRootComponentToLogicalElement=l,t.attachRootComponentToElement=function(e,t,n){var r=document.querySelector(e);if(!r)throw new Error("Could not find any element matching selector '"+e+"'.");l(n||0,o.toLogicalElement(r,!0),t)},t.renderBatch=function(e,t){var n=a[e];if(!n)throw new Error("There is no browser renderer with ID "+e+".");for(var r=t.arrayRangeReader,o=t.updatedComponents(),l=r.values(o),u=r.count(o),s=t.referenceFrames(),c=r.values(s),f=t.diffReader,d=0;d0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&!t)throw new Error("New logical elements must start empty, or allowExistingContents must be true");return e[r]=[],e}function l(e,t,n){var a=e;if(e instanceof Comment&&(s(a)&&s(a).length>0))throw new Error("Not implemented: inserting non-empty logical container");if(u(a))throw new Error("Not implemented: moving existing logical children");var i=s(t);if(n0;)e(r,0);var a=r;a.parentNode.removeChild(a)},t.getLogicalParent=u,t.getLogicalSiblingEnd=function(e){return e[a]||null},t.getLogicalChild=function(e,t){return s(e)[t]},t.isSvgElement=function(e){return"http://www.w3.org/2000/svg"===c(e).namespaceURI},t.getLogicalChildrenArray=s,t.permuteLogicalChildren=function(e,t){var n=s(e);t.forEach(function(e){e.moveRangeStart=n[e.fromSiblingIndex],e.moveRangeEnd=function e(t){if(t instanceof Element)return t;var n=f(t);if(n)return n.previousSibling;var r=u(t);return r instanceof Element?r.lastChild:e(r)}(e.moveRangeStart)}),t.forEach(function(t){var r=t.moveToBeforeMarker=document.createComment("marker"),o=n[t.toSiblingIndex+1];o?o.parentNode.insertBefore(r,o):d(r,e)}),t.forEach(function(e){for(var t=e.moveToBeforeMarker,n=t.parentNode,r=e.moveRangeStart,o=e.moveRangeEnd,a=r;a;){var i=a.nextSibling;if(n.insertBefore(a,t),a===o)break;a=i}n.removeChild(t)}),t.forEach(function(e){n[e.toSiblingIndex]=e.moveRangeStart})},t.getClosestDomElement=c},,,,,function(e,t,n){"use strict";var r;!function(e){window.DotNet=e;var t=[],n={},r={},o=1,a=null;function i(e){t.push(e)}function l(e,t,n,r){var o=s();if(o.invokeDotNetFromJS){var a=JSON.stringify(r,h),i=o.invokeDotNetFromJS(e,t,n,a);return i?f(i):null}throw new Error("The current dispatcher does not support synchronous calls from JS to .NET. Use invokeMethodAsync instead.")}function u(e,t,r,a){if(e&&r)throw new Error("For instance method calls, assemblyName should be null. Received '"+e+"'.");var i=o++,l=new Promise(function(e,t){n[i]={resolve:e,reject:t}});try{var u=JSON.stringify(a,h);s().beginInvokeDotNetFromJS(i,e,t,r,u)}catch(e){c(i,!1,e)}return l}function s(){if(null!==a)return a;throw new Error("No .NET call dispatcher has been set.")}function c(e,t,r){if(!n.hasOwnProperty(e))throw new Error("There is no pending async call with ID "+e+".");var o=n[e];delete n[e],t?o.resolve(r):o.reject(r)}function f(e){return e?JSON.parse(e,function(e,n){return t.reduce(function(t,n){return n(e,t)},n)}):null}function d(e){return e instanceof Error?e.message+"\n"+e.stack:e?e.toString():"null"}function p(e){if(r.hasOwnProperty(e))return r[e];var t,n=window,o="window";if(e.split(".").forEach(function(e){if(!(e in n))throw new Error("Could not find '"+e+"' in '"+o+"'.");t=n,n=n[e],o+="."+e}),n instanceof Function)return n=n.bind(t),r[e]=n,n;throw new Error("The value '"+o+"' is not a function.")}e.attachDispatcher=function(e){a=e},e.attachReviver=i,e.invokeMethod=function(e,t){for(var n=[],r=2;r0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]0&&o[o.length-1])&&(6===a[0]||2===a[0])){i=0;continue}if(3===a[0]&&(!o||a[1]>o[0]&&a[1]-1?a.substring(0,l):"",s=l>-1?a.substring(l+1):a,c=t.monoPlatform.findMethod(e,u,s,i);t.monoPlatform.callMethod(c,null,r)},callMethod:function(e,n,r){if(r.length>4)throw new Error("Currently, MonoPlatform supports passing a maximum of 4 arguments from JS to .NET. You tried to pass "+r.length+".");var o=Module.stackSave();try{for(var a=Module.stackAlloc(r.length),l=Module.stackAlloc(4),u=0;u>2,r=Module.HEAPU32[n+1];if(r>y)throw new Error("Cannot read uint64 with high order part "+r+", because the result would exceed Number.MAX_SAFE_INTEGER.");return r*v+Module.HEAPU32[n]},readFloatField:function(e,t){return Module.getValue(e+(t||0),"float")},readObjectField:function(e,t){return Module.getValue(e+(t||0),"i32")},readStringField:function(e,n){var r=Module.getValue(e+(n||0),"i32");return 0===r?null:t.monoPlatform.toJavaScriptString(r)},readStructField:function(e,t){return e+(t||0)}};var w=document.createElement("a");function E(e){return e+12}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(33),o=window.chrome&&navigator.userAgent.indexOf("Edge")<0,a=!1;function i(){return a&&o}t.hasDebuggingEnabled=i,t.attachDebuggerHotkey=function(e){a=e.some(function(e){return/\.pdb$/.test(r.getFileNameFromUrl(e))});var t=navigator.platform.match(/^Mac/i)?"Cmd":"Alt";i()&&console.info("Debugging hotkey: Shift+"+t+"+D (when application has focus)"),document.addEventListener("keydown",function(e){var t;e.shiftKey&&(e.metaKey||e.altKey)&&"KeyD"===e.code&&(a?o?((t=document.createElement("a")).href="_framework/debug?url="+encodeURIComponent(location.href),t.target="_blank",t.rel="noopener noreferrer",t.click()):console.error("Currently, only Edge(Chromium) or Chrome is supported for debugging."):console.error("Cannot start debugging, because the application was not compiled with debugging enabled."))})}},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var r=n(9),o=function(){function e(e){this.batchAddress=e,this.arrayRangeReader=a,this.arrayBuilderSegmentReader=i,this.diffReader=l,this.editReader=u,this.frameReader=s}return e.prototype.updatedComponents=function(){return r.platform.readStructField(this.batchAddress,0)},e.prototype.referenceFrames=function(){return r.platform.readStructField(this.batchAddress,a.structLength)},e.prototype.disposedComponentIds=function(){return r.platform.readStructField(this.batchAddress,2*a.structLength)},e.prototype.disposedEventHandlerIds=function(){return r.platform.readStructField(this.batchAddress,3*a.structLength)},e.prototype.updatedComponentsEntry=function(e,t){return c(e,t,l.structLength)},e.prototype.referenceFramesEntry=function(e,t){return c(e,t,s.structLength)},e.prototype.disposedComponentIdsEntry=function(e,t){var n=c(e,t,4);return r.platform.readInt32Field(n)},e.prototype.disposedEventHandlerIdsEntry=function(e,t){var n=c(e,t,8);return r.platform.readUint64Field(n)},e}();t.SharedMemoryRenderBatch=o;var a={structLength:8,values:function(e){return r.platform.readObjectField(e,0)},count:function(e){return r.platform.readInt32Field(e,4)}},i={structLength:12,values:function(e){var t=r.platform.readObjectField(e,0),n=r.platform.getObjectFieldsBaseAddress(t);return r.platform.readObjectField(n,0)},offset:function(e){return r.platform.readInt32Field(e,4)},count:function(e){return r.platform.readInt32Field(e,8)}},l={structLength:4+i.structLength,componentId:function(e){return r.platform.readInt32Field(e,0)},edits:function(e){return r.platform.readStructField(e,4)},editsEntry:function(e,t){return c(e,t,u.structLength)}},u={structLength:20,editType:function(e){return r.platform.readInt32Field(e,0)},siblingIndex:function(e){return r.platform.readInt32Field(e,4)},newTreeIndex:function(e){return r.platform.readInt32Field(e,8)},moveToSiblingIndex:function(e){return r.platform.readInt32Field(e,8)},removedAttributeName:function(e){return r.platform.readStringField(e,16)}},s={structLength:36,frameType:function(e){return r.platform.readInt16Field(e,4)},subtreeLength:function(e){return r.platform.readInt32Field(e,8)},elementReferenceCaptureId:function(e){return r.platform.readStringField(e,16)},componentId:function(e){return r.platform.readInt32Field(e,12)},elementName:function(e){return r.platform.readStringField(e,16)},textContent:function(e){return r.platform.readStringField(e,16)},markupContent:function(e){return r.platform.readStringField(e,16)},attributeName:function(e){return r.platform.readStringField(e,16)},attributeValue:function(e){return r.platform.readStringField(e,24)},attributeEventHandlerId:function(e){return r.platform.readUint64Field(e,8)}};function c(e,t,n){return r.platform.getArrayEntryPtr(e,t,n)}}]); \ No newline at end of file diff --git a/src/Components/Web.JS/src/Platform/Mono/MonoDebugger.ts b/src/Components/Web.JS/src/Platform/Mono/MonoDebugger.ts index a0838ac125..e16ec7e195 100644 --- a/src/Components/Web.JS/src/Platform/Mono/MonoDebugger.ts +++ b/src/Components/Web.JS/src/Platform/Mono/MonoDebugger.ts @@ -26,7 +26,7 @@ export function attachDebuggerHotkey(loadAssemblyUrls: string[]) { if (!hasReferencedPdbs) { console.error('Cannot start debugging, because the application was not compiled with debugging enabled.'); } else if (!currentBrowserIsChrome) { - console.error('Currently, only Chrome is supported for debugging.'); + console.error('Currently, only Edge(Chromium) or Chrome is supported for debugging.'); } else { launchDebugger(); } diff --git a/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netcoreapp.cs b/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netcoreapp.cs index cb686083cd..4928dc03fd 100644 --- a/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netcoreapp.cs +++ b/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netcoreapp.cs @@ -125,6 +125,8 @@ namespace Microsoft.AspNetCore.Components.Forms public ValidationSummary() { } [Microsoft.AspNetCore.Components.ParameterAttribute(CaptureUnmatchedValues=true)] public System.Collections.Generic.IReadOnlyDictionary AdditionalAttributes { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } + [Microsoft.AspNetCore.Components.ParameterAttribute] + public object Model { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } protected override void BuildRenderTree(Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder builder) { } protected virtual void Dispose(bool disposing) { } protected override void OnParametersSet() { } @@ -222,97 +224,97 @@ namespace Microsoft.AspNetCore.Components.Web public string Message { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } public string Type { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } } - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onabort", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforeactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecopy", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecut", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforedeactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforepaste", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onblur", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplay", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplaythrough", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onchange", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncontextmenu", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncopy", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncuechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncut", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondblclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondeactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrag", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragend", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragenter", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragleave", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragover", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragstart", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrop", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondurationchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onemptied", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onended", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onerror", typeof(Microsoft.AspNetCore.Components.Web.ErrorEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocus", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusin", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusout", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenerror", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ongotpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninput", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninvalid", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeydown", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeypress", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeyup", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onload", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadeddata", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadedmetadata", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadend", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadstart", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onlostpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousedown", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousemove", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseout", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseover", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseup", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousewheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpaste", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpause", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplay", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplaying", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointercancel", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerdown", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerenter", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerleave", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockerror", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointermove", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerout", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerover", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerup", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onprogress", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onratechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreadystatechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreset", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onscroll", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeked", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeking", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselect", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectionchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectstart", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstalled", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstop", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsubmit", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsuspend", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeout", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeupdate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchcancel", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchend", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchenter", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchleave", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchmove", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchstart", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onvolumechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwaiting", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs))] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onabort", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforeactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecopy", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecut", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforedeactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforepaste", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onblur", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplay", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplaythrough", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onchange", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncontextmenu", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncopy", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncuechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncut", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondblclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondeactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrag", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragend", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragenter", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragleave", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragover", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragstart", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrop", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondurationchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onemptied", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onended", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onerror", typeof(Microsoft.AspNetCore.Components.Web.ErrorEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocus", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusin", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusout", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenerror", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ongotpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninput", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninvalid", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeydown", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeypress", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeyup", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onload", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadeddata", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadedmetadata", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadend", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadstart", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onlostpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousedown", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousemove", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseout", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseover", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseup", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousewheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpaste", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpause", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplay", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplaying", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointercancel", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerdown", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerenter", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerleave", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockerror", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointermove", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerout", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerover", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerup", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onprogress", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onratechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreadystatechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreset", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onscroll", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeked", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeking", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselect", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectionchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectstart", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstalled", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstop", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsubmit", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsuspend", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeout", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeupdate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchcancel", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchend", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchenter", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchleave", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchmove", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchstart", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onvolumechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwaiting", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs), true, true)] public static partial class EventHandlers { } diff --git a/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netstandard2.0.cs b/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netstandard2.0.cs index cb686083cd..4928dc03fd 100644 --- a/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netstandard2.0.cs +++ b/src/Components/Web/ref/Microsoft.AspNetCore.Components.Web.netstandard2.0.cs @@ -125,6 +125,8 @@ namespace Microsoft.AspNetCore.Components.Forms public ValidationSummary() { } [Microsoft.AspNetCore.Components.ParameterAttribute(CaptureUnmatchedValues=true)] public System.Collections.Generic.IReadOnlyDictionary AdditionalAttributes { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } + [Microsoft.AspNetCore.Components.ParameterAttribute] + public object Model { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } protected override void BuildRenderTree(Microsoft.AspNetCore.Components.Rendering.RenderTreeBuilder builder) { } protected virtual void Dispose(bool disposing) { } protected override void OnParametersSet() { } @@ -222,97 +224,97 @@ namespace Microsoft.AspNetCore.Components.Web public string Message { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } public string Type { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } } - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onabort", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforeactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecopy", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecut", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforedeactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforepaste", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onblur", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplay", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplaythrough", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onchange", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncontextmenu", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncopy", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncuechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncut", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondblclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondeactivate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrag", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragend", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragenter", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragleave", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragover", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragstart", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrop", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondurationchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onemptied", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onended", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onerror", typeof(Microsoft.AspNetCore.Components.Web.ErrorEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocus", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusin", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusout", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenerror", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ongotpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninput", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninvalid", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeydown", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeypress", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeyup", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onload", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadeddata", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadedmetadata", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadend", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadstart", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onlostpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousedown", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousemove", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseout", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseover", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseup", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousewheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpaste", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpause", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplay", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplaying", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointercancel", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerdown", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerenter", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerleave", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockerror", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointermove", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerout", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerover", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerup", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onprogress", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onratechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreadystatechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreset", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onscroll", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeked", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeking", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselect", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectionchange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectstart", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstalled", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstop", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsubmit", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsuspend", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeout", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeupdate", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchcancel", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchend", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchenter", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchleave", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchmove", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchstart", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onvolumechange", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwaiting", typeof(System.EventArgs))] - [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs))] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onabort", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforeactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecopy", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforecut", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforedeactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onbeforepaste", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onblur", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplay", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncanplaythrough", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onchange", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncontextmenu", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncopy", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncuechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oncut", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondblclick", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondeactivate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrag", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragend", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragenter", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragleave", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragover", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondragstart", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondrop", typeof(Microsoft.AspNetCore.Components.Web.DragEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ondurationchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onemptied", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onended", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onerror", typeof(Microsoft.AspNetCore.Components.Web.ErrorEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocus", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusin", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfocusout", typeof(Microsoft.AspNetCore.Components.Web.FocusEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onfullscreenerror", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ongotpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninput", typeof(Microsoft.AspNetCore.Components.ChangeEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("oninvalid", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeydown", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeypress", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onkeyup", typeof(Microsoft.AspNetCore.Components.Web.KeyboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onload", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadeddata", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadedmetadata", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadend", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onloadstart", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onlostpointercapture", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousedown", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousemove", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseout", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseover", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmouseup", typeof(Microsoft.AspNetCore.Components.Web.MouseEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onmousewheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpaste", typeof(Microsoft.AspNetCore.Components.Web.ClipboardEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpause", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplay", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onplaying", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointercancel", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerdown", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerenter", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerleave", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerlockerror", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointermove", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerout", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerover", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onpointerup", typeof(Microsoft.AspNetCore.Components.Web.PointerEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onprogress", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onratechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreadystatechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onreset", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onscroll", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeked", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onseeking", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselect", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectionchange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onselectstart", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstalled", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onstop", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsubmit", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onsuspend", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeout", typeof(Microsoft.AspNetCore.Components.Web.ProgressEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontimeupdate", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchcancel", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchend", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchenter", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchleave", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchmove", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("ontouchstart", typeof(Microsoft.AspNetCore.Components.Web.TouchEventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onvolumechange", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwaiting", typeof(System.EventArgs), true, true)] + [Microsoft.AspNetCore.Components.EventHandlerAttribute("onwheel", typeof(Microsoft.AspNetCore.Components.Web.WheelEventArgs), true, true)] public static partial class EventHandlers { } diff --git a/src/Components/Web/src/Forms/ValidationSummary.cs b/src/Components/Web/src/Forms/ValidationSummary.cs index 8e151b1e63..270f787176 100644 --- a/src/Components/Web/src/Forms/ValidationSummary.cs +++ b/src/Components/Web/src/Forms/ValidationSummary.cs @@ -19,6 +19,12 @@ namespace Microsoft.AspNetCore.Components.Forms private EditContext _previousEditContext; private readonly EventHandler _validationStateChangedHandler; + /// + /// Gets or sets the model to produce the list of validation messages for. + /// When specified, this lists all errors that are associated with the model instance. + /// + [Parameter] public object Model { get; set; } + /// /// Gets or sets a collection of additional attributes that will be applied to the created ul element. /// @@ -57,22 +63,31 @@ namespace Microsoft.AspNetCore.Components.Forms { // As an optimization, only evaluate the messages enumerable once, and // only produce the enclosing
    if there's at least one message - var messagesEnumerator = CurrentEditContext.GetValidationMessages().GetEnumerator(); - if (messagesEnumerator.MoveNext()) + var validationMessages = Model is null ? + CurrentEditContext.GetValidationMessages() : + CurrentEditContext.GetValidationMessages(new FieldIdentifier(Model, string.Empty)); + + var first = true; + foreach (var error in validationMessages) { - builder.OpenElement(0, "ul"); - builder.AddMultipleAttributes(1, AdditionalAttributes); - builder.AddAttribute(2, "class", "validation-errors"); - - do + if (first) { - builder.OpenElement(3, "li"); - builder.AddAttribute(4, "class", "validation-message"); - builder.AddContent(5, messagesEnumerator.Current); - builder.CloseElement(); - } - while (messagesEnumerator.MoveNext()); + first = false; + builder.OpenElement(0, "ul"); + builder.AddMultipleAttributes(1, AdditionalAttributes); + builder.AddAttribute(2, "class", "validation-errors"); + } + + builder.OpenElement(3, "li"); + builder.AddAttribute(4, "class", "validation-message"); + builder.AddContent(5, error); + builder.CloseElement(); + } + + if (!first) + { + // We have at least one validation message. builder.CloseElement(); } } diff --git a/src/Components/Web/src/Web/EventHandlers.cs b/src/Components/Web/src/Web/EventHandlers.cs index 46a6f8666c..5e4bb8e83f 100644 --- a/src/Components/Web/src/Web/EventHandlers.cs +++ b/src/Components/Web/src/Web/EventHandlers.cs @@ -11,117 +11,117 @@ namespace Microsoft.AspNetCore.Components.Web /// // Focus events - [EventHandler("onfocus", typeof(FocusEventArgs))] - [EventHandler("onblur", typeof(FocusEventArgs))] - [EventHandler("onfocusin", typeof(FocusEventArgs))] - [EventHandler("onfocusout", typeof(FocusEventArgs))] + [EventHandler("onfocus", typeof(FocusEventArgs), true, true)] + [EventHandler("onblur", typeof(FocusEventArgs), true, true)] + [EventHandler("onfocusin", typeof(FocusEventArgs), true, true)] + [EventHandler("onfocusout", typeof(FocusEventArgs), true, true)] // Mouse events - [EventHandler("onmouseover", typeof(MouseEventArgs))] - [EventHandler("onmouseout", typeof(MouseEventArgs))] - [EventHandler("onmousemove", typeof(MouseEventArgs))] - [EventHandler("onmousedown", typeof(MouseEventArgs))] - [EventHandler("onmouseup", typeof(MouseEventArgs))] - [EventHandler("onclick", typeof(MouseEventArgs))] - [EventHandler("ondblclick", typeof(MouseEventArgs))] - [EventHandler("onwheel", typeof(WheelEventArgs))] - [EventHandler("onmousewheel", typeof(WheelEventArgs))] - [EventHandler("oncontextmenu", typeof(MouseEventArgs))] + [EventHandler("onmouseover", typeof(MouseEventArgs), true, true)] + [EventHandler("onmouseout", typeof(MouseEventArgs), true, true)] + [EventHandler("onmousemove", typeof(MouseEventArgs), true, true)] + [EventHandler("onmousedown", typeof(MouseEventArgs), true, true)] + [EventHandler("onmouseup", typeof(MouseEventArgs), true, true)] + [EventHandler("onclick", typeof(MouseEventArgs), true, true)] + [EventHandler("ondblclick", typeof(MouseEventArgs), true, true)] + [EventHandler("onwheel", typeof(WheelEventArgs), true, true)] + [EventHandler("onmousewheel", typeof(WheelEventArgs), true, true)] + [EventHandler("oncontextmenu", typeof(MouseEventArgs), true, true)] // Drag events - [EventHandler("ondrag", typeof(DragEventArgs))] - [EventHandler("ondragend", typeof(DragEventArgs))] - [EventHandler("ondragenter", typeof(DragEventArgs))] - [EventHandler("ondragleave", typeof(DragEventArgs))] - [EventHandler("ondragover", typeof(DragEventArgs))] - [EventHandler("ondragstart", typeof(DragEventArgs))] - [EventHandler("ondrop", typeof(DragEventArgs))] + [EventHandler("ondrag", typeof(DragEventArgs), true, true)] + [EventHandler("ondragend", typeof(DragEventArgs), true, true)] + [EventHandler("ondragenter", typeof(DragEventArgs), true, true)] + [EventHandler("ondragleave", typeof(DragEventArgs), true, true)] + [EventHandler("ondragover", typeof(DragEventArgs), true, true)] + [EventHandler("ondragstart", typeof(DragEventArgs), true, true)] + [EventHandler("ondrop", typeof(DragEventArgs), true, true)] // Keyboard events - [EventHandler("onkeydown", typeof(KeyboardEventArgs))] - [EventHandler("onkeyup", typeof(KeyboardEventArgs))] - [EventHandler("onkeypress", typeof(KeyboardEventArgs))] + [EventHandler("onkeydown", typeof(KeyboardEventArgs), true, true)] + [EventHandler("onkeyup", typeof(KeyboardEventArgs), true, true)] + [EventHandler("onkeypress", typeof(KeyboardEventArgs), true, true)] // Input events - [EventHandler("onchange", typeof(ChangeEventArgs))] - [EventHandler("oninput", typeof(ChangeEventArgs))] - [EventHandler("oninvalid", typeof(EventArgs))] - [EventHandler("onreset", typeof(EventArgs))] - [EventHandler("onselect", typeof(EventArgs))] - [EventHandler("onselectstart", typeof(EventArgs))] - [EventHandler("onselectionchange", typeof(EventArgs))] - [EventHandler("onsubmit", typeof(EventArgs))] + [EventHandler("onchange", typeof(ChangeEventArgs), true, true)] + [EventHandler("oninput", typeof(ChangeEventArgs), true, true)] + [EventHandler("oninvalid", typeof(EventArgs), true, true)] + [EventHandler("onreset", typeof(EventArgs), true, true)] + [EventHandler("onselect", typeof(EventArgs), true, true)] + [EventHandler("onselectstart", typeof(EventArgs), true, true)] + [EventHandler("onselectionchange", typeof(EventArgs), true, true)] + [EventHandler("onsubmit", typeof(EventArgs), true, true)] // Clipboard events - [EventHandler("onbeforecopy", typeof(EventArgs))] - [EventHandler("onbeforecut", typeof(EventArgs))] - [EventHandler("onbeforepaste", typeof(EventArgs))] - [EventHandler("oncopy", typeof(ClipboardEventArgs))] - [EventHandler("oncut", typeof(ClipboardEventArgs))] - [EventHandler("onpaste", typeof(ClipboardEventArgs))] + [EventHandler("onbeforecopy", typeof(EventArgs), true, true)] + [EventHandler("onbeforecut", typeof(EventArgs), true, true)] + [EventHandler("onbeforepaste", typeof(EventArgs), true, true)] + [EventHandler("oncopy", typeof(ClipboardEventArgs), true, true)] + [EventHandler("oncut", typeof(ClipboardEventArgs), true, true)] + [EventHandler("onpaste", typeof(ClipboardEventArgs), true, true)] // Touch events - [EventHandler("ontouchcancel", typeof(TouchEventArgs))] - [EventHandler("ontouchend", typeof(TouchEventArgs))] - [EventHandler("ontouchmove", typeof(TouchEventArgs))] - [EventHandler("ontouchstart", typeof(TouchEventArgs))] - [EventHandler("ontouchenter", typeof(TouchEventArgs))] - [EventHandler("ontouchleave", typeof(TouchEventArgs))] + [EventHandler("ontouchcancel", typeof(TouchEventArgs), true, true)] + [EventHandler("ontouchend", typeof(TouchEventArgs), true, true)] + [EventHandler("ontouchmove", typeof(TouchEventArgs), true, true)] + [EventHandler("ontouchstart", typeof(TouchEventArgs), true, true)] + [EventHandler("ontouchenter", typeof(TouchEventArgs), true, true)] + [EventHandler("ontouchleave", typeof(TouchEventArgs), true, true)] // Pointer events - [EventHandler("ongotpointercapture", typeof(PointerEventArgs))] - [EventHandler("onlostpointercapture", typeof(PointerEventArgs))] - [EventHandler("onpointercancel", typeof(PointerEventArgs))] - [EventHandler("onpointerdown", typeof(PointerEventArgs))] - [EventHandler("onpointerenter", typeof(PointerEventArgs))] - [EventHandler("onpointerleave", typeof(PointerEventArgs))] - [EventHandler("onpointermove", typeof(PointerEventArgs))] - [EventHandler("onpointerout", typeof(PointerEventArgs))] - [EventHandler("onpointerover", typeof(PointerEventArgs))] - [EventHandler("onpointerup", typeof(PointerEventArgs))] + [EventHandler("ongotpointercapture", typeof(PointerEventArgs), true, true)] + [EventHandler("onlostpointercapture", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointercancel", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointerdown", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointerenter", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointerleave", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointermove", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointerout", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointerover", typeof(PointerEventArgs), true, true)] + [EventHandler("onpointerup", typeof(PointerEventArgs), true, true)] // Media events - [EventHandler("oncanplay", typeof(EventArgs))] - [EventHandler("oncanplaythrough", typeof(EventArgs))] - [EventHandler("oncuechange", typeof(EventArgs))] - [EventHandler("ondurationchange", typeof(EventArgs))] - [EventHandler("onemptied", typeof(EventArgs))] - [EventHandler("onpause", typeof(EventArgs))] - [EventHandler("onplay", typeof(EventArgs))] - [EventHandler("onplaying", typeof(EventArgs))] - [EventHandler("onratechange", typeof(EventArgs))] - [EventHandler("onseeked", typeof(EventArgs))] - [EventHandler("onseeking", typeof(EventArgs))] - [EventHandler("onstalled", typeof(EventArgs))] - [EventHandler("onstop", typeof(EventArgs))] - [EventHandler("onsuspend", typeof(EventArgs))] - [EventHandler("ontimeupdate", typeof(EventArgs))] - [EventHandler("onvolumechange", typeof(EventArgs))] - [EventHandler("onwaiting", typeof(EventArgs))] + [EventHandler("oncanplay", typeof(EventArgs), true, true)] + [EventHandler("oncanplaythrough", typeof(EventArgs), true, true)] + [EventHandler("oncuechange", typeof(EventArgs), true, true)] + [EventHandler("ondurationchange", typeof(EventArgs), true, true)] + [EventHandler("onemptied", typeof(EventArgs), true, true)] + [EventHandler("onpause", typeof(EventArgs), true, true)] + [EventHandler("onplay", typeof(EventArgs), true, true)] + [EventHandler("onplaying", typeof(EventArgs), true, true)] + [EventHandler("onratechange", typeof(EventArgs), true, true)] + [EventHandler("onseeked", typeof(EventArgs), true, true)] + [EventHandler("onseeking", typeof(EventArgs), true, true)] + [EventHandler("onstalled", typeof(EventArgs), true, true)] + [EventHandler("onstop", typeof(EventArgs), true, true)] + [EventHandler("onsuspend", typeof(EventArgs), true, true)] + [EventHandler("ontimeupdate", typeof(EventArgs), true, true)] + [EventHandler("onvolumechange", typeof(EventArgs), true, true)] + [EventHandler("onwaiting", typeof(EventArgs), true, true)] // Progress events - [EventHandler("onloadstart", typeof(ProgressEventArgs))] - [EventHandler("ontimeout", typeof(ProgressEventArgs))] - [EventHandler("onabort", typeof(ProgressEventArgs))] - [EventHandler("onload", typeof(ProgressEventArgs))] - [EventHandler("onloadend", typeof(ProgressEventArgs))] - [EventHandler("onprogress", typeof(ProgressEventArgs))] - [EventHandler("onerror", typeof(ErrorEventArgs))] + [EventHandler("onloadstart", typeof(ProgressEventArgs), true, true)] + [EventHandler("ontimeout", typeof(ProgressEventArgs), true, true)] + [EventHandler("onabort", typeof(ProgressEventArgs), true, true)] + [EventHandler("onload", typeof(ProgressEventArgs), true, true)] + [EventHandler("onloadend", typeof(ProgressEventArgs), true, true)] + [EventHandler("onprogress", typeof(ProgressEventArgs), true, true)] + [EventHandler("onerror", typeof(ErrorEventArgs), true, true)] // General events - [EventHandler("onactivate", typeof(EventArgs))] - [EventHandler("onbeforeactivate", typeof(EventArgs))] - [EventHandler("onbeforedeactivate", typeof(EventArgs))] - [EventHandler("ondeactivate", typeof(EventArgs))] - [EventHandler("onended", typeof(EventArgs))] - [EventHandler("onfullscreenchange", typeof(EventArgs))] - [EventHandler("onfullscreenerror", typeof(EventArgs))] - [EventHandler("onloadeddata", typeof(EventArgs))] - [EventHandler("onloadedmetadata", typeof(EventArgs))] - [EventHandler("onpointerlockchange", typeof(EventArgs))] - [EventHandler("onpointerlockerror", typeof(EventArgs))] - [EventHandler("onreadystatechange", typeof(EventArgs))] - [EventHandler("onscroll", typeof(EventArgs))] + [EventHandler("onactivate", typeof(EventArgs), true, true)] + [EventHandler("onbeforeactivate", typeof(EventArgs), true, true)] + [EventHandler("onbeforedeactivate", typeof(EventArgs), true, true)] + [EventHandler("ondeactivate", typeof(EventArgs), true, true)] + [EventHandler("onended", typeof(EventArgs), true, true)] + [EventHandler("onfullscreenchange", typeof(EventArgs), true, true)] + [EventHandler("onfullscreenerror", typeof(EventArgs), true, true)] + [EventHandler("onloadeddata", typeof(EventArgs), true, true)] + [EventHandler("onloadedmetadata", typeof(EventArgs), true, true)] + [EventHandler("onpointerlockchange", typeof(EventArgs), true, true)] + [EventHandler("onpointerlockerror", typeof(EventArgs), true, true)] + [EventHandler("onreadystatechange", typeof(EventArgs), true, true)] + [EventHandler("onscroll", typeof(EventArgs), true, true)] public static class EventHandlers { } diff --git a/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubInvalidEventTest.cs b/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubInvalidEventTest.cs index 65b48594f0..26bce75205 100644 --- a/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubInvalidEventTest.cs +++ b/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubInvalidEventTest.cs @@ -38,7 +38,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.ServerExecutionTests { // Arrange var expectedError = $"There was an unhandled exception on the current circuit, so this circuit will be terminated. For more details turn on " + - $"detailed exceptions in 'CircuitOptions.DetailedErrors'. Bad input data."; + $"detailed exceptions by setting 'DetailedErrors: true' in 'appSettings.Development.json' or set 'CircuitOptions.DetailedErrors'. Bad input data."; var eventDescriptor = Serialize(new WebEventDescriptor() { @@ -65,7 +65,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.ServerExecutionTests { // Arrange var expectedError = $"There was an unhandled exception on the current circuit, so this circuit will be terminated. For more details turn on " + - $"detailed exceptions in 'CircuitOptions.DetailedErrors'. Failed to dispatch event."; + $"detailed exceptions by setting 'DetailedErrors: true' in 'appSettings.Development.json' or set 'CircuitOptions.DetailedErrors'. Failed to dispatch event."; var eventDescriptor = Serialize(new WebEventDescriptor() { @@ -105,7 +105,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.ServerExecutionTests { // Arrange var expectedError = $"There was an unhandled exception on the current circuit, so this circuit will be terminated. For more details turn on " + - $"detailed exceptions in 'CircuitOptions.DetailedErrors'. Failed to complete render batch '1846'."; + $"detailed exceptions by setting 'DetailedErrors: true' in 'appSettings.Development.json' or set 'CircuitOptions.DetailedErrors'. Failed to complete render batch '1846'."; Client.ConfirmRenderBatch = false; diff --git a/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubReliabilityTest.cs b/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubReliabilityTest.cs index 42eae05174..707aad52b9 100644 --- a/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubReliabilityTest.cs +++ b/src/Components/test/E2ETest/ServerExecutionTests/ComponentHubReliabilityTest.cs @@ -216,7 +216,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.ServerExecutionTests { // Arrange var expectedError = "There was an unhandled exception on the current circuit, so this circuit will be terminated. " + - "For more details turn on detailed exceptions in 'CircuitOptions.DetailedErrors'. " + + "For more details turn on detailed exceptions by setting 'DetailedErrors: true' in 'appSettings.Development.json' or set 'CircuitOptions.DetailedErrors'. " + "Location change to 'http://example.com' failed."; var rootUri = ServerFixture.RootUri; @@ -245,7 +245,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.ServerExecutionTests { // Arrange var expectedError = "There was an unhandled exception on the current circuit, so this circuit will be terminated. " + - "For more details turn on detailed exceptions in 'CircuitOptions.DetailedErrors'. " + + "For more details turn on detailed exceptions by setting 'DetailedErrors: true' in 'appSettings.Development.json' or set 'CircuitOptions.DetailedErrors'. " + "Location change failed."; var rootUri = ServerFixture.RootUri; diff --git a/src/Components/test/E2ETest/ServerExecutionTests/IgnitorTest.cs b/src/Components/test/E2ETest/ServerExecutionTests/IgnitorTest.cs index 6e96fb16fb..60ec73621a 100644 --- a/src/Components/test/E2ETest/ServerExecutionTests/IgnitorTest.cs +++ b/src/Components/test/E2ETest/ServerExecutionTests/IgnitorTest.cs @@ -75,11 +75,6 @@ namespace Microsoft.AspNetCore.Components async Task IAsyncLifetime.DisposeAsync() { - if (TestSink != null) - { - TestSink.MessageLogged -= TestSink_MessageLogged; - } - await DisposeAsync(); } @@ -90,6 +85,11 @@ namespace Microsoft.AspNetCore.Components protected virtual Task DisposeAsync() { + if (TestSink != null) + { + TestSink.MessageLogged -= TestSink_MessageLogged; + } + return Task.CompletedTask; } @@ -97,7 +97,18 @@ namespace Microsoft.AspNetCore.Components { var log = new LogMessage(context.LogLevel, context.EventId, context.Message, context.Exception); Logs.Enqueue(log); - Output.WriteLine(log.ToString()); + try + { + // This might produce an InvalidOperationException when the logger tries to log a message after + // the test has completed but before the handler has been removed. + // ---> System.InvalidOperationException: There is no currently active test. + // For that reason, we capture the exception here and silence it, as the message is captured inside the Logs + // variable anyway. + Output.WriteLine(log.ToString()); + } + catch (Exception) + { + } } [DebuggerDisplay("{LogLevel.ToString(),nq} - {Message ?? \"null\",nq} - {Exception?.Message,nq}")] diff --git a/src/Components/test/E2ETest/Tests/FormsTest.cs b/src/Components/test/E2ETest/Tests/FormsTest.cs index 2d622ba864..edd7404f6f 100644 --- a/src/Components/test/E2ETest/Tests/FormsTest.cs +++ b/src/Components/test/E2ETest/Tests/FormsTest.cs @@ -1,18 +1,17 @@ // 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.Linq; +using System.Text.Json; +using System.Threading.Tasks; using BasicTestApp; using BasicTestApp.FormsTest; using Microsoft.AspNetCore.Components.E2ETest.Infrastructure; using Microsoft.AspNetCore.Components.E2ETest.Infrastructure.ServerFixtures; using Microsoft.AspNetCore.E2ETesting; -using Microsoft.AspNetCore.Testing; using OpenQA.Selenium; using OpenQA.Selenium.Support.UI; -using System; -using System.Linq; -using System.Text.Json; -using System.Threading.Tasks; using Xunit; using Xunit.Abstractions; @@ -34,14 +33,20 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests Navigate(ServerPathBase, noReload: _serverFixture.ExecutionMode == ExecutionMode.Client); } + protected virtual IWebElement MountSimpleValidationComponent() + => Browser.MountTestComponent(); + + protected virtual IWebElement MountTypicalValidationComponent() + => Browser.MountTestComponent(); + [Fact] public async Task EditFormWorksWithDataAnnotationsValidator() { - var appElement = Browser.MountTestComponent(); + var appElement = MountSimpleValidationComponent();; var form = appElement.FindElement(By.TagName("form")); var userNameInput = appElement.FindElement(By.ClassName("user-name")).FindElement(By.TagName("input")); var acceptsTermsInput = appElement.FindElement(By.ClassName("accepts-terms")).FindElement(By.TagName("input")); - var submitButton = appElement.FindElement(By.TagName("button")); + var submitButton = appElement.FindElement(By.CssSelector("button[type=submit]")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); // The form emits unmatched attributes @@ -77,7 +82,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputTextInteractsWithEditContext() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var nameInput = appElement.FindElement(By.ClassName("name")).FindElement(By.TagName("input")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -104,7 +109,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputNumberInteractsWithEditContext_NonNullableInt() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var ageInput = appElement.FindElement(By.ClassName("age")).FindElement(By.TagName("input")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -136,7 +141,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputNumberInteractsWithEditContext_NullableFloat() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var heightInput = appElement.FindElement(By.ClassName("height")).FindElement(By.TagName("input")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -160,7 +165,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputTextAreaInteractsWithEditContext() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var descriptionInput = appElement.FindElement(By.ClassName("description")).FindElement(By.TagName("textarea")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -187,7 +192,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputDateInteractsWithEditContext_NonNullableDateTime() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var renewalDateInput = appElement.FindElement(By.ClassName("renewal-date")).FindElement(By.TagName("input")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -218,7 +223,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputDateInteractsWithEditContext_NullableDateTimeOffset() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var expiryDateInput = appElement.FindElement(By.ClassName("expiry-date")).FindElement(By.TagName("input")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -241,7 +246,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputSelectInteractsWithEditContext() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var ticketClassInput = new SelectElement(appElement.FindElement(By.ClassName("ticket-class")).FindElement(By.TagName("select"))); var select = ticketClassInput.WrappedElement; var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -263,7 +268,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void InputCheckboxInteractsWithEditContext() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var acceptsTermsInput = appElement.FindElement(By.ClassName("accepts-terms")).FindElement(By.TagName("input")); var isEvilInput = appElement.FindElement(By.ClassName("is-evil")).FindElement(By.TagName("input")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); @@ -297,7 +302,7 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests var appElement = Browser.MountTestComponent(); var userNameInput = appElement.FindElement(By.ClassName("user-name")).FindElement(By.TagName("input")); var acceptsTermsInput = appElement.FindElement(By.ClassName("accepts-terms")).FindElement(By.TagName("input")); - var submitButton = appElement.FindElement(By.TagName("button")); + var submitButton = appElement.FindElement(By.CssSelector("button[type=submit]")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); var submissionStatus = appElement.FindElement(By.Id("submission-status")); @@ -331,11 +336,11 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests [Fact] public void ValidationMessageDisplaysMessagesForField() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var emailContainer = appElement.FindElement(By.ClassName("email")); var emailInput = emailContainer.FindElement(By.TagName("input")); var emailMessagesAccessor = CreateValidationMessagesAccessor(emailContainer); - var submitButton = appElement.FindElement(By.TagName("button")); + var submitButton = appElement.FindElement(By.CssSelector("button[type=submit]")); // Doesn't show messages for other fields submitButton.Click(); @@ -355,10 +360,43 @@ namespace Microsoft.AspNetCore.Components.E2ETest.Tests Browser.Empty(emailMessagesAccessor); } + [Fact] + public void ErrorsFromCompareAttribute() + { + var appElement = MountTypicalValidationComponent(); + var emailContainer = appElement.FindElement(By.ClassName("email")); + var emailInput = emailContainer.FindElement(By.TagName("input")); + var confirmEmailContainer = appElement.FindElement(By.ClassName("confirm-email")); + var confirmInput = confirmEmailContainer.FindElement(By.TagName("input")); + var confirmEmailValidationMessage = CreateValidationMessagesAccessor(confirmEmailContainer); + var modelErrors = CreateValidationMessagesAccessor(appElement.FindElement(By.ClassName("model-errors"))); + CreateValidationMessagesAccessor(emailContainer); + var submitButton = appElement.FindElement(By.CssSelector("button[type=submit]")); + + // Updates on edit + emailInput.SendKeys("a@b.com\t"); + + submitButton.Click(); + Browser.Empty(confirmEmailValidationMessage); + Browser.Equal(new[] { "Email and confirm email do not match." }, modelErrors); + + confirmInput.SendKeys("not-test@example.com\t"); + Browser.Equal(new[] { "Email and confirm email do not match." }, confirmEmailValidationMessage); + + // Can become correct + confirmInput.Clear(); + confirmInput.SendKeys("a@b.com\t"); + + Browser.Empty(confirmEmailValidationMessage); + + submitButton.Click(); + Browser.Empty(modelErrors); + } + [Fact] public void InputComponentsCauseContainerToRerenderOnChange() { - var appElement = Browser.MountTestComponent(); + var appElement = MountTypicalValidationComponent(); var ticketClassInput = new SelectElement(appElement.FindElement(By.ClassName("ticket-class")).FindElement(By.TagName("select"))); var selectedTicketClassDisplay = appElement.FindElement(By.Id("selected-ticket-class")); var messagesAccessor = CreateValidationMessagesAccessor(appElement); diff --git a/src/Components/test/E2ETest/Tests/FormsTestWithExperimentalValidator.cs b/src/Components/test/E2ETest/Tests/FormsTestWithExperimentalValidator.cs new file mode 100644 index 0000000000..dc2fb06b33 --- /dev/null +++ b/src/Components/test/E2ETest/Tests/FormsTestWithExperimentalValidator.cs @@ -0,0 +1,90 @@ +// 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 BasicTestApp.FormsTest; +using Microsoft.AspNetCore.Components.E2ETest.Infrastructure.ServerFixtures; +using Microsoft.AspNetCore.E2ETesting; +using OpenQA.Selenium; +using OpenQA.Selenium.Support.UI; +using Xunit; +using Xunit.Abstractions; + +namespace Microsoft.AspNetCore.Components.E2ETest.Tests +{ + public class FormsTestWithExperimentalValidator : FormsTest + { + public FormsTestWithExperimentalValidator( + BrowserFixture browserFixture, + ToggleExecutionModeServerFixture serverFixture, + ITestOutputHelper output) : base(browserFixture, serverFixture, output) + { + } + + protected override IWebElement MountSimpleValidationComponent() + => Browser.MountTestComponent(); + + protected override IWebElement MountTypicalValidationComponent() + => Browser.MountTestComponent(); + + [Fact] + public void EditFormWorksWithNestedValidation() + { + var appElement = Browser.MountTestComponent(); + + var nameInput = appElement.FindElement(By.CssSelector(".name input")); + var emailInput = appElement.FindElement(By.CssSelector(".email input")); + var confirmEmailInput = appElement.FindElement(By.CssSelector(".confirm-email input")); + var streetInput = appElement.FindElement(By.CssSelector(".street input")); + var zipInput = appElement.FindElement(By.CssSelector(".zip input")); + var countryInput = new SelectElement(appElement.FindElement(By.CssSelector(".country select"))); + var descriptionInput = appElement.FindElement(By.CssSelector(".description input")); + var weightInput = appElement.FindElement(By.CssSelector(".weight input")); + + var submitButton = appElement.FindElement(By.CssSelector("button[type=submit]")); + + submitButton.Click(); + + Browser.Equal(4, () => appElement.FindElements(By.CssSelector(".all-errors .validation-message")).Count); + + Browser.Equal("Enter a name", () => appElement.FindElement(By.CssSelector(".name .validation-message")).Text); + Browser.Equal("Enter an email", () => appElement.FindElement(By.CssSelector(".email .validation-message")).Text); + Browser.Equal("A street address is required.", () => appElement.FindElement(By.CssSelector(".street .validation-message")).Text); + Browser.Equal("Description is required.", () => appElement.FindElement(By.CssSelector(".description .validation-message")).Text); + + // Verify class-level validation + nameInput.SendKeys("Some person"); + emailInput.SendKeys("test@example.com"); + countryInput.SelectByValue("Mordor"); + descriptionInput.SendKeys("Fragile staff"); + streetInput.SendKeys("Mount Doom\t"); + + submitButton.Click(); + + // Verify member validation from IValidatableObject on a model property, CustomValidationAttribute on a model attribute, and BlazorCompareAttribute. + Browser.Equal("A ZipCode is required", () => appElement.FindElement(By.CssSelector(".zip .validation-message")).Text); + Browser.Equal("'Confirm email address' and 'EmailAddress' do not match.", () => appElement.FindElement(By.CssSelector(".confirm-email .validation-message")).Text); + Browser.Equal("Fragile items must be placed in secure containers", () => appElement.FindElement(By.CssSelector(".item-error .validation-message")).Text); + Browser.Equal(3, () => appElement.FindElements(By.CssSelector(".all-errors .validation-message")).Count); + + zipInput.SendKeys("98052"); + confirmEmailInput.SendKeys("test@example.com"); + descriptionInput.Clear(); + weightInput.SendKeys("0"); + descriptionInput.SendKeys("The One Ring\t"); + + submitButton.Click(); + // Verify validation from IValidatableObject on the model. + Browser.Equal("Some items in your list cannot be delivered.", () => appElement.FindElement(By.CssSelector(".model-errors .validation-message")).Text); + + Browser.Single(() => appElement.FindElements(By.CssSelector(".all-errors .validation-message"))); + + // Let's make sure the form submits + descriptionInput.Clear(); + descriptionInput.SendKeys("A different ring\t"); + submitButton.Click(); + + Browser.Empty(() => appElement.FindElements(By.CssSelector(".all-errors .validation-message"))); + Browser.Equal("OnValidSubmit", () => appElement.FindElement(By.CssSelector(".submission-log")).Text); + } + } +} diff --git a/src/Components/test/testassets/BasicTestApp/BasicTestApp.csproj b/src/Components/test/testassets/BasicTestApp/BasicTestApp.csproj index ac0e530516..98357d0e88 100644 --- a/src/Components/test/testassets/BasicTestApp/BasicTestApp.csproj +++ b/src/Components/test/testassets/BasicTestApp/BasicTestApp.csproj @@ -17,6 +17,7 @@ + diff --git a/src/Components/test/testassets/BasicTestApp/FormsTest/ExperimentalValidationComponent.razor b/src/Components/test/testassets/BasicTestApp/FormsTest/ExperimentalValidationComponent.razor new file mode 100644 index 0000000000..fe3df5382e --- /dev/null +++ b/src/Components/test/testassets/BasicTestApp/FormsTest/ExperimentalValidationComponent.razor @@ -0,0 +1,185 @@ +@using System.ComponentModel.DataAnnotations +@using Microsoft.AspNetCore.Components.Forms + +

    + This component is used to verify the use of the experimental ObjectGraphDataAnnotationsValidator type with IValidatableObject and deep validation, as well + as the ComparePropertyAttribute. +

    + + + + +

    + Name: + +

    + + + + + +
    + Items to deliver +

    + +

    +
      + @foreach (var item in model.Items) + { +
    • +
      +
      + + +
      + +
      + + +
      +
      + +
      +
      +
    • + } +
    +
    + +
    + Shipping details +

    + Street Address: + +

    +

    + Zip Code: + +

    +

    + Country: + + + + + + + + +

    +

    + +

    +
    + +
    + +
    + + +
    + +
    + +
    + +
      + @foreach (var entry in submissionLog) + { +
    • @entry
    • + } +
    + +@code { + Delivery model = new Delivery(); + + public class Delivery : IValidatableObject + { + [Required(ErrorMessage = "Enter a name")] + public string Recipient { get; set; } + + [Required(ErrorMessage = "Enter an email")] + [EmailAddress(ErrorMessage = "Enter a valid email address")] + public string EmailAddress { get; set; } + + [CompareProperty(nameof(EmailAddress))] + [Display(Name = "Confirm email address")] + public string ConfirmEmailAddress { get; set; } + + [ValidateComplexType] + public Address Address { get; } = new Address(); + + [ValidateComplexType] + public List Items { get; } = new List + { + new Item(), + }; + + public IEnumerable Validate(ValidationContext context) + { + if (Address.Street == "Mount Doom" && Items.Any(i => i.Description == "The One Ring")) + { + yield return new ValidationResult("Some items in your list cannot be delivered."); + } + } + } + + public class Address : IValidatableObject + { + [Required(ErrorMessage = "A street address is required.")] + public string Street { get; set; } + + public string ZipCode { get; set; } + + [EnumDataType(typeof(Country))] + public Country Country { get; set; } + + public IEnumerable Validate(ValidationContext context) + { + if (Country == Country.Mordor && string.IsNullOrEmpty(ZipCode)) + { + yield return new ValidationResult("A ZipCode is required", new[] { nameof(ZipCode) }); + } + } + } + + [CustomValidation(typeof(Item), nameof(Item.CustomValidate))] + public class Item + { + [Required(ErrorMessage = "Description is required.")] + public string Description { get; set; } + + [Range(0.1, 50, ErrorMessage = "Items must weigh between 0.1 and 5")] + public double Weight { get; set; } = 1; + + public static ValidationResult CustomValidate(Item item, ValidationContext context) + { + if (item.Weight < 2.0 && item.Description.StartsWith("Fragile")) + { + return new ValidationResult("Fragile items must be placed in secure containers"); + } + + return ValidationResult.Success; + } + } + + public enum Country { Gondor, Mordor, Rohan, Shire } + + List submissionLog = new List(); + + void HandleValidSubmit() + { + submissionLog.Add("OnValidSubmit"); + } + + void AddItem() + { + model.Items.Add(new Item()); + } +} diff --git a/src/Components/test/testassets/BasicTestApp/FormsTest/SimpleValidationComponent.razor b/src/Components/test/testassets/BasicTestApp/FormsTest/SimpleValidationComponent.razor index aa8ccfbe54..2c9a4d2456 100644 --- a/src/Components/test/testassets/BasicTestApp/FormsTest/SimpleValidationComponent.razor +++ b/src/Components/test/testassets/BasicTestApp/FormsTest/SimpleValidationComponent.razor @@ -2,7 +2,14 @@ @using Microsoft.AspNetCore.Components.Forms - + @if (UseExperimentalValidator) + { + + } + else + { + + }

    User name: @@ -29,6 +36,8 @@ } @code { + protected virtual bool UseExperimentalValidator => false; + string lastCallback; [Required(ErrorMessage = "Please choose a username")] diff --git a/src/Components/test/testassets/BasicTestApp/FormsTest/SimpleValidationComponentUsingExperimentalValidator.cs b/src/Components/test/testassets/BasicTestApp/FormsTest/SimpleValidationComponentUsingExperimentalValidator.cs new file mode 100644 index 0000000000..90484aad05 --- /dev/null +++ b/src/Components/test/testassets/BasicTestApp/FormsTest/SimpleValidationComponentUsingExperimentalValidator.cs @@ -0,0 +1,7 @@ +namespace BasicTestApp.FormsTest +{ + public class TypicalValidationComponentUsingExperimentalValidator : TypicalValidationComponent + { + protected override bool UseExperimentalValidator => true; + } +} diff --git a/src/Components/test/testassets/BasicTestApp/FormsTest/TypicalValidationComponent.razor b/src/Components/test/testassets/BasicTestApp/FormsTest/TypicalValidationComponent.razor index 1bd3b748d1..90b2f6a26b 100644 --- a/src/Components/test/testassets/BasicTestApp/FormsTest/TypicalValidationComponent.razor +++ b/src/Components/test/testassets/BasicTestApp/FormsTest/TypicalValidationComponent.razor @@ -2,7 +2,14 @@ @using Microsoft.AspNetCore.Components.Forms + @if (UseExperimentalValidator) + { + + } + else + { + }

    Name: @@ -11,6 +18,10 @@ Email:

    +

    Age (years):

    @@ -49,12 +60,18 @@ +

    + +

    +
      @foreach (var entry in submissionLog) {
    • @entry
    • }
    @code { + protected virtual bool UseExperimentalValidator => false; + Person person = new Person(); EditContext editContext; ValidationMessageStore customValidationMessageStore; @@ -75,6 +92,9 @@ [StringLength(10, ErrorMessage = "We only accept very short email addresses (max 10 chars)")] public string Email { get; set; } + [Compare(nameof(Email), ErrorMessage = "Email and confirm email do not match.")] + public string ConfirmEmail { get; set; } + [Range(0, 200, ErrorMessage = "Nobody is that old")] public int AgeInYears { get; set; } diff --git a/src/Components/test/testassets/BasicTestApp/FormsTest/TypicalValidationComponentUsingExperimentalValidator.cs b/src/Components/test/testassets/BasicTestApp/FormsTest/TypicalValidationComponentUsingExperimentalValidator.cs new file mode 100644 index 0000000000..9ede005a8a --- /dev/null +++ b/src/Components/test/testassets/BasicTestApp/FormsTest/TypicalValidationComponentUsingExperimentalValidator.cs @@ -0,0 +1,7 @@ +namespace BasicTestApp.FormsTest +{ + public class SimpleValidationComponentUsingExperimentalValidator : SimpleValidationComponent + { + protected override bool UseExperimentalValidator => true; + } +} diff --git a/src/Components/test/testassets/BasicTestApp/Index.razor b/src/Components/test/testassets/BasicTestApp/Index.razor index fe94ad595e..f836fa6c39 100644 --- a/src/Components/test/testassets/BasicTestApp/Index.razor +++ b/src/Components/test/testassets/BasicTestApp/Index.razor @@ -29,7 +29,10 @@ + + + diff --git a/src/Components/test/testassets/ComponentsApp.Server/wwwroot/css/site.css b/src/Components/test/testassets/ComponentsApp.Server/wwwroot/css/site.css index 2789bc7b8d..c15c2e1556 100644 --- a/src/Components/test/testassets/ComponentsApp.Server/wwwroot/css/site.css +++ b/src/Components/test/testassets/ComponentsApp.Server/wwwroot/css/site.css @@ -4,6 +4,16 @@ html, body { font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif; } +a, .btn-link { + color: #0366d6; +} + +.btn-primary { + color: #fff; + background-color: #1b6ec2; + border-color: #1861ac; +} + app { position: relative; display: flex; @@ -21,10 +31,21 @@ app { } .main .top-row { - background-color: #e6e6e6; + background-color: #f7f7f7; border-bottom: 1px solid #d6d5d5; + justify-content: flex-end; } + .main .top-row > a, .main .top-row .btn-link { + white-space: nowrap; + margin-left: 1.5rem; + } + +.main .top-row a:first-child { + overflow: hidden; + text-overflow: ellipsis; +} + .sidebar { background-image: linear-gradient(180deg, rgb(5, 39, 103) 0%, #3a0647 70%); } @@ -44,38 +65,38 @@ app { top: -2px; } -.nav-item { - font-size: 0.9rem; - padding-bottom: 0.5rem; -} - - .nav-item:first-of-type { - padding-top: 1rem; + .sidebar .nav-item { + font-size: 0.9rem; + padding-bottom: 0.5rem; } - .nav-item:last-of-type { - padding-bottom: 1rem; - } - - .nav-item a { - color: #d7d7d7; - border-radius: 4px; - height: 3rem; - display: flex; - align-items: center; - line-height: 3rem; - } - - .nav-item a.active { - background-color: rgba(255,255,255,0.25); - color: white; + .sidebar .nav-item:first-of-type { + padding-top: 1rem; } - .nav-item a:hover { - background-color: rgba(255,255,255,0.1); - color: white; + .sidebar .nav-item:last-of-type { + padding-bottom: 1rem; } + .sidebar .nav-item a { + color: #d7d7d7; + border-radius: 4px; + height: 3rem; + display: flex; + align-items: center; + line-height: 3rem; + } + + .sidebar .nav-item a.active { + background-color: rgba(255,255,255,0.25); + color: white; + } + + .sidebar .nav-item a:hover { + background-color: rgba(255,255,255,0.1); + color: white; + } + .content { padding-top: 1.1rem; } @@ -96,10 +117,37 @@ app { color: red; } +#blazor-error-ui { + background: lightyellow; + bottom: 0; + box-shadow: 0 -1px 2px rgba(0, 0, 0, 0.2); + display: none; + left: 0; + padding: 0.6rem 1.25rem 0.7rem 1.25rem; + position: fixed; + width: 100%; + z-index: 1000; +} + +#blazor-error-ui .dismiss { + cursor: pointer; + position: absolute; + right: 0.75rem; + top: 0.5rem; +} + @media (max-width: 767.98px) { - .main .top-row { + .main .top-row:not(.auth) { display: none; } + + .main .top-row.auth { + justify-content: space-between; + } + + .main .top-row a, .main .top-row .btn-link { + margin-left: 0; + } } @media (min-width: 768px) { diff --git a/src/Hosting/test/FunctionalTests/ShutdownTests.cs b/src/Hosting/test/FunctionalTests/ShutdownTests.cs index 46007e6a99..54f7adb4e8 100644 --- a/src/Hosting/test/FunctionalTests/ShutdownTests.cs +++ b/src/Hosting/test/FunctionalTests/ShutdownTests.cs @@ -24,17 +24,15 @@ namespace Microsoft.AspNetCore.Hosting.FunctionalTests public ShutdownTests(ITestOutputHelper output) : base(output) { } - [ConditionalFact(Skip = "https://github.com/aspnet/AspNetCore-Internal/issues/2577")] + [ConditionalFact] [OSSkipCondition(OperatingSystems.Windows)] [OSSkipCondition(OperatingSystems.MacOSX)] - [Flaky("https://github.com/aspnet/AspNetCore-Internal/issues/2577", FlakyOn.All)] public async Task ShutdownTestRun() { await ExecuteShutdownTest(nameof(ShutdownTestRun), "Run"); } [ConditionalFact] - [Flaky("https://github.com/aspnet/Hosting/issues/1214", FlakyOn.All)] [OSSkipCondition(OperatingSystems.Windows)] [OSSkipCondition(OperatingSystems.MacOSX)] public async Task ShutdownTestWaitForShutdown() diff --git a/src/Http/WebUtilities/src/FormPipeReader.cs b/src/Http/WebUtilities/src/FormPipeReader.cs index b0a7d4684c..60f337757b 100644 --- a/src/Http/WebUtilities/src/FormPipeReader.cs +++ b/src/Http/WebUtilities/src/FormPipeReader.cs @@ -167,7 +167,7 @@ namespace Microsoft.AspNetCore.WebUtilities if (!isFinalBlock) { // Don't buffer indefinately - if (span.Length > KeyLengthLimit + ValueLengthLimit) + if ((uint)span.Length > (uint)KeyLengthLimit + (uint)ValueLengthLimit) { ThrowKeyOrValueTooLargeException(); } @@ -236,7 +236,7 @@ namespace Microsoft.AspNetCore.WebUtilities if (!isFinalBlock) { // Don't buffer indefinately - if ((sequenceReader.Consumed - consumedBytes) > KeyLengthLimit + ValueLengthLimit) + if ((uint)(sequenceReader.Consumed - consumedBytes) > (uint)KeyLengthLimit + (uint)ValueLengthLimit) { ThrowKeyOrValueTooLargeException(); } diff --git a/src/Http/WebUtilities/test/FormPipeReaderTests.cs b/src/Http/WebUtilities/test/FormPipeReaderTests.cs index 58d3af12d5..f0e806aae0 100644 --- a/src/Http/WebUtilities/test/FormPipeReaderTests.cs +++ b/src/Http/WebUtilities/test/FormPipeReaderTests.cs @@ -211,6 +211,28 @@ namespace Microsoft.AspNetCore.WebUtilities Assert.Equal("", dict["t"]); } + [Theory] + [MemberData(nameof(Encodings))] + public void TryParseFormValues_LimitsCanBeLarge(Encoding encoding) + { + var readOnlySequence = ReadOnlySequenceFactory.SingleSegmentFactory.CreateWithContent(encoding.GetBytes("foo=bar&baz=boo&t=")); + + KeyValueAccumulator accumulator = default; + + var formReader = new FormPipeReader(null, encoding); + formReader.KeyLengthLimit = int.MaxValue; + formReader.ValueLengthLimit = int.MaxValue; + formReader.ParseFormValues(ref readOnlySequence, ref accumulator, isFinalBlock: false); + formReader.ParseFormValues(ref readOnlySequence, ref accumulator, isFinalBlock: true); + Assert.True(readOnlySequence.IsEmpty); + + Assert.Equal(3, accumulator.KeyCount); + var dict = accumulator.GetResults(); + Assert.Equal("bar", dict["foo"]); + Assert.Equal("boo", dict["baz"]); + Assert.Equal("", dict["t"]); + } + [Theory] [MemberData(nameof(Encodings))] public void TryParseFormValues_SplitAcrossSegmentsWorks(Encoding encoding) @@ -230,6 +252,28 @@ namespace Microsoft.AspNetCore.WebUtilities Assert.Equal("", dict["t"]); } + [Theory] + [MemberData(nameof(Encodings))] + public void TryParseFormValues_SplitAcrossSegmentsWorks_LimitsCanBeLarge(Encoding encoding) + { + var readOnlySequence = ReadOnlySequenceFactory.SegmentPerByteFactory.CreateWithContent(encoding.GetBytes("foo=bar&baz=boo&t=")); + + KeyValueAccumulator accumulator = default; + + var formReader = new FormPipeReader(null, encoding); + formReader.KeyLengthLimit = int.MaxValue; + formReader.ValueLengthLimit = int.MaxValue; + formReader.ParseFormValues(ref readOnlySequence, ref accumulator, isFinalBlock: false); + formReader.ParseFormValues(ref readOnlySequence, ref accumulator, isFinalBlock: true); + Assert.True(readOnlySequence.IsEmpty); + + Assert.Equal(3, accumulator.KeyCount); + var dict = accumulator.GetResults(); + Assert.Equal("bar", dict["foo"]); + Assert.Equal("boo", dict["baz"]); + Assert.Equal("", dict["t"]); + } + [Theory] [MemberData(nameof(Encodings))] public void TryParseFormValues_MultiSegmentWithArrayPoolAcrossSegmentsWorks(Encoding encoding) diff --git a/src/Identity/Extensions.Core/src/AuthenticatorTokenProvider.cs b/src/Identity/Extensions.Core/src/AuthenticatorTokenProvider.cs index 9f611e44fb..f067e398c2 100644 --- a/src/Identity/Extensions.Core/src/AuthenticatorTokenProvider.cs +++ b/src/Identity/Extensions.Core/src/AuthenticatorTokenProvider.cs @@ -48,7 +48,7 @@ namespace Microsoft.AspNetCore.Identity { var key = await manager.GetAuthenticatorKeyAsync(user); int code; - if (!int.TryParse(token, out code)) + if (key == null || !int.TryParse(token, out code)) { return false; } diff --git a/src/Identity/UI/ref/Microsoft.AspNetCore.Identity.UI.netcoreapp.cs b/src/Identity/UI/ref/Microsoft.AspNetCore.Identity.UI.netcoreapp.cs index 946e9c778c..73b686d1e6 100644 --- a/src/Identity/UI/ref/Microsoft.AspNetCore.Identity.UI.netcoreapp.cs +++ b/src/Identity/UI/ref/Microsoft.AspNetCore.Identity.UI.netcoreapp.cs @@ -108,7 +108,6 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal public string ReturnUrl { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } public virtual System.Threading.Tasks.Task OnGetAsync(string returnUrl = null) { throw null; } public virtual System.Threading.Tasks.Task OnPostAsync(string returnUrl = null) { throw null; } - public virtual System.Threading.Tasks.Task OnPostSendVerificationEmailAsync() { throw null; } public partial class InputModel { public InputModel() { } @@ -177,7 +176,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal public bool DisplayConfirmAccountLink { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } public string Email { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } public string EmailConfirmationUrl { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } - public virtual System.Threading.Tasks.Task OnGetAsync(string email) { throw null; } + public virtual System.Threading.Tasks.Task OnGetAsync(string email, string returnUrl = null) { throw null; } } [Microsoft.AspNetCore.Authorization.AllowAnonymousAttribute] public abstract partial class RegisterModel : Microsoft.AspNetCore.Mvc.RazorPages.PageModel @@ -627,7 +626,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V4.Pages.Account.Internal public bool DisplayConfirmAccountLink { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } public string Email { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } public string EmailConfirmationUrl { [System.Runtime.CompilerServices.CompilerGeneratedAttribute]get { throw null; } [System.Runtime.CompilerServices.CompilerGeneratedAttribute]set { } } - public virtual System.Threading.Tasks.Task OnGetAsync(string email) { throw null; } + public virtual System.Threading.Tasks.Task OnGetAsync(string email, string returnUrl = null) { throw null; } } [Microsoft.AspNetCore.Authorization.AllowAnonymousAttribute] public abstract partial class RegisterModel : Microsoft.AspNetCore.Mvc.RazorPages.PageModel diff --git a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml index 8ebfba2d1b..9b17733fbc 100644 --- a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml +++ b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml @@ -41,9 +41,6 @@

    Register as a new user

    -

    - -

    diff --git a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml.cs b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml.cs index 74ec7bb1cd..5c8af937ce 100644 --- a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml.cs +++ b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Login.cshtml.cs @@ -92,12 +92,6 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal /// directly from your code. This API may change or be removed in future releases. /// public virtual Task OnPostAsync(string returnUrl = null) => throw new NotImplementedException(); - - /// - /// This API supports the ASP.NET Core Identity default UI infrastructure and is not intended to be used - /// directly from your code. This API may change or be removed in future releases. - /// - public virtual Task OnPostSendVerificationEmailAsync() => throw new NotImplementedException(); } internal class LoginModel : LoginModel where TUser : class @@ -105,15 +99,12 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal private readonly UserManager _userManager; private readonly SignInManager _signInManager; private readonly ILogger _logger; - private readonly IEmailSender _emailSender; public LoginModel(SignInManager signInManager, ILogger logger, - UserManager userManager, - IEmailSender emailSender) + UserManager userManager) { _userManager = userManager; _signInManager = signInManager; - _emailSender = emailSender; _logger = logger; } @@ -169,34 +160,5 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal // If we got this far, something failed, redisplay form return Page(); } - - public override async Task OnPostSendVerificationEmailAsync() - { - if (!ModelState.IsValid) - { - return Page(); - } - - var user = await _userManager.FindByEmailAsync(Input.Email); - if (user == null) - { - ModelState.AddModelError(string.Empty, "Verification email sent. Please check your email."); - } - - var userId = await _userManager.GetUserIdAsync(user); - var code = await _userManager.GenerateEmailConfirmationTokenAsync(user); - var callbackUrl = Url.Page( - "/Account/ConfirmEmail", - pageHandler: null, - values: new { userId = userId, code = code }, - protocol: Request.Scheme); - await _emailSender.SendEmailAsync( - Input.Email, - "Confirm your email", - $"Please confirm your account by clicking here."); - - ModelState.AddModelError(string.Empty, "Verification email sent. Please check your email."); - return Page(); - } } } diff --git a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Register.cshtml.cs b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Register.cshtml.cs index 4b2a418d8a..ade1e60d2a 100644 --- a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Register.cshtml.cs +++ b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/Register.cshtml.cs @@ -147,7 +147,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal var callbackUrl = Url.Page( "/Account/ConfirmEmail", pageHandler: null, - values: new { area = "Identity", userId = userId, code = code }, + values: new { area = "Identity", userId = userId, code = code, returnUrl = returnUrl }, protocol: Request.Scheme); await _emailSender.SendEmailAsync(Input.Email, "Confirm your email", @@ -155,7 +155,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal if (_userManager.Options.SignIn.RequireConfirmedAccount) { - return RedirectToPage("RegisterConfirmation", new { email = Input.Email }); + return RedirectToPage("RegisterConfirmation", new { email = Input.Email, returnUrl = returnUrl }); } else { diff --git a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/RegisterConfirmation.cshtml.cs b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/RegisterConfirmation.cshtml.cs index 39db719ff9..0220bb7bd1 100644 --- a/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/RegisterConfirmation.cshtml.cs +++ b/src/Identity/UI/src/Areas/Identity/Pages/V3/Account/RegisterConfirmation.cshtml.cs @@ -43,7 +43,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal /// This API supports the ASP.NET Core Identity default UI infrastructure and is not intended to be used /// directly from your code. This API may change or be removed in future releases. /// - public virtual Task OnGetAsync(string email) => throw new NotImplementedException(); + public virtual Task OnGetAsync(string email, string returnUrl = null) => throw new NotImplementedException(); } internal class RegisterConfirmationModel : RegisterConfirmationModel where TUser : class @@ -57,12 +57,13 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal _sender = sender; } - public override async Task OnGetAsync(string email) + public override async Task OnGetAsync(string email, string returnUrl = null) { if (email == null) { return RedirectToPage("/Index"); } + returnUrl = returnUrl ?? Url.Content("~/"); var user = await _userManager.FindByEmailAsync(email); if (user == null) @@ -81,7 +82,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V3.Pages.Account.Internal EmailConfirmationUrl = Url.Page( "/Account/ConfirmEmail", pageHandler: null, - values: new { area = "Identity", userId = userId, code = code }, + values: new { area = "Identity", userId = userId, code = code, returnUrl = returnUrl }, protocol: Request.Scheme); } diff --git a/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/Register.cshtml.cs b/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/Register.cshtml.cs index 512adeb754..8e2a7e2faf 100644 --- a/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/Register.cshtml.cs +++ b/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/Register.cshtml.cs @@ -146,7 +146,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V4.Pages.Account.Internal var callbackUrl = Url.Page( "/Account/ConfirmEmail", pageHandler: null, - values: new { area = "Identity", userId = userId, code = code }, + values: new { area = "Identity", userId = userId, code = code, returnUrl = returnUrl }, protocol: Request.Scheme); await _emailSender.SendEmailAsync(Input.Email, "Confirm your email", @@ -154,7 +154,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V4.Pages.Account.Internal if (_userManager.Options.SignIn.RequireConfirmedAccount) { - return RedirectToPage("RegisterConfirmation", new { email = Input.Email }); + return RedirectToPage("RegisterConfirmation", new { email = Input.Email, returnUrl = returnUrl }); } else { diff --git a/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/RegisterConfirmation.cshtml.cs b/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/RegisterConfirmation.cshtml.cs index aa32c17361..7b88864fa0 100644 --- a/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/RegisterConfirmation.cshtml.cs +++ b/src/Identity/UI/src/Areas/Identity/Pages/V4/Account/RegisterConfirmation.cshtml.cs @@ -43,7 +43,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V4.Pages.Account.Internal /// This API supports the ASP.NET Core Identity default UI infrastructure and is not intended to be used /// directly from your code. This API may change or be removed in future releases. /// - public virtual Task OnGetAsync(string email) => throw new NotImplementedException(); + public virtual Task OnGetAsync(string email, string returnUrl = null) => throw new NotImplementedException(); } internal class RegisterConfirmationModel : RegisterConfirmationModel where TUser : class @@ -57,12 +57,13 @@ namespace Microsoft.AspNetCore.Identity.UI.V4.Pages.Account.Internal _sender = sender; } - public override async Task OnGetAsync(string email) + public override async Task OnGetAsync(string email, string returnUrl = null) { if (email == null) { return RedirectToPage("/Index"); } + returnUrl = returnUrl ?? Url.Content("~/"); var user = await _userManager.FindByEmailAsync(email); if (user == null) @@ -81,7 +82,7 @@ namespace Microsoft.AspNetCore.Identity.UI.V4.Pages.Account.Internal EmailConfirmationUrl = Url.Page( "/Account/ConfirmEmail", pageHandler: null, - values: new { area = "Identity", userId = userId, code = code }, + values: new { area = "Identity", userId = userId, code = code, returnUrl = returnUrl }, protocol: Request.Scheme); } diff --git a/src/Identity/UI/src/Areas/Identity/Pages/V4/_Layout.cshtml b/src/Identity/UI/src/Areas/Identity/Pages/V4/_Layout.cshtml index 21f5ba6ee3..c19e8e2029 100644 --- a/src/Identity/UI/src/Areas/Identity/Pages/V4/_Layout.cshtml +++ b/src/Identity/UI/src/Areas/Identity/Pages/V4/_Layout.cshtml @@ -56,12 +56,13 @@