Host NServiceBus endpoints with Azure Functions and Azure Service Bus triggers.
Microsoft announced that .NET 8 will be the last release supporting the in-process hosting model. New projects should use the isolated worker model instead.
Basic usage
Endpoint configuration
NServiceBus can be registered and configured on the host builder using the UseNServiceBus
extension method in the startup class:
class Startup : FunctionsStartup
{
public override void Configure(IFunctionsHostBuilder builder)
{
builder.UseNServiceBus(() => new ServiceBusTriggeredEndpointConfiguration("MyFunctionsEndpoint"));
}
}
Any services registered via the IFunctionsHostBuilder
will be available to message handlers via dependency injection. The startup class must be declared via the FunctionStartup
attribute: [assembly: FunctionsStartup(typeof(Startup))]
.
Azure Function queue trigger for NServiceBus
To access IFunctionEndpoint
from the Azure Function trigger, inject the IFunctionEndpoint
via constructor-injection into the containing class and pass the incoming Message
to the injected IFunctionEndpoint
:
class MyFunction
{
readonly IFunctionEndpoint endpoint;
// inject the FunctionEndpoint via dependency injection:
public MyFunction(IFunctionEndpoint endpoint)
{
this.endpoint = endpoint;
}
[FunctionName("MyFunctionsEndpoint")]
public async Task Run(
[ServiceBusTrigger(queueName: "MyFunctionsEndpoint")]
Message message,
ILogger logger,
ExecutionContext executionContext)
{
await endpoint.Process(message, executionContext, logger);
}
}
Dispatching outside a message handler
Triggering a message using HTTP function:
public class HttpSender
{
readonly IFunctionEndpoint functionEndpoint;
public HttpSender(IFunctionEndpoint functionEndpoint)
{
this.functionEndpoint = functionEndpoint;
}
[FunctionName("HttpSender")]
public async Task<IActionResult> Run(
[HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest request, ExecutionContext executionContext, ILogger logger)
{
logger.LogInformation("C# HTTP trigger function received a request.");
var sendOptions = new SendOptions();
sendOptions.RouteToThisEndpoint();
await functionEndpoint.Send(new TriggerMessage(), sendOptions, executionContext, logger);
return new OkObjectResult($"{nameof(TriggerMessage)} sent.");
}
}
Transport configuration constraints and limitations
The configuration API exposes NServiceBus transport configuration options via the configuration.
property to allow customization. However, not all of the options will be applicable for execution within Azure Functions.
Concurrency-related settings are controlled via the Azure Function host.
configuration file. See Concurrency in Azure Functions for details.
Calling AdvancedConfiguration.
is not supported and may prevent the endpoint from processing messages. Use the .
property to configure the transport. Use the .
property to configure transport routing.
Message consistency
All transport operations behave equal to ReceiveOnly
transport transaction mode. There is no support for the SendsAtomicWithReceive
transport transaction mode in this version.
Configuration
ServiceBusTriggeredEndpointConfiguration
loads certain configuration values from the Azure Function host environment in the following order:
IConfiguration
passed in via the constructor- Environment variables
Key | Value | Notes |
---|---|---|
AzureWebJobsServiceBus | Connection string for the Azure ServiceBus namespace to connect to | This value is required for ServiceBusTriggerAttribute . An alternative key can be passed into the constructor. |
ENDPOINT_NAME | The name of the NServiceBus endpoint to host | A value can be provided directly to the constructor. |
NSERVICEBUS_LICENSE | The NServiceBus license | Can also be provided via serviceBusTriggeredEndpointConfig. . |
WEBSITE_SITE_NAME | The name of the Azure Function app. Provided when hosting the function in Azure. | Used to set the NServiceBus host identifier. Local machine name is used if not set. |
For local development, use local.
. In Azure, specify a Function setting using the environment variable as the key.
{
"IsEncrypted": false,
"Values": {
...
"NSERVICEBUS_LICENSE": "<?xml version=\"1.0\" encoding=\"utf-8\"?><license id=\"1222e1d1-2222-4a46-b1c6-943c442ca710\" expiration=\"2113-11-30T00:00:00.0000000\" type=\"Standard\" LicenseType=\"Standard\" LicenseVersion=\"4.0\" MaxMessageThroughputPerSecond=\"Max\" WorkerThreads=\"Max\" AllowedNumberOfWorkerNodes=\"Max\">. . .</license>"
}
}
Custom diagnostics
NServiceBus startup diagnostics are disabled by default when using Azure Functions. Diagnostics can be written to the logs via the following snippet:
class ConfigureErrorQueueOnStartup : FunctionsStartup
{
public override void Configure(IFunctionsHostBuilder builder)
{
builder.UseNServiceBus(() =>
{
var configuration = new ServiceBusTriggeredEndpointConfiguration("MyFunctionsEndpoint");
configuration.LogDiagnostics();
return configuration;
});
}
}
Diagnostics data will be written with logger identification StartupDiagnostics
with log level Informational.
Error queue
For recoverability to move the continuously failing messages to the error queue rather than to the Azure Service Bus dead-letter queue, the error queue must be created in advance and configured using the following API:
class EnableDiagnosticsOnStartup : FunctionsStartup
{
public override void Configure(IFunctionsHostBuilder builder)
{
builder.UseNServiceBus(() =>
{
var configuration = new ServiceBusTriggeredEndpointConfiguration("MyFunctionsEndpoint");
configuration.AdvancedConfiguration.SendFailedMessagesTo("error");
return configuration;
});
}
}
Preparing the Azure Service Bus namespace
Function endpoints cannot create their own queues or other infrastructure in the Azure Service Bus namespace.
Use the asb-transport
command line (CLI) tool to provision the entities in the namespace for the Function endpoint.
Creating the endpoint queue
asb-transport endpoint create <queue name>
See the full documentation for the asb-transport endpoint create
command for more details.
If the asb-tranport
command-line tool is not used to create the queue, it is recommended to set the MaxDeliveryCount
setting to the maximum value.
Subscribing to events
asb-transport endpoint subscribe <queue name> <eventtype>
See the full documentation for the asb-transport endpoint subscribe
command for more details.
Package requirements
NServiceBus.
requires Visual Studio 2019 and .NET SDK version 5.
or higher. Older versions of the .NET SDK might display the following warning which prevents the trigger definition from being auto-generated:
CSC : warning CS8032: An instance of analyzer NServiceBus.AzureFunctions.SourceGenerator.TriggerFunctionGenerator cannot be created from NServiceBus.AzureFunctions.SourceGenerator.dll : Could not load file or assembly 'Microsoft.CodeAnalysis, Version=3.10.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35'. The system cannot find the file specified..
Starting in version 4.1.0 of NServiceBus.
and NServiceBus.
, warning CS8032 is treated as an error. To suppress this error, update the project's .csproj file to include the following line in the
section at the top:
<WarningsAsErrors></WarningsAsErrors>
This will revert CS8032 to a warning status so that it does not stop the build process.