Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added example for working with Azure Managed Identity #477

Merged
merged 1 commit into from
Nov 20, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions Tingle.EventBus.sln
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AmazonSqsAndSns", "samples\
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AzureIotHub", "samples\AzureIotHub\AzureIotHub.csproj", "{3759B206-BF8D-4E46-9B04-1C19F156D295}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AzureManagedIdentity", "samples\AzureManagedIdentity\AzureManagedIdentity.csproj", "{A9AA8DC8-F463-4BB2-AD7B-59060C758862}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "CustomEventConfigurator", "samples\CustomEventConfigurator\CustomEventConfigurator.csproj", "{8C0EE13F-701F-45EF-BADF-6B7A22AA6785}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "CustomEventSerializer", "samples\CustomEventSerializer\CustomEventSerializer.csproj", "{2C55FABC-8C94-4104-BE05-42A477D2AD9E}"
Expand Down Expand Up @@ -150,6 +152,10 @@ Global
{3759B206-BF8D-4E46-9B04-1C19F156D295}.Debug|Any CPU.Build.0 = Debug|Any CPU
{3759B206-BF8D-4E46-9B04-1C19F156D295}.Release|Any CPU.ActiveCfg = Release|Any CPU
{3759B206-BF8D-4E46-9B04-1C19F156D295}.Release|Any CPU.Build.0 = Release|Any CPU
{A9AA8DC8-F463-4BB2-AD7B-59060C758862}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{A9AA8DC8-F463-4BB2-AD7B-59060C758862}.Debug|Any CPU.Build.0 = Debug|Any CPU
{A9AA8DC8-F463-4BB2-AD7B-59060C758862}.Release|Any CPU.ActiveCfg = Release|Any CPU
{A9AA8DC8-F463-4BB2-AD7B-59060C758862}.Release|Any CPU.Build.0 = Release|Any CPU
{8C0EE13F-701F-45EF-BADF-6B7A22AA6785}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{8C0EE13F-701F-45EF-BADF-6B7A22AA6785}.Debug|Any CPU.Build.0 = Debug|Any CPU
{8C0EE13F-701F-45EF-BADF-6B7A22AA6785}.Release|Any CPU.ActiveCfg = Release|Any CPU
Expand Down Expand Up @@ -209,6 +215,7 @@ Global
{E4D62A60-39E4-401E-B146-0EA8DA272664} = {BDD324B6-9EFC-49A3-9CF6-6CE494446C4B}
{C369A8E1-F29D-4705-BD38-28C3DE80D8DB} = {62F603F3-FF36-4E36-AC0C-08D1883525BE}
{3759B206-BF8D-4E46-9B04-1C19F156D295} = {62F603F3-FF36-4E36-AC0C-08D1883525BE}
{A9AA8DC8-F463-4BB2-AD7B-59060C758862} = {62F603F3-FF36-4E36-AC0C-08D1883525BE}
{8C0EE13F-701F-45EF-BADF-6B7A22AA6785} = {62F603F3-FF36-4E36-AC0C-08D1883525BE}
{2C55FABC-8C94-4104-BE05-42A477D2AD9E} = {62F603F3-FF36-4E36-AC0C-08D1883525BE}
{C9293277-90BA-4F1A-BEA7-85CE41103B8D} = {62F603F3-FF36-4E36-AC0C-08D1883525BE}
Expand Down
11 changes: 11 additions & 0 deletions samples/AzureManagedIdentity/AzureManagedIdentity.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<Project Sdk="Microsoft.NET.Sdk.Worker">

<ItemGroup>
<PackageReference Include="Azure.Identity" Version="1.8.0" />
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\..\src\Tingle.EventBus.Transports.Azure.EventHubs\Tingle.EventBus.Transports.Azure.EventHubs.csproj" />
<ProjectReference Include="..\..\src\Tingle.EventBus.Transports.Azure.ServiceBus\Tingle.EventBus.Transports.Azure.ServiceBus.csproj" />
</ItemGroup>
</Project>
60 changes: 60 additions & 0 deletions samples/AzureManagedIdentity/Program.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
using Azure.Identity;
using AzureManagedIdentity;
using Tingle.EventBus.Configuration;
using Tingle.EventBus.Transports.Azure.EventHubs;
using Tingle.EventBus.Transports.Azure.ServiceBus;

var host = Host.CreateDefaultBuilder(args)
.ConfigureServices((hostContext, services) =>
{
var configuration = hostContext.Configuration;

services.AddEventBus(builder =>
{
builder.Configure(o =>
{
o.DefaultTransportName = AzureServiceBusDefaults.Name;

o.ConfigureEvent<VehicleTelemetryEvent>(reg =>
{
reg.ConfigureAsIotHubEvent(configuration["IotHubEventHubName"]!)
.UseIotHubEventSerializer();

reg.TransportName = AzureEventHubsDefaults.Name; // you can also use EventTransportNameAttribute on the event type declaration
});
});

builder.AddConsumer<VehicleTelemetryEventsConsumer>();

var credential = new DefaultAzureCredential();

// Transport specific configuration
builder.AddAzureEventHubsTransport(options =>
{
options.Credentials = new AzureEventHubsTransportCredentials
{
TokenCredential = credential,
FullyQualifiedNamespace = "{your_namespace}.servicebus.windows.net"
};
options.BlobStorageCredentials = new AzureBlobStorageCredentials
{
TokenCredential = credential,
BlobServiceUrl = new Uri("https://{account_name}.blob.core.windows.net"),
};
});

// Transport specific configuration
builder.AddAzureServiceBusTransport(options =>
{
options.Credentials = new AzureServiceBusTransportCredentials
{
TokenCredential = credential,
FullyQualifiedNamespace = "{your_namespace}.servicebus.windows.net"
};
options.DefaultEntityKind = EntityKind.Queue; // required if using the basic SKU (does not support topics)
});
});
})
.Build();

