-
Notifications
You must be signed in to change notification settings - Fork 0
Modules
With Hosuto modules you can create isolated parts of your application that will all run in their own host but share global settings and a DI container. As each module has it's own service provider you can register different services in each module. For example if you host a server component in one module you could configure another module to host a client of the same component. If you now distribute the application you can choose to run each module in it's own application or to run the modules in the same application.
To use modules first create a modules host in your applications main method. This host replaces the default .Net Generic Host.
Add a reference to the nuget package Dbosoft.Hosuto.Hosting and build the modules host from a ModulesHostBuilder:
static Task Main(string[] args)
{
var builder = ModulesHost.CreateDefaultBuilder(args);
// you can configure a modules host builder like a host builder.
// All configurations set with ConfigureHostConfiguration will be shared between all modules.
builder.UseEnvironment(EnvironmentName.Development);
return builder.RunConsoleAsync();
}
Then you can define your modules. A module is typical placed in its own assembly but this is not required. Modules have a convention based setup logic like the Startup class for Asp.Net Core.
public class SimpleModule
{
public void ConfigureServices(
IServiceCollection services)
{
[...]
The configure service method will configure the DI container of the module host. To do something useful you will typical have to register at least one HostedServices here.
The module has now to be added to the modules host builder:
static Task Main(string[] args)
{
var builder = ModulesHost.CreateDefaultBuilder(args);
[...]
builder.HostModule<SomeModule>();
return builder.RunConsoleAsync();
}
Hosuto supports also hosting of Asp.Net Core WebApplications in modules.
To enable the aspnetcore support you have to method UseAspNetCore
on ModulesHostBuilder:
For Asp.NetCore 3.0 or higher:
builder.HostModule<SampleWebModule>();
builder.UseAspNetCoreWithDefaults((module, webBuilder) =>
{
});
or without defaults
builder.HostModule<SampleWebModule>();
builder.UseAspNetCore((module, webBuilder) =>
{
});
For Asp.Net Core 2.0 and 2.1:
builder.HostModule<SampleWebModule>();
builder.UseAspNetCore(() => WebHost.CreateDefaultBuilder(args), (module, webBuilder) =>
{
});
The Module has to be defined with interface IWebModule
or as WebModule
. As the module is compatible with the AspNet.Core startup class you can rename your generated startup class to the module name and inherits from WebModule
:
public class SampleWebModule : WebModule
{
// this is optional, see sample of UseAspNetCore above for usage
public override string Path => "/sample";
public SampleWebModule(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
[...]
Please note that if you host multiple web modules in one application you will have to configure each module to its own port / path. For Kestrel you should assign a unique port to each module. On Windows you can also use http.sys. This has the advantage that http.sys supports port sharing and therefore you could use the path of the module instead of a port:
.UseAspNetCore((module, webHostBuilder) =>
{
webHostBuilder.UseHttpSys(options =>
{
options.UrlPrefixes.Add($"https://localhost:8080{module.Path}");
})
.UseUrls($"https://localhost:8080{module.Path}");
})
Content and Razor/Blazor
For a Api WebApp you can use any project type. If you would like to use Blazor, Razor or assets in you WebModule you should create it first as normal Web Application from the templates.
Afterwards change project SDK from Microsoft.NET.Sdk.Web
to Microsoft.NET.Sdk.Razor
and add also the StaticWebAssetBasePath
property as in this sample:
<Project Sdk="Microsoft.NET.Sdk.Razor">
<PropertyGroup>
<AddRazorSupportForMvc>true</AddRazorSupportForMvc>
<StaticWebAssetBasePath>.modules/$(AssemblyName)</StaticWebAssetBasePath>
</PropertyGroup>
This will enable automatic handling of assets for the module, so that assets are available in Development and after packageing.
You can use the interface INamedModule
to assign a name for the module.
This has been added for compatibilty with ASPNetCore 2.x where it will be used to set the content root.
In that case you have to use the same name for module and the project folder of the module. For example the SampleWebModule from the code above has both a project folder name SampleWebModule (see also https://github.com/dbosoft/Hosuto/tree/master/samples/dotnetcore21).