Skip to content

Commit f951168

Browse files
authored
Collection simplification (#34531)
1 parent a52acaf commit f951168

26 files changed

+434
-54
lines changed

aspnetcore/blazor/call-web-api.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -662,7 +662,7 @@ public class CookieHandler : DelegatingHandler
662662
HttpRequestMessage request, CancellationToken cancellationToken)
663663
{
664664
request.SetBrowserRequestCredentials(BrowserRequestCredentials.Include);
665-
request.Headers.Add("X-Requested-With", ["XMLHttpRequest"]);
665+
request.Headers.Add("X-Requested-With", [ "XMLHttpRequest" ]);
666666

667667
return base.SendAsync(request, cancellationToken);
668668
}
@@ -694,7 +694,7 @@ When composing an <xref:System.Net.Http.HttpRequestMessage>, set the browser req
694694
var requestMessage = new HttpRequestMessage() { ... };
695695

696696
requestMessage.SetBrowserRequestCredentials(BrowserRequestCredentials.Include);
697-
requestMessage.Headers.Add("X-Requested-With", ["XMLHttpRequest"]);
697+
requestMessage.Headers.Add("X-Requested-With", [ "XMLHttpRequest" ]);
698698
```
699699

700700
## `HttpClient` and `HttpRequestMessage` with Fetch API request options

aspnetcore/blazor/components/class-libraries-and-static-server-side-rendering.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -93,11 +93,11 @@ Reusable Razor components may include forms (either `<form>` or `<EditForm>`), a
9393
Consider the following example:
9494

9595
```razor
96-
<EditForm Enhance FormName="NewProduct" Model="Model" OnValidSubmit="SaveProduct">
96+
<EditForm Enhance FormName="NewProduct" Model="Model" OnValidSubmit="Save">
9797
<DataAnnotationsValidator />
9898
<ValidationSummary />
9999
100-
<p><label>Name: <InputText @bind-Value="Item.Name" /></label></p>
100+
<p><label>Name: <InputText @bind-Value="Model!.Name" /></label></p>
101101
102102
<button type="submit">Submit</button>
103103
</EditForm>

