https://github.com/smokedlinq/aemediator
A MediatR bridge for Azure Event Grid
https://github.com/smokedlinq/aemediator
azure csharp dotnet eventgrid mediatr
Last synced: 8 months ago
JSON representation
A MediatR bridge for Azure Event Grid
- Host: GitHub
- URL: https://github.com/smokedlinq/aemediator
- Owner: smokedlinq
- License: mit
- Created: 2023-02-13T00:18:41.000Z (over 3 years ago)
- Default Branch: main
- Last Pushed: 2024-05-01T04:29:08.000Z (about 2 years ago)
- Last Synced: 2025-01-01T12:41:38.495Z (over 1 year ago)
- Topics: azure, csharp, dotnet, eventgrid, mediatr
- Language: C#
- Homepage:
- Size: 63.5 KB
- Stars: 3
- Watchers: 1
- Forks: 0
- Open Issues: 1
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# Azure Event Grid Mediator
---

[](https://sonarcloud.io/summary/new_code?id=smokedlinq_aemediator)
[](https://www.nuget.org/packages/MediatR.Azure.EventGrid)
[](https://www.nuget.org/packages/MediatR.Azure.EventGrid)
A [MediatR](/jbogard/MediatR) bridge for Azure Event Grid.
## Installing MediatR.Azure.EventGrid
You can install the latest version of `MediatR.Azure.EventGrid` from NuGet by running the following command in PowerShell:
```powershell
Install-Package MediatR.Azure.EventGrid
```
Alternatively, you can use the .NET command line:
```dotnetcli
dotnet add package MediatR.Azure.EventGrid
```
## Getting Started
To use `EventGridMediator`, you need to register it with the `IServiceCollection` along with MediatR:
```csharp
services
.AddMediatR(mediator => mediator.RegisterServicesFromAssembly(typeof(Program).Assembly))
.AddEventGridMediator();
```
This will automatically deserialize the [Event Grid system topics](https://learn.microsoft.com/azure/event-grid/system-topics) data.
## Custom Events
For custom events, you need to register each data type:
- For `EventGridEvent` objects, the `EventType` and `DataVersion` properties are used to resolve the .NET type.
- For `CloudEvent` objects, the `Type` and `DataSchema` properties are used to resolve the .NET type.
To register a custom data type, use the `DataTypes.Add` method on the `EventGridMediatorBuilder`:
```csharp
services.AddEventGridMediator(builder =>
{
builder.DataTypes
.Add(nameof(MyCustomEventData))
.Add(nameof(MyCustomEventData), "2.0");
});
```
Alternatively, you can use the `EventGridDataTypeAttribute` attribute on classes to register them through assembly discovery of public types:
```csharp
services.AddEventGridMediator(builder => builder.DataTypes.RegisterFromAssembly(typeof(Program).Assembly));
[EventGridDataType(nameof(MyCustomEventData))]
public class MyCustomEventData
{
}
```
## Publishing Events to MediatR
To publish `EventGridEvent` objects using the `EventGridMediator`, use the following code (the example is an ASP.NET Core Minimal API):
```csharp
app.MapPost("/api/events", async (HttpContext context, CancellationToken cancellationToken) =>
{
var json = await BinaryData.FromStreamAsync(context.Request.Body, cancellationToken).ConfigureAwait(false);
var events = EventGridEvent.ParseMany(json);
var mediator = context.RequestServices.GetRequiredService();
await mediator.PublishAsync(events, cancellationToken);
});
```
To publish `CloudEvent` objects, use the following code (the example is an ASP.NET Core Minimal API):
```csharp
app.MapPost("/api/events", async (HttpContext context, CancellationToken cancellationToken) =>
{
var json = await BinaryData.FromStreamAsync(context.Request.Body, cancellationToken).ConfigureAwait(false);
var events = CloudEvent.ParseMany(json);
var mediator = context.RequestServices.GetRequiredService();
await mediator.PublishAsync(events, cancellationToken);
});
```
## Publishing Events to Event Grid
If you don't want to have a dependency on the `MediatR` package, you can still publish events to Event Grid by using the `MediatR.Azure.EventGrid.Serialization` package on its own.
To publish `EventGridEvent` objects using the default serializer used by `EventGridMediator` to resolve the data type, use the following code (the example is an ASP.NET Core Minimal API):
```csharp
app.MapPost("/api/endpoint", async (HttpContext context, CancellationToken cancellationToken) =>
{
var eventData = new MyCustomEventData();
var factory = context.RequestServices.GetRequiredService();
var client = context.RequestServices.GetRequiredService();
var eventGridEvent = factory.Create("subject", eventData);
await client.SendEventAsync(eventGridEvent, cancellationToken);
});
public record MyCustomEventData { }
```
To publish `CloudEvent objects, use the following code (the example is an ASP.NET Core Minimal API):
```csharp
app.MapPost("/api/endpoint", async (HttpContext context, CancellationToken cancellationToken) =>
{
var eventData = new MyCustomEventData();
var factory = context.RequestServices.GetRequiredService();
var client = context.RequestServices.GetRequiredService();
var cloudEvent = factory.Create("source", eventData);
await client.SendEventAsync(cloudEvent, cancellationToken);
});
public record MyCustomEventData { }
```
## Handling Events
By default, MediatR will invoke each `INotificationHandler` sequentially. However, as of MediatR 12.0.0, you can now parallelize the notification with the `TaskWhenAllPublisher` strategy. For more information, see [pull request 838](https://github.com/jbogard/MediatR/pull/838).
Regardless of the notification strategy you choose, keep in mind that handlers should be idempotent because any failures may require reprocessing of the event.
To handle `EventGridEvent` objects, implement `IEventGridEventHandler`:
```csharp
public record MyCustomEventData { }
public class MyCustomEventHandler : IEventGridEventHandler
{
public Task HandleAsync(EventGridEvent eventGridEvent, MyCustomEventData data, CancellationToken cancellationToken)
{
Debug.WriteLine($"Received event {eventGridEvent.Id} of type {eventGridEvent.EventType} with data {data}.");
return Task.CompletedTask;
}
}
```
To handle `CloudEvent` objects, implement `ICloudEventHandler`:
```csharp
public record MyCustomEventData { }
public class MyCustomEventHandler : ICloudEventHandler
{
public Task HandleAsync(CloudEvent cloudEvent, MyCustomEventData data, CancellationToken cancellationToken)
{
Debug.WriteLine($"Received event {cloudEvent.Id} of type {cloudEvent.Type} with data {data}.");
return Task.CompletedTask;
}
}
```