await host.RunAsync();
11 changes: 11 additions & 0 deletions samples/AzureManagedIdentity/Properties/launchSettings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"profiles": {
"AzureManagedIdentity": {
"commandName": "Project",
"dotnetRunMessages": true,
"environmentVariables": {
"DOTNET_ENVIRONMENT": "Development"
}
}
}
}
9 changes: 9 additions & 0 deletions samples/AzureManagedIdentity/VehicleDoorOpenedEvent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
namespace AzureManagedIdentity;

public class VehicleDoorOpenedEvent
{
public string? VehicleId { get; set; }
public VehicleDoorKind Kind { get; set; }
public DateTimeOffset? Opened { get; set; }
public DateTimeOffset? Closed { get; set; }
}
45 changes: 45 additions & 0 deletions samples/AzureManagedIdentity/VehicleTelemetryEvent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
using System.Text.Json.Nodes;
using System.Text.Json.Serialization;
using Tingle.EventBus.Transports.Azure.EventHubs.IotHub;

namespace AzureManagedIdentity;

internal record VehicleTelemetryEvent : IotHubEvent<VehicleTelemetry>
{
public VehicleTelemetryEvent(IotHubEventMessageSource source,
VehicleTelemetry? telemetry,
IotHubOperationalEvent<IotHubDeviceTwinChangeEvent>? twinEvent,
IotHubOperationalEvent<IotHubDeviceLifecycleEvent>? lifecycleEvent,
IotHubOperationalEvent<IotHubDeviceConnectionStateEvent>? connectionStateEvent)
: base(source, telemetry, twinEvent, lifecycleEvent, connectionStateEvent) { }
}

internal class VehicleTelemetry
{
public DateTimeOffset Timestamp { get; set; }

public string? Action { get; set; }

public VehicleDoorKind? VehicleDoorKind { get; set; }
public VehicleDoorStatus? VehicleDoorStatus { get; set; }

[JsonExtensionData]
public JsonObject? Extras { get; set; }
}

public enum VehicleDoorStatus
{
Unknown,
Open,
Closed,
}

public enum VehicleDoorKind
{
FrontLeft,
FrontRight,
RearLeft,
ReadRight,
Hood,
Trunk,
}
55 changes: 55 additions & 0 deletions samples/AzureManagedIdentity/VehicleTelemetryEventsConsumer.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
using Tingle.EventBus.Transports.Azure.EventHubs.IotHub;

namespace AzureManagedIdentity;

internal class VehicleTelemetryEventsConsumer : IEventConsumer<VehicleTelemetryEvent>
{
private readonly ILogger logger;

public VehicleTelemetryEventsConsumer(ILogger<VehicleTelemetryEventsConsumer> logger)
{
this.logger = logger ?? throw new ArgumentNullException(nameof(logger));
}

public async Task ConsumeAsync(EventContext<VehicleTelemetryEvent> context, CancellationToken cancellationToken)
{
var evt = context.Event;
var source = evt.Source;
if (source != IotHubEventMessageSource.Telemetry) return;

var telemetry = evt.Telemetry!;
var action = telemetry.Action;
if (action is not "door-status-changed")
{
logger.LogWarning("Telemetry with action '{TelemetryAction}' is not yet supported", action);
return;
}

var status = telemetry.VehicleDoorStatus;
if (status is not VehicleDoorStatus.Open and not VehicleDoorStatus.Closed)
{
logger.LogWarning("Vehicle Door status '{VehicleDoorStatus}' is not yet supported", status);
return;
}

var kind = telemetry.VehicleDoorKind;
if (kind is null)
{
logger.LogWarning("Vehicle Door kind '{VehicleDoorKind}' cannot be null", kind);
return;
}

var deviceId = context.GetIotHubDeviceId();
var timestamp = telemetry.Timestamp;
var updateEvt = new VehicleDoorOpenedEvent
{
VehicleId = deviceId, // not the registration number
Kind = kind.Value,
Closed = status is VehicleDoorStatus.Closed ? timestamp : null,
Opened = status is VehicleDoorStatus.Open ? timestamp : null,
};

// the VehicleDoorOpenedEvent on a broadcast bus would notify all subscribers
await context.PublishAsync(updateEvt, cancellationToken: cancellationToken);
}
}
16 changes: 16 additions & 0 deletions samples/AzureManagedIdentity/appsettings.Development.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
{
"Logging": {
"LogLevel": {
"Default": "Debug",
"Microsoft": "Information",
"System": "Information"
},
"Console": {
"FormatterName": "simple",
"FormatterOptions": {
"SingleLine": true,
"TimestampFormat": "HH:mm:ss "
}
}
}
}
11 changes: 11 additions & 0 deletions samples/AzureManagedIdentity/appsettings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft": "Warning",
"Microsoft.Hosting.Lifetime": "Information"
}
},

"IotHubEventHubName": "iothub-ehub-test-dev-0000000-0aaaa000aa"
}