E2E tests for cascading parameters generally

This commit is contained in:
Steve Sanderson 2018-10-15 14:26:55 +01:00
parent 18df30568c
commit 7530ad9a26
9 changed files with 202 additions and 0 deletions

View File

@ -56,4 +56,12 @@ namespace Microsoft.AspNetCore.Blazor.E2ETest.ServerExecutionTests
{
}
}
public class ServerCascadingValueTest : CascadingValueTest
{
public ServerCascadingValueTest(BrowserFixture browserFixture, ToggleExecutionModeServerFixture<Program> serverFixture, ITestOutputHelper output)
: base(browserFixture, serverFixture.WithServerExecution(), output)
{
}
}
}

View File

@ -0,0 +1,86 @@
// 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;
using Microsoft.AspNetCore.Blazor.E2ETest.Infrastructure;
using Microsoft.AspNetCore.Blazor.E2ETest.Infrastructure.ServerFixtures;
using OpenQA.Selenium;
using Xunit;
using Xunit.Abstractions;
namespace Microsoft.AspNetCore.Blazor.E2ETest.Tests
{
public class CascadingValueTest : BasicTestAppTestBase
{
public CascadingValueTest(
BrowserFixture browserFixture,
ToggleExecutionModeServerFixture<Program> serverFixture,
ITestOutputHelper output)
: base(browserFixture, serverFixture, output)
{
Navigate(ServerPathBase, noReload: !serverFixture.UsingAspNetHost);
MountTestComponent<BasicTestApp.CascadingValueTest.CascadingValueSupplier>();
}
[Fact]
public void CanUpdateValuesMatchedByType()
{
var currentCount = Browser.FindElement(By.Id("current-count"));
var incrementButton = Browser.FindElement(By.Id("increment-count"));
// We have the correct initial value
WaitAssert.Equal("100", () => currentCount.Text);
// Updates are propagated
incrementButton.Click();
WaitAssert.Equal("101", () => currentCount.Text);
incrementButton.Click();
WaitAssert.Equal("102", () => currentCount.Text);
// Didn't re-render unrelated descendants
Assert.Equal("1", Browser.FindElement(By.Id("receive-by-interface-num-renders")).Text);
}
[Fact]
public void CanUpdateValuesMatchedByName()
{
var currentFlag1Value = Browser.FindElement(By.Id("flag-1"));
var currentFlag2Value = Browser.FindElement(By.Id("flag-2"));
WaitAssert.Equal("False", () => currentFlag1Value.Text);
WaitAssert.Equal("False", () => currentFlag2Value.Text);
// Observe that the correct cascading parameter updates
Browser.FindElement(By.Id("toggle-flag-1")).Click();
WaitAssert.Equal("True", () => currentFlag1Value.Text);
WaitAssert.Equal("False", () => currentFlag2Value.Text);
Browser.FindElement(By.Id("toggle-flag-2")).Click();
WaitAssert.Equal("True", () => currentFlag1Value.Text);
WaitAssert.Equal("True", () => currentFlag2Value.Text);
// Didn't re-render unrelated descendants
Assert.Equal("1", Browser.FindElement(By.Id("receive-by-interface-num-renders")).Text);
}
[Fact]
public void CanUpdateFixedValuesMatchedByInterface()
{
var currentCount = Browser.FindElement(By.Id("current-count"));
var decrementButton = Browser.FindElement(By.Id("decrement-count"));
// We have the correct initial value
WaitAssert.Equal("100", () => currentCount.Text);
// Updates are propagated
decrementButton.Click();
WaitAssert.Equal("99", () => currentCount.Text);
decrementButton.Click();
WaitAssert.Equal("98", () => currentCount.Text);
// Renders the descendant the same number of times we triggered
// events on it, because we always re-render components after they
// have an event
Assert.Equal("3", Browser.FindElement(By.Id("receive-by-interface-num-renders")).Text);
}
}
}

View File

@ -0,0 +1,9 @@
@*
The only purpose of this component is to validate that cascaded value updates
can pass through entirely unrelated components that wouldn't normally rerender
their children when they themselves are being rerendered.
*@
<CascadingValueReceiveByType />
<CascadingValueReceiveByName />
<CascadingValueReceiveFixedByInterface />

View File

@ -0,0 +1,16 @@
@*
This component is to show that we can differentiate cascaded values
by name if they are of the same type.
*@
<p>
Flag 1: <strong id="flag-1">@MyFlag1</strong>
</p>
<p>
Flag 2: <strong id="flag-2">@MyFlag2</strong>
</p>
@functions {
[CascadingParameter(Name = "TestFlag1")] bool MyFlag1 { get; set; }
[CascadingParameter(Name = "TestFlag2")] bool MyFlag2 { get; set; }
}

View File

@ -0,0 +1,8 @@
<p>
Current count:
<strong id="current-count">@CurrentCounter.NumClicks</strong>
</p>
@functions {
[CascadingParameter] CounterDTO CurrentCounter { get; set; }
}

View File

@ -0,0 +1,21 @@
@*
This component is to show that:
1. We can match a cascading parameter based on interface
2. Since the supplied value is fixed (see CascadingValueSupplier.cshtml),
ancestor renders don't trigger descendant renders even though the
supplied value type is mutable.
*@
@{ numRenders++; }
<p>
@(nameof(CascadingValueReceiveFixedByInterface)) render count:
<strong id="receive-by-interface-num-renders">@numRenders</strong>
<button id="decrement-count" onclick=@Ancestor.DecrementCount>Decrement</button>
</p>
@functions {
int numRenders = 0;
[CascadingParameter] ICanDecrement Ancestor { get; set; }
}

View File

@ -0,0 +1,33 @@
@implements ICanDecrement
@*
While it looks somewhat ridiculous to nest so many CascadingValue components,
it simplifies the E2E test and is not intended as a representative use case.
Each of the CascadingValue components here is configured differently for the test.
*@
<CascadingValue Value=this Fixed=true>
<CascadingValue Value=counterState>
<CascadingValue Name="TestFlag1" Value="currentFlagValue1">
<CascadingValue Name="TestFlag2" Value="currentFlagValue2">
<CascadingValueIntermediary />
</CascadingValue>
</CascadingValue>
</CascadingValue>
</CascadingValue>
<p><button id="increment-count" onclick=@counterState.IncrementCount>Increment</button></p>
<p><label><input type="checkbox" id="toggle-flag-1" bind=currentFlagValue1 /> Flag 1</label></p>
<p><label><input type="checkbox" id="toggle-flag-2" bind=currentFlagValue2 /> Flag 2</label></p>
@functions {
CounterDTO counterState = new CounterDTO { NumClicks = 100 };
bool currentFlagValue1;
bool currentFlagValue2;
public void DecrementCount()
{
counterState.NumClicks--;
StateHasChanged();
}
}

View File

@ -0,0 +1,20 @@
// 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 BasicTestApp.CascadingValueTest
{
public class CounterDTO
{
public int NumClicks { get; set; }
public void IncrementCount()
{
NumClicks++;
}
}
public interface ICanDecrement
{
void DecrementCount();
}
}

View File

@ -41,6 +41,7 @@
<option value="BasicTestApp.HtmlEncodedChildContent">ChildContent HTML Encoded Block</option>
<option value="BasicTestApp.RazorTemplates">Razor Templates</option>
<option value="BasicTestApp.MultipleChildContent">Multiple child content</option>
<option value="BasicTestApp.CascadingValueTest.CascadingValueSupplier">Cascading values</option>
</select>
@if (SelectedComponentType != null)