aspnetcore/blazor/components/data-binding.md

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -399,6 +399,67 @@ Binding supports [`multiple`](https://developer.mozilla.org/docs/Web/HTML/Attrib
399399

400400
`BindMultipleInput.razor`:
401401

402+
:::moniker-end
403+
404+
:::moniker range=">= aspnetcore-8.0"
405+
406+
```razor
407+
@page "/bind-multiple-input"
408+
409+
<h1>Bind Multiple <code>input</code>Example</h1>
410+
411+
<p>
412+
<label>
413+
Select one or more cars:
414+
<select @onchange="SelectedCarsChanged" multiple>
415+
<option value="audi">Audi</option>
416+
<option value="jeep">Jeep</option>
417+
<option value="opel">Opel</option>
418+
<option value="saab">Saab</option>
419+
<option value="volvo">Volvo</option>
420+
</select>
421+
</label>
422+
</p>
423+
424+
<p>
425+
Selected Cars: @string.Join(", ", SelectedCars)
426+
</p>
427+
428+
<p>
429+
<label>
430+
Select one or more cities:
431+
<select @bind="SelectedCities" multiple>
432+
<option value="bal">Baltimore</option>
433+
<option value="la">Los Angeles</option>
434+
<option value="pdx">Portland</option>
435+
<option value="sf">San Francisco</option>
436+
<option value="sea">Seattle</option>
437+
</select>
438+
</label>
439+
</p>
440+
441+
<span>
442+
Selected Cities: @string.Join(", ", SelectedCities)
443+
</span>
444+
445+
@code {
446+
public string[] SelectedCars { get; set; } = [];
447+
public string[] SelectedCities { get; set; } = [ "bal", "sea" ];
448+
449+
private void SelectedCarsChanged(ChangeEventArgs e)
450+
{
451+
if (e.Value is not null)
452+
{
453+
SelectedCars = (string[])e.Value;
454+
}
455+
}
456+
}
457+
```
458+
459+
:::moniker-end
460+
461+
:::moniker range=">= aspnetcore-6.0 < aspnetcore-8.0"
462+
402463
```razor
403464
@page "/bind-multiple-input"
404465
@@ -452,6 +513,10 @@ Binding supports [`multiple`](https://developer.mozilla.org/docs/Web/HTML/Attrib
452513
}
453514
```
454515

516+
:::moniker-end
517+
518+
:::moniker range=">= aspnetcore-6.0"
519+
455520
For information on how empty strings and `null` values are handled in data binding, see the [Binding `<select>` element options to C# object `null` values](#binding-select-element-options-to-c-object-null-values) section.
456521

457522
:::moniker-end

aspnetcore/blazor/components/virtualization.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -214,7 +214,7 @@ Change the `OnInitialized` method lambda to see the component display strings:
214214

215215
```csharp
216216
protected override void OnInitialized() =>
217-
stringList ??= new() { "Here's a string!", "Here's another string!" };
217+
stringList ??= [ "Here's a string!", "Here's another string!" ];
218218
```
219219

220220
:::moniker-end

aspnetcore/blazor/forms/validation.md

Lines changed: 111 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -353,6 +353,61 @@ The validation for the `Defense` ship classification only occurs on the server i
353353
354354
`Controllers/StarshipValidation.cs`:
355355

356+
:::moniker range=">= aspnetcore-8.0"
357+
358+
```csharp
359+
using Microsoft.AspNetCore.Authorization;
360+
using Microsoft.AspNetCore.Mvc;
361+
using BlazorSample.Shared;
362+
363+
namespace BlazorSample.Server.Controllers;
364+
365+
[Authorize]
366+
[ApiController]
367+
[Route("[controller]")]
368+
public class StarshipValidationController(
369+
ILogger<StarshipValidationController> logger)
370+
: ControllerBase
371+
{
372+
static readonly string[] scopeRequiredByApi = [ "API.Access" ];
373+
374+
[HttpPost]
375+
public async Task<IActionResult> Post(Starship model)
376+
{
377+
HttpContext.VerifyUserHasAnyAcceptedScope(scopeRequiredByApi);
378+
379+
try
380+
{
381+
if (model.Classification == "Defense" &&
382+
string.IsNullOrEmpty(model.Description))
383+
{
384+
ModelState.AddModelError(nameof(model.Description),
385+
"For a 'Defense' ship " +
386+
"classification, 'Description' is required.");
387+
}
388+
else
389+
{
390+
logger.LogInformation("Processing the form asynchronously");
391+
392+
// async ...
393+
394+
return Ok(ModelState);
395+
}
396+
}
397+
catch (Exception ex)
398+
{
399+
logger.LogError("Validation Error: {Message}", ex.Message);
400+
}
401+
402+
return BadRequest(ModelState);
403+
}
404+
}
405+
```
406+
407+
:::moniker-end
408+
409+
:::moniker range="< aspnetcore-8.0"
410+
356411
```csharp
357412
using Microsoft.AspNetCore.Authorization;
358413
using Microsoft.AspNetCore.Mvc;
@@ -402,6 +457,8 @@ public class StarshipValidationController(
402457
}
403458
```
404459

460+
:::moniker-end
461+
405462
Confirm or update the namespace of the preceding controller (`BlazorSample.Server.Controllers`) to match the app's controllers' namespace.
406463

407464
When a model binding validation error occurs on the server, an [`ApiController`](xref:web-api/index) (<xref:Microsoft.AspNetCore.Mvc.ApiControllerAttribute>) normally returns a [default bad request response](xref:web-api/index#default-badrequest-response) with a <xref:Microsoft.AspNetCore.Mvc.ValidationProblemDetails>. The response contains more data than just the validation errors, as shown in the following example when all of the fields of the `Starfleet Starship Database` form aren't submitted and the form fails validation:
@@ -411,10 +468,10 @@ When a model binding validation error occurs on the server, an [`ApiController`]
411468
"title": "One or more validation errors occurred.",
412469
"status": 400,
413470
"errors": {
414-
"Id": ["The Id field is required."],
415-
"Classification": ["The Classification field is required."],
416-
"IsValidatedDesign": ["This form disallows unapproved ships."],
417-
"MaximumAccommodation": ["Accommodation invalid (1-100000)."]
471+
"Id": [ "The Id field is required." ],
472+
"Classification": [ "The Classification field is required." ],
473+
"IsValidatedDesign": [ "This form disallows unapproved ships." ],
474+
"MaximumAccommodation": [ "Accommodation invalid (1-100000)." ]
418475
}
419476
}
420477
```
@@ -426,10 +483,10 @@ If the server API returns the preceding default JSON response, it's possible for
426483

427484
```json
428485
{
429-
"Id": ["The Id field is required."],
430-
"Classification": ["The Classification field is required."],
431-
"IsValidatedDesign": ["This form disallows unapproved ships."],
432-
"MaximumAccommodation": ["Accommodation invalid (1-100000)."]
486+
"Id": [ "The Id field is required." ],
487+
"Classification": [ "The Classification field is required." ],
488+
"IsValidatedDesign": [ "This form disallows unapproved ships." ],
489+
"MaximumAccommodation": [ "Accommodation invalid (1-100000)." ]
433490
}
434491
```
435492

@@ -951,6 +1008,50 @@ To ensure that a validation result is correctly associated with a field when usi
9511008

9521009
`CustomValidator.cs`:
9531010

1011+
:::moniker range=">= aspnetcore-8.0"
1012+
1013+
```csharp
1014+
using System;
1015+
using System.ComponentModel.DataAnnotations;
1016+
1017+
public class CustomValidator : ValidationAttribute
1018+
{
1019+
protected override ValidationResult IsValid(object? value,
1020+
ValidationContext validationContext)
1021+
{
1022+
...
1023+
1024+
return new ValidationResult("Validation message to user.",
1025+
[ validationContext.MemberName! ]);
1026+
}
1027+
}
1028+
```
1029+
1030+
:::moniker-end
1031+
1032+
:::moniker range=">= aspnetcore-6.0 < aspnetcore-8.0"
1033+
1034+
```csharp
1035+
using System;
1036+
using System.ComponentModel.DataAnnotations;
1037+
1038+
public class CustomValidator : ValidationAttribute
1039+
{
1040+
protected override ValidationResult IsValid(object? value,
1041+
ValidationContext validationContext)
1042+
{
1043+
...
1044+
1045+
return new ValidationResult("Validation message to user.",
1046+
new[] { validationContext.MemberName! });
1047+
}
1048+
}
1049+
```
1050+
1051+
:::moniker-end
1052+
1053+
:::moniker range="< aspnetcore-6.0"
1054+
9541055
```csharp
9551056
using System;
9561057
using System.ComponentModel.DataAnnotations;
@@ -968,6 +1069,8 @@ public class CustomValidator : ValidationAttribute
9681069
}
9691070
```
9701071

1072+
:::moniker-end
1073+
9711074
Inject services into custom validation attributes through the <xref:System.ComponentModel.DataAnnotations.ValidationContext>. The following example demonstrates a salad chef form that validates user input with dependency injection (DI).
9721075

9731076
The `SaladChef` class indicates the approved starship ingredient list for a Ten Forward salad.

aspnetcore/blazor/fundamentals/dependency-injection.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -579,7 +579,7 @@ public class CircuitServicesAccessor
579579
public IServiceProvider? Services
580580
{
581581
get => blazorServices.Value;
582-
set => blazorServices.Value = value;
582+
set => blazorServices.Value = value!;
583583
}
584584
}
585585

aspnetcore/blazor/fundamentals/routing.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -199,7 +199,7 @@ In the following example, the `Routes` component is in the server project, and t
199199
```razor
200200
<Router
201201
AppAssembly="..."
202-
AdditionalAssemblies="new[] { typeof(BlazorSample.Client._Imports).Assembly }">
202+
AdditionalAssemblies="[ typeof(BlazorSample.Client._Imports).Assembly ]">
203203
...
204204
</Router>
205205
```

aspnetcore/blazor/globalization-localization.md

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1042,11 +1042,11 @@ The component adopts the following approaches to work for either SSR or CSR comp
10421042
{ "es-CR", "Spanish (Costa Rica)" }
10431043
};
10441044
1045-
private CultureInfo[] supportedCultures = new[]
1046-
{
1047-
new CultureInfo("en-US"),
1048-
new CultureInfo("es-CR"),
1049-
};
1045+
private CultureInfo[] supportedCultures =
1046+
[
1047+
new CultureInfo("en-US"),
1048+
new CultureInfo("es-CR"),
1049+
];
10501050
10511051
private CultureInfo? selectedCulture;
10521052

aspnetcore/blazor/hybrid/class-libraries.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -186,10 +186,10 @@ namespace {APP NAMESPACE}.Services;
186186

187187
public class WeatherForecastService : IWeatherForecastService
188188
{
189-
private static readonly string[] Summaries = new[]
190-
{
189+
private static readonly string[] Summaries =
190+
[
191191
"Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot"
192-
};
192+
];
193193

194194
public async Task<WeatherForecast[]?> GetForecastAsync(DateTime startDate) =>
195195
await Task.FromResult(Enumerable.Range(1, 5)

aspnetcore/blazor/javascript-interoperability/call-javascript-from-dotnet.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1102,10 +1102,22 @@ The `{TIMEOUT}` placeholder is a <xref:System.TimeSpan> (for example, `TimeSpan.
11021102

11031103
Set a per-invocation timeout in component code. The specified timeout overrides the global timeout set by <xref:Microsoft.AspNetCore.Components.Server.CircuitOptions.JSInteropDefaultCallTimeout>:
11041104

1105+
:::moniker range=">= aspnetcore-8.0"
1106+
1107+
```csharp
1108+
var result = await JS.InvokeAsync<string>("{ID}", {TIMEOUT}, [ "Arg1" ]);
1109+
```
1110+
1111+
:::moniker-end
1112+
1113+
:::moniker range="< aspnetcore-8.0"
1114+
11051115
```csharp
11061116
var result = await JS.InvokeAsync<string>("{ID}", {TIMEOUT}, new[] { "Arg1" });
11071117
```
11081118

1119+
:::moniker-end
1120+
11091121
In the preceding example:
11101122

11111123
* The `{TIMEOUT}` placeholder is a <xref:System.TimeSpan> (for example, `TimeSpan.FromSeconds(80)`).

0 commit comments

Comments
 (0)