Abstractions

Dosaic.Hosting.Abstractions is the core abstraction/interface package that allows .NET developers to build their own Dosaic plugins. Every plugin in the Dosaic ecosystem depends on this package.

Installation

dotnet add package Dosaic.Hosting.Abstractions

or add as a package reference to your .csproj:

<PackageReference Include="Dosaic.Hosting.Abstractions" Version="" />

Usage

Creating a Plugin

A plugin is any public, non-abstract class that implements one or more of the plugin interfaces below. The source generator in Dosaic.Hosting.Generator automatically discovers all such classes at compile time — no runtime reflection or manual registration needed.

using Dosaic.Hosting.Abstractions.Plugins;
using Microsoft.Extensions.DependencyInjection;

namespace MyCompany.MyPlugin
{
    public class MyPlugin : IPluginServiceConfiguration, IPluginApplicationConfiguration
    {
        public void ConfigureServices(IServiceCollection serviceCollection)
        {
            serviceCollection.AddTransient<IMyService, MyService>();
        }

        public void ConfigureApplication(IApplicationBuilder applicationBuilder)
        {
            applicationBuilder.UseMyMiddleware();
        }
    }
}

Plugin Interfaces

All plugin interfaces live in Dosaic.Hosting.Abstractions.Plugins and extend IPluginActivateable.

Interface
Method
Purpose

IPluginActivateable

Marker interface — all plugins must implement this (directly or via one of the interfaces below)

IPluginServiceConfiguration

ConfigureServices(IServiceCollection)

DI registrations, called during the service-configuration phase

IPluginApplicationConfiguration

ConfigureApplication(IApplicationBuilder)

Middleware pipeline setup, called after Build()

IPluginEndpointsConfiguration

ConfigureEndpoints(IEndpointRouteBuilder, IServiceProvider)

Minimal API endpoint registration

IPluginHealthChecksConfiguration

ConfigureHealthChecks(IHealthChecksBuilder)

Custom health check registration

IPluginControllerConfiguration

ConfigureControllers(IMvcBuilder)

MVC/controller configuration

IPluginConfigurator

Marker for sub-configurator objects injected as IPluginConfigurator[] collections into plugins

Plugin execution order

Plugin namespace
Execution order

Dosaic.* namespace

First (sbyte.MinValue)

Third-party plugins

Middle (0)

Host assembly plugins

Last (sbyte.MaxValue)

IPluginServiceConfiguration

Called during service-collection setup. Use this for DI registrations.

IPluginApplicationConfiguration

Called after WebApplication.Build(). Use this for UseXyz() pipeline calls.

IPluginEndpointsConfiguration

Registers minimal API endpoints. Called during endpoint routing setup.

IPluginHealthChecksConfiguration

Registers health checks programmatically. See also the health check attributes for declarative registration.

IPluginControllerConfiguration

Configures the MVC builder (e.g. options, formatters, assemblies).

IPluginConfigurator

A sub-configurator is a small, focused configuration object that is automatically collected and injected as an array into plugins that declare a constructor parameter of type IPluginConfigurator[] (or IEnumerable<IPluginConfigurator>).


Attributes

[Configuration]

Decorating a class with [Configuration("section")] causes the web host to automatically bind the class to the corresponding section in appsettings.* files or environment variables. The bound instance is then injectable as a constructor parameter in any plugin.

Nested sections are supported using : as the delimiter:

[Middleware]

Marks an ApiMiddleware subclass for automatic registration in the middleware pipeline. The optional order parameter controls execution order (default: int.MaxValue — runs last). Lower values run earlier.

Built-in middlewares and their order:

Middleware
Order
Behaviour

ExceptionMiddleware

int.MinValue (first)

Catches all exceptions; maps DosaicException subtypes to HTTP status codes

EnrichRequestMetricsMiddleware

int.MaxValue (last)

Adds azp claim as a metrics tag on every request

RequestContentLengthLimitMiddleware

int.MaxValue (last)

Returns 413 when Content-Length exceeds the Kestrel limit

[ReadinessCheckAttribute]

Registers an IHealthCheck implementation as a readiness health check (tags it with HealthCheckTag.Readiness).

[LivenessCheckAttribute]

Registers an IHealthCheck implementation as a liveness health check (tags it with HealthCheckTag.Liveness).

Both attributes can be combined on the same class, and additional tags can be passed via the overloaded constructors:

[YamlTypeConverterAttribute]

Attaches a custom YAML type converter to a class or struct so that it is used during SerializationExtensions.Serialize / Deserialize calls with SerializationMethod.Yaml. The converter type must implement IYamlConverter.


HealthCheckTag

HealthCheckTag is a validated value object (via Vogenarrow-up-right) with two predefined instances:

Instance
Value

HealthCheckTag.Readiness

"readiness"

HealthCheckTag.Liveness

"liveness"

Custom tags are supported:


Exceptions

All domain exceptions extend DosaicException, which carries an HttpStatus property automatically used by ExceptionMiddleware to produce the correct HTTP response.

Exception
Default HTTP status

DosaicException

500 Internal Server Error (configurable via constructor)

NotFoundDosaicException

404 Not Found

ConflictDosaicException

409 Conflict

ValidationDosaicException

422 Unprocessable Entity

Error Response Models

ExceptionMiddleware produces JSON responses using these models from Dosaic.Hosting.Abstractions.Middlewares.Models:


IImplementationResolver

IImplementationResolver is the runtime service used internally by the web host to discover and instantiate plugins. It is also injectable into plugins for advanced scenarios.

Convenience extensions from ImplementationResolverExtensions:


IFactory<T>

IFactory<TService> is a lightweight factory abstraction for resolving services lazily or optionally from the DI container. Register using AddFactory<T>().


Metrics

Dosaic uses OpenTelemetry for metrics. The static Metrics class provides typed factory methods that cache instrument instances, preventing duplicate-creation errors.

Access the underlying Meter directly for advanced scenarios:


Tracing

DosaicDiagnostic

DosaicDiagnostic.CreateSource() creates an ActivitySource named after the calling class's fully-qualified name using the call stack. Call it from a static field initializer.

Constants:

Constant
Value
Purpose

DosaicDiagnostic.DosaicActivityPrefix

"Dosaic."

Prefix for all Dosaic activity sources

DosaicDiagnostic.DosaicAllActivities

"Dosaic.*"

Wildcard for subscribing to all Dosaic traces in OpenTelemetry

TracingExtensions


Serialization

SerializationExtensions provides uniform JSON and YAML serialization.

IKindSpecifier — Polymorphic deserialization

Implementing IKindSpecifier on an interface enables discriminated-union deserialization where the concrete type is selected based on a Kind property in the JSON/YAML payload.


Utility Extensions

ObjectExtensions — DeepPatch

Applies non-null property values from a patch object onto a target, with configurable behaviour for nested objects and lists.

PatchMode flags: Full, IgnoreLists, IgnoreObjects, OverwriteLists.

StringExtensions

ConfigurationExtensions

TypeExtensions

EnumerableExtensions

EnumExtensions


GlobalStatusCodeOptions

Controls which HTTP status codes are automatically rewritten to the standard ErrorResponse JSON format by ExceptionMiddleware. Default codes: 401, 403, 404, 406, 415, 500.


ApiMiddleware

ApiMiddleware is the abstract base class for all Dosaic middlewares. Subclass it and decorate with [Middleware] for automatic registration in the pipeline.

Helper methods available inside ApiMiddleware:

Last updated