Purview.ZodSharp.Blazor
3.0.0-prerelease.2
dotnet add package Purview.ZodSharp.Blazor --version 3.0.0-prerelease.2
NuGet\Install-Package Purview.ZodSharp.Blazor -Version 3.0.0-prerelease.2
<PackageReference Include="Purview.ZodSharp.Blazor" Version="3.0.0-prerelease.2" />
<PackageVersion Include="Purview.ZodSharp.Blazor" Version="3.0.0-prerelease.2" />
<PackageReference Include="Purview.ZodSharp.Blazor" />
paket add Purview.ZodSharp.Blazor --version 3.0.0-prerelease.2
#r "nuget: Purview.ZodSharp.Blazor, 3.0.0-prerelease.2"
#:package Purview.ZodSharp.Blazor@3.0.0-prerelease.2
#addin nuget:?package=Purview.ZodSharp.Blazor&version=3.0.0-prerelease.2&prerelease
#tool nuget:?package=Purview.ZodSharp.Blazor&version=3.0.0-prerelease.2&prerelease
Purview.ZodSharp.Blazor
Blazor forms validated by ZodSharp on Blazor Server, Blazor
WebAssembly and Auto render mode (net11.0).
dotnet add package Purview.ZodSharp.Blazor
// Program.cs - the server AND the client project of a Blazor Web App.
builder.Services.AddZodSharpMyAppSharedSchemas(); // generated, trim-safe registration of your [ZodSchema] models
builder.Services.AddZodSharpBlazor();
AddZodSharpBlazor()does not validate your minimal APIs. It registers the validation bridge for form models only, so a server that also maps endpoints keeps them as they were. To have the .NET 11 pipeline validate ZodSharp-typed endpoint parameters too (a 400 before the handler runs), also callbuilder.Services.AddZodSharpValidation()(either order), or passAddZodSharpBlazor(validation => validation.ValidateParameters = true); opt endpoints out withDisableValidation().
Route 1: the standard <DataAnnotationsValidator />
<EditForm Model="order" OnValidSubmit="Save">
<DataAnnotationsValidator />
<InputText @bind-Value="order.Customer.Email" />
<ValidationMessage For="() => order.Customer.Email" />
<ValidationSummary />
</EditForm>
[ZodSchema] models validate with ZodSharp, including nested objects, collections and dictionaries, with no
[ValidatableType] and no Microsoft.Extensions.Validation generator - the generator does not flow to a
WebAssembly client, so this is what makes nested validation work there. A field change runs only that member's
own rules; async rules show the platform's pending and faulted states.
Route 2: <ZodValidator /> (full fidelity)
<EditForm Model="order" OnValidSubmit="Save">
<ZodValidator ValidateOn="ZodValidationTrigger.Input" DebounceMilliseconds="300" />
<ZodValidationMessage For="() => order.Customer.Email" ShowCode="true" />
<ZodValidationSummary GroupByPath="true" ShowUnionDetails="true" />
</EditForm>
- Keeps the full
ValidationError(code, category, origin, bounds, parameters) behind every message:editContext.GetZodErrors(() => order.Customer.Email),GetZodErrors(field),GetZodErrors(). ValidateOn:Submit,Change(default) orInputwithDebounceMilliseconds(each change supersedes and cancels the pending check). Submit-time validation always runs.Schema: an explicit validator for models without a registered one -ZodModelSchema.For<Order>(Z.Object().Field("Reference", Z.String().Min(3)).Build()).ValidateNestedOnFieldChange: a field change re-validates the whole owning object (cross-field rules).- With a
DataAnnotationsValidatoron the same form it records the full errors but leaves the messages toDataAnnotationsValidator, so nothing is shown twice, and logs one warning. Use one validator.
ZodValidationMessage and ZodValidationSummary render the same markup and CSS classes as the built-in
components, plus data-code/data-category.
Server errors onto the form
var response = await http.PostAsJsonAsync("/orders", order);
if (await response.TryReadZodValidationProblemAsync() is { } problem)
editContext.AddZodProblemDetails(problem); // cleared per field when the field changes
Reads Purview.ZodSharp.AspNetCore's issues[] (typed segments), or a plain errors dictionary, with
source-generated JSON metadata (trim- and AOT-safe). TryReadZodValidationProblemAsync and ZodValidationProblemDetails
come from Purview.ZodSharp.Http, which this package references.
Errors produced anywhere else go on the form the same way, by their typed paths:
var sent = await http.PostAsJsonValidatedAsync("/orders", order,
new OrderSchemaValidator(), AppJsonContext.Default.Order, services);
if (!sent.IsSuccess)
editContext.AddZodErrors(sent.Errors); // rejected before sending; cleared per field like server errors
AddZodErrors and AddZodProblemDetails replace each other's errors, GetZodErrors reads them back, and
ClearZodErrors removes them.
Static SSR client-side validation
zodsharp-validation.js ships as a static web asset and registers itself through a Blazor JavaScript initializer.
On the server, AddZodSharpClientValidation() (Purview.ZodSharp.AspNetCore) adds the matching rules - for
[StartsWith], [EndsWith], [Includes], [UUID], [Cuid2], [ULID], [IPAddress], [Cidr], [Regex],
[Int], [MultipleOf] and the bound attributes - to the form's data-rules payload, beside ASP.NET Core's
DataAnnotations rules.
Limitations:
- ASP.NET Core has no public API to add rules to its DataAnnotations provider, so ZodSharp decorates it and merges into its rendered payload. The payload format is pinned by contract tests.
- Async, service-aware and culture-sensitive rules, and custom rules whose metadata has no JavaScript equivalent, are enforced on the server only. .NET and JavaScript regular expressions differ at the edges.
- Client rules only improve the user experience; the server always validates the posted form.
Notes
- Blazor Server: validation services resolve from the circuit scope. In async validators use
IDbContextFactory<T>or an explicitly created scope rather than a scopedDbContext. - Don't validate in
OnInitializedof prerendered components; it would run once per render phase. - WebAssembly: prefer the generated
AddZodSharp{Assembly}Schemas()registration; assembly scanning is not trim-safe. - Value objects and other struct members: an error inside one (
Email.Value) is shown on the owning member's field (For="() => model.Email"), because a struct cannot be aFieldIdentifiermodel; a scalar value object's messages use the owning member's display name.
Documentation: https://purview.dev/docs/zodsharp/
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net11.0 is compatible. |
-
net11.0
- Microsoft.AspNetCore.Components.Forms (>= 11.0.0-rc.3.26522.148)
- Microsoft.AspNetCore.Components.Web (>= 11.0.0-rc.3.26522.148)
- Microsoft.Extensions.DependencyInjection (>= 11.0.0-rc.3.26522.148)
- Microsoft.Extensions.Validation (>= 11.0.0-rc.3.26522.148)
- Purview.ZodSharp (>= 3.0.0-prerelease.2)
- Purview.ZodSharp.Extensions.Validation (>= 3.0.0-prerelease.2)
- Purview.ZodSharp.Http (>= 3.0.0-prerelease.2)
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated |
|---|---|---|
| 3.0.0-prerelease.2 | 66 | 11/2/2026 |