Skip to content

Commit 7e2c848

Browse files
committed
Bump NuGet packages, add Async.razor test
All NuGet packages actualized, required some fixes Add Async.razor test: Multiple renders triggered by StateHasChanged() need to be specified in the expectRenders int argument (instead of the old expectRender bool).
1 parent efb250b commit 7e2c848

File tree

59 files changed

+683
-169
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

59 files changed

+683
-169
lines changed

asp.websharper.sln

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11

22
Microsoft Visual Studio Solution File, Format Version 12.00
3-
# Visual Studio Version 16
4-
VisualStudioVersion = 16.0.29806.167
3+
# Visual Studio Version 17
4+
VisualStudioVersion = 17.1.32407.343
55
MinimumVisualStudioVersion = 10.0.40219.1
66
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "asplib.core", "src\asplib.core\asplib.core.csproj", "{4C3371F0-AD02-4E39-97CA-EBD1C84D85D2}"
77
EndProject

doc/blazor.md

Lines changed: 64 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
* [The RenderMain override](#the-rendermain-override)
1414
* [`EditForm` handling](#editform-handling)
1515
* [`select` and `InputSelect` inputs](#select-and-inputselect-inputs)
16+
* [Multiple async renders](#multiple-async-renders)
1617
* [Comparison with bUnit](#comparison-with-bunit)
1718
* [Semantic HTML comparison in bUnit](#semantic-html-comparison-in-bunit)
1819
* [The `BUnitTestContext`](#the-bunittestcontext)
@@ -351,12 +352,71 @@ currently cannot be selected by its instance, but individual options clicked on
351352
by CSS selectors like this multi select example:
352353

353354
```csharp
354-
Click(By.CssSelector, "#saladSelection > option[value=Corn]", expectRender: false);
355-
Click(By.CssSelector, "#saladSelection > option[value=Lentils]", expectRender: false);
355+
Click(By.CssSelector, "#saladSelection > option[value=Corn]", expectRenders: 0);
356+
Click(By.CssSelector, "#saladSelection > option[value=Lentils]", expectRenders: 0);
356357
```
357358

358-
The non-default `expectRender: false` has to be added to prevent triggering
359-
`TestFocus` synchronization.
359+
The non-default `expectRenders: 0` has to be added to prevent triggering
360+
`TestFocus` synchronization when there is no server action.
361+
362+
363+
## Multiple async renders
364+
365+
The optional `expectRenders` parameter on the `Click` method default to 1 and
366+
replaces the original expectRender bool which just discriminated whether a
367+
rendering is expected to happen (usually) or not (e.g. when selecting an
368+
option).
369+
370+
But when awaiting another async method in an async event handler, Blazor will
371+
return to the caller method from the framework, allowing it to re-render the
372+
component. The `AutoResetEvent` from `TestFocus` needs to be awaited as many
373+
times as a re-rendering is triggered, otherwise it will continue too early.
374+
375+
The `Async.razor` example page specifically exposes that property of Blazor. The
376+
core is the following button click event handler:
377+
378+
```
379+
public static int Iterations = 100;
380+
public CountModel model = new(Iterations);
381+
382+
public async Task Start()
383+
{
384+
while (model.Counter > 0)
385+
{
386+
model.Counter--;
387+
await Task.Delay(1);
388+
if (model.Counter % 2 == 0) // only render each 2nd time
389+
{
390+
StateHasChanged();
391+
}
392+
}
393+
}
394+
```
395+
396+
The corresponding test methods with a given iteration count either need to wait
397+
for the rendering cascade to finish (`NonSynchronized`) - or to specify the
398+
exact expected number of renderings in advance (`Synchronized`):
399+
400+
```
401+
[Test]
402+
public void NonSynchronized()
403+
{
404+
Navigate("/async");
405+
Assert.That(Component.countNumber.Value, Is.EqualTo(Async.Iterations));
406+
Click(Component.startButton);
407+
this.AssertPoll(() => Component.countNumber.Value, () => Is.EqualTo(0));
408+
}
409+
410+
[Test]
411+
public void Synchronized()
412+
{
413+
Navigate("/async");
414+
Assert.That(Component.countNumber.Value, Is.EqualTo(Async.Iterations));
415+
// Will always render once plus additionally half of the iterations
416+
cut.Click(cut.Instance.startButton, expectRenders: (Async.Iterations / 2) + 1);
417+
Assert.That(Component.countNumber.Value, Is.EqualTo(0));
418+
}
419+
```
360420

361421

362422
## Comparison with bUnit

src/apicaller.core/apicaller.core.csproj

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,13 @@
77
</PropertyGroup>
88

99
<ItemGroup>
10-
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.8" />
11-
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="6.0.8">
10+
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.10" />
11+
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="6.0.10">
1212
<PrivateAssets>all</PrivateAssets>
1313
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
1414
</PackageReference>
1515
<PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="6.0.0" />
16-
<PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="6.0.8" />
16+
<PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="6.0.10" />
1717
</ItemGroup>
1818

1919
<ItemGroup>

src/apiservice.core/apiservice.core.csproj

Lines changed: 6 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -7,28 +7,19 @@
77
</PropertyGroup>
88

99
<ItemGroup>
10-
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.8" />
11-
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.8">
10+
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.10" />
11+
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.10" />
12+
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.10">
1213
<PrivateAssets>all</PrivateAssets>
1314
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
1415
</PackageReference>
15-
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.8" />
16-
</ItemGroup>
17-
18-
<ItemGroup>
19-
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.8" />
20-
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.8" />
21-
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.8">
22-
<PrivateAssets>all</PrivateAssets>
23-
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
24-
</PackageReference>
25-
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="6.0.8">
16+
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="6.0.10">
2617
<PrivateAssets>all</PrivateAssets>
2718
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
2819
</PackageReference>
2920
<PackageReference Include="Microsoft.Extensions.Logging.Debug" Version="6.0.0" />
30-
<PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="6.0.8" />
31-
<PackageReference Include="System.Data.SqlClient" Version="4.8.3" />
21+
<PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="6.0.10" />
22+
<PackageReference Include="System.Data.SqlClient" Version="4.8.4" />
3223
</ItemGroup>
3324

3425
<ItemGroup>

src/apitest.core/apicaller/Controllers/CallControllerTest.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ private AccesscodeController ServiceController
4747
get { return (AccesscodeController)StaticControllerExtension.GetController(); }
4848
}
4949

50-
[OneTimeSetUp]
50+
[SetUp] // instead of OneTimeSetUp, enforce a new session
5151
public void ConfigureServices()
5252
{
5353
this.configuration = ServiceProvider.Configuration;

src/apitest.core/apitest.core.csproj

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,14 +9,14 @@
99
</PropertyGroup>
1010

1111
<ItemGroup>
12-
<PackageReference Include="Microsoft.AspNetCore.TestHost" Version="6.0.8" />
12+
<PackageReference Include="Microsoft.AspNetCore.TestHost" Version="6.0.10" />
1313
<PackageReference Include="nunit" Version="3.13.3" />
1414
<PackageReference Include="NUnit3TestAdapter" Version="4.2.1">
1515
<PrivateAssets>all</PrivateAssets>
1616
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
1717
</PackageReference>
18-
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.3.0" />
19-
<PackageReference Include="System.Data.SqlClient" Version="4.8.3" />
18+
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.3.2" />
19+
<PackageReference Include="System.Data.SqlClient" Version="4.8.4" />
2020
</ItemGroup>
2121

2222
<ItemGroup>

src/asp.blazor/Models/CountModel.cs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
namespace asp.blazor.Models
2+
{
3+
/// <summary>
4+
/// For Async.razor
5+
/// </summary>
6+
public class CountModel
7+
{
8+
public CountModel(int initialize)
9+
{
10+
Counter = initialize;
11+
}
12+
13+
public int Counter = 0;
14+
}
15+
}

src/asp.blazor/Pages/Async.razor

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
@page "/async"
2+
3+
@using asplib.Components
4+
@inherits StaticComponentBase
5+
6+
<h3>Async Countdown</h3>
7+
8+
<EditForm Model="@model" OnValidSubmit="@Start">
9+
<InputNumber @bind-Value="model.Counter" @ref="countNumber"></InputNumber>
10+
<button type="submit" @ref="startButton">Start</button>
11+
</EditForm>
12+
13+
@code {
14+
public static int Iterations = 100;
15+
public CountModel model = new(Iterations);
16+
public InputNumber<int> countNumber = default!;
17+
public ElementReference startButton = default!;
18+
19+
public async Task Start()
20+
{
21+
while (model.Counter > 0)
22+
{
23+
model.Counter--;
24+
// Await to return to the caller, allow it to additionally render:
25+
//await Task.Yield(); // with zero delay not working in the asptestrunnder.blazor, only from the VS debugger directly
26+
await Task.Delay(1);
27+
if (model.Counter % 2 == 0) // only render each 2nd time
28+
{
29+
StateHasChanged();
30+
}
31+
}
32+
}
33+
}

src/asp.blazor/_Imports.razor

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,3 +10,4 @@
1010
@using asp.blazor
1111
@using asp.blazor.Shared
1212
@using asp.blazor.Components
13+
@using asp.blazor.Models

src/asp.blazor/asp.blazor.csproj

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,9 +22,9 @@
2222
</ItemGroup>
2323

2424
<ItemGroup>
25-
<PackageReference Include="Selenium.WebDriver" Version="4.4.0" />
26-
<PackageReference Include="Selenium.WebDriver.ChromeDriver" Version="104.0.5112.7900" />
27-
<PackageReference Include="Selenium.WebDriver.MSEdgeDriver" Version="104.0.1293.54" />
25+
<PackageReference Include="Selenium.WebDriver" Version="4.5.1" />
26+
<PackageReference Include="Selenium.WebDriver.ChromeDriver" Version="106.0.5249.6100" />
27+
<PackageReference Include="Selenium.WebDriver.MSEdgeDriver" Version="106.0.1370.34" />
2828
</ItemGroup>
2929

3030
<ItemGroup>

0 commit comments

Comments
 (0)