![]() |
VOOZH | about |
dotnet add package OpenRiaServices.Hosting.AspNetCore --version 1.5.0
NuGet\Install-Package OpenRiaServices.Hosting.AspNetCore -Version 1.5.0
<PackageReference Include="OpenRiaServices.Hosting.AspNetCore" Version="1.5.0" />
<PackageVersion Include="OpenRiaServices.Hosting.AspNetCore" Version="1.5.0" />Directory.Packages.props
<PackageReference Include="OpenRiaServices.Hosting.AspNetCore" />Project file
paket add OpenRiaServices.Hosting.AspNetCore --version 1.5.0
#r "nuget: OpenRiaServices.Hosting.AspNetCore, 1.5.0"
#:package OpenRiaServices.Hosting.AspNetCore@1.5.0
#addin nuget:?package=OpenRiaServices.Hosting.AspNetCore&version=1.5.0Install as a Cake Addin
#tool nuget:?package=OpenRiaServices.Hosting.AspNetCore&version=1.5.0Install as a Cake Tool
This software will allow existing applications written for OpenRiaServices or WCF RIA Services to run on net6 and kestrel, making them future proof and improving their performance.
Hopefully it will allow you as a consumer to make large savings in development time, weeks or even man years, by not having to rewrite your application as well as allowing rapid development.
The software is provided free of charge, but I urge you to use some of the money saved by using this software to support Ukraine The civilian suffering due to the Russian invasion, the attacks on hospitals and other war crimes are enormous.
By using this project or its source code, for any purpose and in any shape or form, you grant your agreement to all the following statements:
This excludes usage by the Russian state, Russian state-owned companies, Russian education who spread propaganda instead of truth, anyone who work with the filtration camps, or finance the war by importing Russian oil or gas.
There is no documentation except for this yet readme, please see AspNetCoreWebsite project in repository for usage.
Create a new dotnet 6 web application dotnet new web or similar
Add a reference to OpenRiaServices.Hosting.AspNetCore
dotnet add package OpenRiaServices.Hosting.AspNetCore
Add a reference to OpenRiaServices.Server
Add one or more domainservices
[EnableClientAccess]
public class CityDomainService : DomainService
{
/* ..... */
}
For more documentation see https://openriaservices.gitbook.io/openriaservices/ee707348/ee707373 or samples https://github.com/OpenRIAServices/OpenRiaServices/blob/086ea8c8fcb115000749be6b2b01cd43bb95bf80/docs/gg602754.md#add-the-poco-class
Sample program:
using OpenRiaServices.Hosting.AspNetCore;
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddOpenRiaServices();
// Register DomainServices in DI
builder.Services.AddDomainService<CityDomainService>();
// OR builder.Services.AddDomainServices(AppDomain.CurrentDomain.GetAssemblies());
var app = builder.Build();
// Map OpenRiaServices routes , you can optionally add a prefix such as "/Services"
// This will automatically map all DomainServices that are registered in builder.Services
// Using routes similar to $"{DomainServiceName}/{MethodName}"
app.MapOpenRiaServices();
// OR app.MapOpenRiaServices(builder => { builder.AddDomainService<CityDomainService>(); }); to specify exactly the DomainServices to map which works better with Trimming
app.Run();
You can configure the hosting options by passing a callback to AddOpenRiaServices method.
Options include:
ExceptionHandler - A delegate that can be used to handle exceptions that occur during the execution of a DomainService method.
IncludeExceptionMessageInErrors - A boolean that determines if the exception message should be included in the error response.
ExceptionHandler and
ensuring that the message is not passed on to the client is "safe" and does not give to much information about the system to a potential hacker.IncludeExceptionStackTraceInErrors - A boolean that determines if the exception stack trace should be included in the error response.
Example setup:
builder.Services.AddOpenRiaServices(o => {
o.ExceptionHandler = (context, response) =>
{
// Pass all exceptions to client
response.ErrorMessage ??= context.Exception.Message;
};
// There is at least one test which test that checks that calls stacks of normal exceptions are passed to the client
// To get StackTrack of "normal" exceptions we need to pass them on to the user, as well as include stack traces
o.IncludeExceptionMessageInErrors = true;
o.IncludeExceptionStackTraceInErrors = true;
});
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddOpenRiaServices(o => { } )
.AddXmlSerialization();
You can remove default built in formats by calling ClearSerializationProviders.
The following sample will only accept and return plain text based xml
using MIME-type application/xml
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddOpenRiaServices(o => { } )
.ClearSerializationProviders()
.AddXmlSerialization();
You can configure reader quotas to limit resource consumption and mitigate denial-of-service (DoS) attacks. By default all quotas are set to their maximum values to preserve backward compatibility.
Configure XML serialization quotas:
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddOpenRiaServices()
.AddXmlSerialization(options =>
{
options.ReaderQuotas = new System.Xml.XmlDictionaryReaderQuotas
{
MaxStringContentLength = 1024 * 1024, // 1 MB
MaxArrayLength = 65536,
MaxDepth = 32,
};
});
Configure binary XML serialization quotas (for the default binary provider):
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddOpenRiaServices()
.ConfigureBinarySerialization(options =>
{
options.ReaderQuotas = new System.Xml.XmlDictionaryReaderQuotas
{
MaxStringContentLength = 1024 * 1024, // 1 MB
MaxArrayLength = 65536,
MaxDepth = 32,
};
});
You can choose between 3 different approaches to how the endpoint routes are generated.
You do this by adding the DomainServiceEndpointRoutePattern attribute to your assembly.
The options are WCF, FullName and ShortName.
WCF will generate the same routes as WCF RIA Services Some-Namespace-TypeName.svc/binary/Method
FullName will generate routes with the full name of the DomainService Some-Namespace-TypeName/MethodName will generate routes with the short name of the DomainService TypeName/MethodThe default will be changed to FullName which is the same as in WCF RIA Services.
[assembly: DomainServiceEndpointRoutePattern(EndpointRoutePattern.WCF)]
// or
[assembly: DomainServiceEndpointRoutePattern(EndpointRoutePattern.FullName)]
// or
[assembly: DomainServiceEndpointRoutePattern(EndpointRoutePattern.Name)]
If you want to change the route for a specific DomainService or need to map a DomainService to multiple routes you can specify
a route directly when adding domainservices during the MapOpenRiaServices call.
app.MapOpenRiaServices(builder =>
{
builder.AddDomainService<Cities.CityDomainService>("Cities-CityDomainService.svc/binary");
});
Since 0.4.0 any attivbute applied to Invoke/Query are added to the corresponding AspNetCore-Endpoint allowing the use of any AspNetCore endpoint middleware (not MVC specific filters, they must work with "minimal api's").
This means you can use standard aspnetcore Authentication and Authorization to validate most requests (but NOT indivudual Insert,Update,Delete methods, you can apply atttributes to your DomainService class for those). The validation will happen before the DomainService is even created, making them more powerful than built in attributes.
You can still (and probably should) use the OpenRiaServices specific attributes such as [RequiresAuthentication] or your own Authorization attributes
Simple authorization, which works on all methods.
You can use standard aspnetcore Authentication and Authorization to validate most requests (but NOT indivudual Insert, Update, Delete methods, you can apply atttributes to your DomainService class for those). The validation will happen before the DomainService is even created, making them more powerful than built in attributes.
The AspNetCore Sample shows how cookie based login similar to ASP.NET Membership provider can be handled. The change was added in #16: Add AspNetCore AuthenticationService You will need to tweak it so it validates credentials, assign correct Claims (Roles) to users and fits your choosen scheme for authentication.
For the client, you need to ensure that all HttpClients share the same CookieContainer and that the it is set to use to cookies (https://learn.microsoft.com/en-us/dotnet/api/system.net.http.httpclienthandler.usecookies?view=net-7.0#system-net-http-httpclienthandler-usecookies)
In Program.cs the following code is needed
Service registrations, adds cookie based authentication and enable Authorization
// Additional dependencies for cookie based AuthenticationService
builder.Services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme)
.AddCookie();
builder.Services.AddHttpContextAccessor();
builder.Services.AddAuthorization();
After the "application has been built" and the middleware is configured you should add Authentication (and Authorization if used). They should be added before OpenRiaServices
// Add authentication
app.UseAuthentication();
app.UseAuthorization();
// Enable OpenRiaServices
app.MapOpenRiaServices(....
A good idea is to protect your DomainServices, all of them or individual, by requiring authorization. The Authorization middleware should run before the DomainService is created so you will avoid any cost with creating the DomainService and it's dependencies, providing a much better protection against DOS.
IMPORANT: error message on the client will be different and not as user friendly as if the [RequiresAuthentication] attribute is used.
You might want to consider changing the HTTP status code to match 401 or similar instead of 404 (when it tries to redirect to missing "/Account/Login" endpoint)
Note: If you need to selectivly only require authentication for some Submit operations (Insert, Update, Delete or Entity Action) then remember to use [RequiresAuthentication]
Require request to all DomainServices be authorized using default authorization policy:
app.MapOpenRiaServices(builder =>
{
builder.AddDomainService<SampleDomainService>();
builder.AddDomainService<MyAuthenticationService>();
}).RequireAuthorization();
You can also control the setting per DomainService using code
app.MapOpenRiaServices(builder =>
{
builder.AddDomainService<SampleDomainService>()
.RequireAuthorization();
});
You can also control the setting per DomainService using attributes
[Authorize]
public class MyAuthenticationService : DomainService, IAuthentication<MyUser>
{
[AllowAnonymous]
public MyUser GetUser() {...}
Sample showing how to integrate the OutputCache middleware WARNING: Se caching documentation and ensure that any usage of output cache is not sent to the wrong user.
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddOpenRiaServices();
builder.Services.AddOutputCache(options =>
{
options.AddBasePolicy(builder => builder.NoCache());
});
builder.Services.AddDomainService<CacheTestDomainService>();
var app = builder.Build();
app.UseOutputCache();
[EnableClientAccess]
public class CacheTestDomainService : DomainService
{
[Invoke(HasSideEffects = false)]
public string NoCache()
=> DateTime.Now.ToString();
[Invoke(HasSideEffects = false)]
[Microsoft.AspNetCore.OutputCaching.OutputCache(Duration = 5)]
public string OutputCache()
=> DateTime.Now.ToString();
}
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net8.0 net8.0 is compatible. net8.0-android net8.0-android was computed. net8.0-browser net8.0-browser was computed. net8.0-ios net8.0-ios was computed. net8.0-maccatalyst net8.0-maccatalyst was computed. net8.0-macos net8.0-macos was computed. net8.0-tvos net8.0-tvos was computed. net8.0-windows net8.0-windows was computed. net9.0 net9.0 was computed. net9.0-android net9.0-android was computed. net9.0-browser net9.0-browser was computed. net9.0-ios net9.0-ios was computed. net9.0-maccatalyst net9.0-maccatalyst was computed. net9.0-macos net9.0-macos was computed. net9.0-tvos net9.0-tvos was computed. net9.0-windows net9.0-windows was computed. net10.0 net10.0 was computed. net10.0-android net10.0-android was computed. net10.0-browser net10.0-browser was computed. net10.0-ios net10.0-ios was computed. net10.0-maccatalyst net10.0-maccatalyst was computed. net10.0-macos net10.0-macos was computed. net10.0-tvos net10.0-tvos was computed. net10.0-windows net10.0-windows was computed. |
This package is not used by any NuGet packages.
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated | |
|---|---|---|---|
| 1.6.0-preview.1 | 41 | 6/17/2026 | |
| 1.5.0 | 86 | 6/11/2026 | |
| 1.4.0 | 1,082 | 4/2/2026 | |
| 1.4.0-preview.2 | 67 | 4/27/2026 | |
| 1.3.1 | 3,236 | 11/18/2024 | 1.3.1 is deprecated. |
| 1.3.0 | 295 | 11/14/2024 | 1.3.0 is deprecated. |
| 1.2.0 | 397 | 6/13/2024 | 1.2.0 is deprecated. |
| 1.1.0 | 373 | 3/14/2024 | 1.1.0 is deprecated. |
| 1.1.0-ci.9 | 164 | 3/14/2024 | 1.1.0-ci.9 is deprecated. |
| 1.0.0 | 397 | 1/11/2024 | 1.0.0 is deprecated. |
| 0.4.0 | 449 | 6/22/2023 | 0.4.0 is deprecated. |
| 0.4.0-preview.2 | 202 | 8/1/2023 | 0.4.0-preview.2 is deprecated. |
| 0.3.0 | 353 | 5/26/2023 | 0.3.0 is deprecated. |
| 0.2.1 | 410 | 4/14/2023 | 0.2.1 is deprecated. |
| 0.2.1-tags-v-5-3-0.8 | 232 | 4/14/2023 | 0.2.1-tags-v-5-3-0.8 is deprecated. |
| 0.2.0 | 555 | 11/25/2022 | 0.2.0 is deprecated. |
| 0.1.0 | 875 | 6/9/2022 | 0.1.0 is deprecated. |
For release notes see https://github.com/OpenRIAServices/OpenRiaServices/releases