From d80cdb2cdb1d6a30158c51015a54c1094ea09f48 Mon Sep 17 00:00:00 2001 From: Felipe Henrique Date: Sat, 25 Apr 2026 10:15:05 -0400 Subject: [PATCH 1/3] feat(otel): add TelemetryTags and MessagingAttributes constants --- .../GlobalUsings.cs | 5 +- .../OpenTelemetry/MessagingAttributes.cs | 49 +++++++++++++++++++ .../OpenTelemetry/TelemetryTags.cs | 17 +++++++ 3 files changed, 69 insertions(+), 2 deletions(-) create mode 100644 src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/MessagingAttributes.cs create mode 100644 src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/TelemetryTags.cs diff --git a/src/Core/EcommerceDDD.Core.Infrastructure/GlobalUsings.cs b/src/Core/EcommerceDDD.Core.Infrastructure/GlobalUsings.cs index 58109f81..f22944a0 100644 --- a/src/Core/EcommerceDDD.Core.Infrastructure/GlobalUsings.cs +++ b/src/Core/EcommerceDDD.Core.Infrastructure/GlobalUsings.cs @@ -1,5 +1,6 @@ global using Asp.Versioning; global using Confluent.Kafka; +global using Confluent.Kafka.Admin; global using Duende.IdentityModel; global using Duende.IdentityModel.Client; global using EcommerceDDD.Core.CQRS.CommandHandling; @@ -42,6 +43,7 @@ global using Microsoft.OpenApi; global using Newtonsoft.Json; global using Newtonsoft.Json.Linq; +global using Npgsql; global using OpenTelemetry.Logs; global using OpenTelemetry.Metrics; global using OpenTelemetry.Resources; @@ -49,10 +51,9 @@ global using Polly; global using Swashbuckle.AspNetCore.SwaggerGen; global using System.Diagnostics; -global using System.Linq.Expressions; global using System.IdentityModel.Tokens.Jwt; +global using System.Linq.Expressions; global using System.Net.Mime; global using System.Reflection; global using System.Security.Claims; global using System.Text; -global using Npgsql; \ No newline at end of file diff --git a/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/MessagingAttributes.cs b/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/MessagingAttributes.cs new file mode 100644 index 00000000..96a5988f --- /dev/null +++ b/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/MessagingAttributes.cs @@ -0,0 +1,49 @@ +// Local subset of OpenTelemetry messaging semantic conventions. +// Todo: replace constant with the official `OpenTelemetry.SemanticConventions` package is released. +// Source: https://github.com/open-telemetry/opentelemetry-dotnet-contrib/blob/main/src/OpenTelemetry.SemanticConventions/Attributes/MessagingAttributes.cs + +namespace EcommerceDDD.Core.Infrastructure.OpenTelemetry; + +public static class MessagingAttributes +{ + /// An identifier for the messaging system being used. See MessagingSystemValues. + public const string AttributeMessagingSystem = "messaging.system"; + + /// The message destination name (queue, topic, or broker-specific entity). + public const string AttributeMessagingDestinationName = "messaging.destination.name"; + + /// The partition identifier within messaging.destination.name. + public const string AttributeMessagingDestinationPartitionId = "messaging.destination.partition.id"; + + /// The type of the messaging operation. See MessagingOperationTypeValues. + public const string AttributeMessagingOperationType = "messaging.operation.type"; + + /// The name of the consumer group with which a consumer is associated. + public const string AttributeMessagingConsumerGroupName = "messaging.consumer.group.name"; + + /// The offset of a record in the corresponding Kafka partition. + public const string AttributeMessagingKafkaOffset = "messaging.kafka.offset"; + + /// The Kafka message key (partition routing key; not a unique message id). + public const string AttributeMessagingKafkaMessageKey = "messaging.kafka.message.key"; + + /// A value used by the messaging system as an identifier for the message. + public const string AttributeMessagingMessageId = "messaging.message.id"; + + public static class MessagingSystemValues + { + public const string Kafka = "kafka"; + } + + public static class MessagingOperationTypeValues + { + /// One or more messages are provided for sending to an intermediary. + public const string Send = "send"; + + /// One or more messages are requested by a consumer (pull-based). + public const string Receive = "receive"; + + /// One or more messages are processed by a consumer. + public const string Process = "process"; + } +} diff --git a/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/TelemetryTags.cs b/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/TelemetryTags.cs new file mode 100644 index 00000000..ec1e3f42 --- /dev/null +++ b/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/TelemetryTags.cs @@ -0,0 +1,17 @@ +namespace EcommerceDDD.Core.Infrastructure.OpenTelemetry; + +/// +/// Project-specific telemetry tag keys and literal values that are not part of +/// the OpenTelemetry semantic conventions spec. Keys defined by the spec live +/// in (and future domain attribute files). +/// +public static class TelemetryTags +{ + public const string OrderId = "order.id"; + public const string EventType = "event.type"; + + public static class DestinationValues + { + public const string Outbox = "outbox"; + } +} From 30b160343e434c9eb914ce43ffa32298efc2b039 Mon Sep 17 00:00:00 2001 From: Felipe Henrique Date: Sat, 25 Apr 2026 10:15:28 -0400 Subject: [PATCH 2/3] refactor(otel): align Kafka and outbox spans with current semconv names --- .../Kafka/Consumer/KafkaConsumer.cs | 20 +++++++++---------- .../Marten/MartenRepository.cs | 8 ++++---- 2 files changed, 13 insertions(+), 15 deletions(-) diff --git a/src/Core/EcommerceDDD.Core.Infrastructure/Kafka/Consumer/KafkaConsumer.cs b/src/Core/EcommerceDDD.Core.Infrastructure/Kafka/Consumer/KafkaConsumer.cs index a2106738..7c634141 100644 --- a/src/Core/EcommerceDDD.Core.Infrastructure/Kafka/Consumer/KafkaConsumer.cs +++ b/src/Core/EcommerceDDD.Core.Infrastructure/Kafka/Consumer/KafkaConsumer.cs @@ -1,6 +1,4 @@ -using Confluent.Kafka.Admin; - -namespace EcommerceDDD.Core.Infrastructure.Kafka.Consumer; +namespace EcommerceDDD.Core.Infrastructure.Kafka.Consumer; public class KafkaConsumer : IEventConsumer { @@ -260,13 +258,13 @@ private async Task ConsumeNextMessage(IConsumer consumer, parentContext: default, tags: null, links: links); - activity?.SetTag("messaging.system", "kafka"); - activity?.SetTag("messaging.destination", result.Topic); - activity?.SetTag("messaging.operation", "receive"); - activity?.SetTag("messaging.kafka.consumer_group", _config.Group); - activity?.SetTag("messaging.kafka.partition", result.Partition.Value); - activity?.SetTag("messaging.kafka.message_offset", result.Offset.Value); - activity?.SetTag("messaging.message_id", result.Message.Key); + activity?.SetTag(MessagingAttributes.AttributeMessagingSystem, MessagingAttributes.MessagingSystemValues.Kafka); + activity?.SetTag(MessagingAttributes.AttributeMessagingDestinationName, result.Topic); + activity?.SetTag(MessagingAttributes.AttributeMessagingOperationType, MessagingAttributes.MessagingOperationTypeValues.Receive); + activity?.SetTag(MessagingAttributes.AttributeMessagingConsumerGroupName, _config.Group); + activity?.SetTag(MessagingAttributes.AttributeMessagingDestinationPartitionId, result.Partition.Value); + activity?.SetTag(MessagingAttributes.AttributeMessagingKafkaOffset, result.Offset.Value); + activity?.SetTag(MessagingAttributes.AttributeMessagingKafkaMessageKey, result.Message.Key); // Deserialize the domain event from the raw outbox payload var messageBytes = Encoding.UTF8.GetBytes(result.Message.Value); @@ -312,7 +310,7 @@ await _eventPublisher private async Task EnsureTopicsExistAsync() { if (_config is null) - throw new InvalidOperationException(nameof(Config)); + throw new InvalidOperationException("Kafka consumer config is not initialized."); try { diff --git a/src/Core/EcommerceDDD.Core.Infrastructure/Marten/MartenRepository.cs b/src/Core/EcommerceDDD.Core.Infrastructure/Marten/MartenRepository.cs index d058eabe..81551d2f 100644 --- a/src/Core/EcommerceDDD.Core.Infrastructure/Marten/MartenRepository.cs +++ b/src/Core/EcommerceDDD.Core.Infrastructure/Marten/MartenRepository.cs @@ -78,10 +78,10 @@ public void AppendToOutbox(INotification @event) $"outbox.publish {eventName}", ActivityKind.Producer); - _pendingOutboxActivity?.SetTag("messaging.system", "kafka"); - _pendingOutboxActivity?.SetTag("messaging.destination.name", "outbox"); - _pendingOutboxActivity?.SetTag("messaging.operation", "publish"); - _pendingOutboxActivity?.SetTag("event.type", eventName); + _pendingOutboxActivity?.SetTag(MessagingAttributes.AttributeMessagingSystem, MessagingAttributes.MessagingSystemValues.Kafka); + _pendingOutboxActivity?.SetTag(MessagingAttributes.AttributeMessagingDestinationName, TelemetryTags.DestinationValues.Outbox); + _pendingOutboxActivity?.SetTag(MessagingAttributes.AttributeMessagingOperationType, MessagingAttributes.MessagingOperationTypeValues.Send); + _pendingOutboxActivity?.SetTag(TelemetryTags.EventType, eventName); var integrationEvent = IntegrationEvent.FromNotification(@event!); From b7b70d3d0fe74abbad6518c3ab46189fa274a916 Mon Sep 17 00:00:00 2001 From: Felipe Henrique Date: Sat, 25 Apr 2026 10:17:35 -0400 Subject: [PATCH 3/3] refactor(otel): unify ITraceable as object-valued tag source --- .../OpenTelemetry/ITraceable.cs | 2 +- .../Orders/CancelingOrder/CancelOrder.cs | 4 ++-- .../ConfirmingDelivery/ConfirmDelivery.cs | 4 ++-- .../Orders/PlacingOrder/PlaceOrderHandler.cs | 2 +- .../Orders/ProcessingOrder/ProcessOrder.cs | 4 ++-- .../RecordingPayment/RecordPayment.cs | 4 ++-- .../RequestingPayment/RequestPayment.cs | 4 ++-- .../RecordingShipment/RecordShipment.cs | 4 ++-- .../RequestingShipment/RequestShipment.cs | 4 ++-- .../Application/ProcessPaymentHandlerTests.cs | 4 ++-- .../ProcessingPayment/ProcessPayment.cs | 19 +++++++++++++------ .../ProcessPaymentHandler.cs | 1 - .../RequestingPayment/RequestPayment.cs | 4 ++-- .../RequestPaymentHandler.cs | 2 +- .../Application/ShipPackageHandlerTests.cs | 2 +- .../ProcessingShipment/ProcessShipment.cs | 19 +++++++++++++------ .../ProcessShipmentHandler.cs | 1 - .../RequestingShipment/RequestShipment.cs | 4 ++-- .../RequestShipmentHandler.cs | 2 +- 19 files changed, 51 insertions(+), 39 deletions(-) diff --git a/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/ITraceable.cs b/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/ITraceable.cs index 1186956d..84291f12 100644 --- a/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/ITraceable.cs +++ b/src/Core/EcommerceDDD.Core.Infrastructure/OpenTelemetry/ITraceable.cs @@ -2,5 +2,5 @@ namespace EcommerceDDD.Core.Infrastructure.OpenTelemetry; public interface ITraceable { - IEnumerable> GetSpanTags(); + IEnumerable> GetSpanTags(); } diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/CancelingOrder/CancelOrder.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/CancelingOrder/CancelOrder.cs index 0743ead5..aaf04d34 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/CancelingOrder/CancelOrder.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/CancelingOrder/CancelOrder.cs @@ -15,8 +15,8 @@ public static CancelOrder Create( return new CancelOrder(orderId, CancellationReason); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private CancelOrder( OrderId orderId, diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ConfirmingDelivery/ConfirmDelivery.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ConfirmingDelivery/ConfirmDelivery.cs index 1cdd9705..369c7790 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ConfirmingDelivery/ConfirmDelivery.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ConfirmingDelivery/ConfirmDelivery.cs @@ -12,8 +12,8 @@ public static ConfirmDelivery Create(OrderId orderId) return new ConfirmDelivery(orderId); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private ConfirmDelivery(OrderId orderId) { diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/PlacingOrder/PlaceOrderHandler.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/PlacingOrder/PlaceOrderHandler.cs index 2f018e62..164936bf 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/PlacingOrder/PlaceOrderHandler.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/PlacingOrder/PlaceOrderHandler.cs @@ -43,7 +43,7 @@ public async Task HandleAsync(PlaceOrder command, CancellationToken canc orderItems); var order = Order.Place(orderData); - Activity.Current?.SetTag("order.id", order.Id.Value.ToString()); + Activity.Current?.SetTag(TelemetryTags.OrderId, order.Id.Value); var orderPlacedEvent = order.GetUncommittedEvents() .OfType().FirstOrDefault(); diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ProcessingOrder/ProcessOrder.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ProcessingOrder/ProcessOrder.cs index 9192a6c9..28e03f3c 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ProcessingOrder/ProcessOrder.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Orders/ProcessingOrder/ProcessOrder.cs @@ -21,8 +21,8 @@ public static ProcessOrder Create( return new ProcessOrder(customerId, orderId, quoteId); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private ProcessOrder( CustomerId customerId, diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RecordingPayment/RecordPayment.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RecordingPayment/RecordPayment.cs index 3340868a..e17158e9 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RecordingPayment/RecordPayment.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RecordingPayment/RecordPayment.cs @@ -21,8 +21,8 @@ public static RecordPayment Create( return new RecordPayment(orderId, paymentId, totalPaid); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private RecordPayment( OrderId orderId, diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RequestingPayment/RequestPayment.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RequestingPayment/RequestPayment.cs index c317105b..a1d9335b 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RequestingPayment/RequestPayment.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Payments/RequestingPayment/RequestPayment.cs @@ -25,8 +25,8 @@ public static RequestPayment Create( return new RequestPayment(customerId, orderId, totalPrice, currency); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private RequestPayment( CustomerId customerId, diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RecordingShipment/RecordShipment.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RecordingShipment/RecordShipment.cs index 35b5370b..f58c6340 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RecordingShipment/RecordShipment.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RecordingShipment/RecordShipment.cs @@ -17,8 +17,8 @@ public static RecordShipment Create( return new RecordShipment(orderId, shipmentId); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private RecordShipment( OrderId orderId, diff --git a/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RequestingShipment/RequestShipment.cs b/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RequestingShipment/RequestShipment.cs index b649dc47..02823ce8 100644 --- a/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RequestingShipment/RequestShipment.cs +++ b/src/Services/EcommerceDDD.OrderProcessing/Application/Shipments/RequestingShipment/RequestShipment.cs @@ -12,8 +12,8 @@ public static RequestShipment Create(OrderId orderId) return new RequestShipment(orderId); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private RequestShipment(OrderId orderId) => OrderId = orderId; } \ No newline at end of file diff --git a/src/Services/EcommerceDDD.PaymentProcessing.Tests/Application/ProcessPaymentHandlerTests.cs b/src/Services/EcommerceDDD.PaymentProcessing.Tests/Application/ProcessPaymentHandlerTests.cs index 16d34f98..c75b0d37 100644 --- a/src/Services/EcommerceDDD.PaymentProcessing.Tests/Application/ProcessPaymentHandlerTests.cs +++ b/src/Services/EcommerceDDD.PaymentProcessing.Tests/Application/ProcessPaymentHandlerTests.cs @@ -28,7 +28,7 @@ public async Task ProcessPayment_WithCommand_ShouldCompletePayment() .Returns(Task.FromResult(true)); // When - var processPayment = ProcessPayment.Create(payment.Id); + var processPayment = ProcessPayment.Create(payment.Id, orderId); var processPaymentHandler = new ProcessPaymentHandler( _productInventoryHandler, _customerCreditChecker, paymentWriteRepository); await processPaymentHandler.HandleAsync(processPayment, CancellationToken.None); @@ -68,7 +68,7 @@ public async Task ProcessPayment_WithoutEnoughCredit_CancelPayment() .CheckProductsInStockAsync(Arg.Any>(), CancellationToken.None) .Returns(Task.FromResult(true)); - var processPayment = ProcessPayment.Create(payment.Id); + var processPayment = ProcessPayment.Create(payment.Id, orderId); var processPaymentHandler = new ProcessPaymentHandler( _productInventoryHandler, _customerCreditChecker, paymentWriteRepository); diff --git a/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPayment.cs b/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPayment.cs index 8b1325cc..f64d7035 100644 --- a/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPayment.cs +++ b/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPayment.cs @@ -1,19 +1,26 @@ -namespace EcommerceDDD.PaymentProcessing.Application.ProcessingPayment; +namespace EcommerceDDD.PaymentProcessing.Application.ProcessingPayment; -public record class ProcessPayment : ICommand +public record class ProcessPayment : ICommand, ITraceable { public PaymentId PaymentId { get; private set; } + public OrderId OrderId { get; private set; } - public static ProcessPayment Create(PaymentId paymentId) + public static ProcessPayment Create(PaymentId paymentId, OrderId orderId) { if (paymentId is null) throw new ArgumentNullException(nameof(paymentId)); + if (orderId is null) + throw new ArgumentNullException(nameof(orderId)); - return new ProcessPayment(paymentId); + return new ProcessPayment(paymentId, orderId); } - private ProcessPayment(PaymentId paymentId) + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; + + private ProcessPayment(PaymentId paymentId, OrderId orderId) { PaymentId = paymentId; + OrderId = orderId; } -} \ No newline at end of file +} diff --git a/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPaymentHandler.cs b/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPaymentHandler.cs index f8025bb0..08aa8197 100644 --- a/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPaymentHandler.cs +++ b/src/Services/EcommerceDDD.PaymentProcessing/Application/ProcessingPayment/ProcessPaymentHandler.cs @@ -18,7 +18,6 @@ public async Task HandleAsync(ProcessPayment command, CancellationToken if (payment is null) return Result.Fail($"Payment {command.PaymentId} was not found."); - Activity.Current?.SetTag("order.id", payment.OrderId.Value.ToString()); try { if (!await _creditChecker diff --git a/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPayment.cs b/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPayment.cs index 678cbc66..5d8d4538 100644 --- a/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPayment.cs +++ b/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPayment.cs @@ -29,8 +29,8 @@ public static RequestPayment Create( return new RequestPayment(customerId, orderId, totalPrice, currency, productItems); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private RequestPayment( CustomerId customerId, diff --git a/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPaymentHandler.cs b/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPaymentHandler.cs index 5edd7938..018c6321 100644 --- a/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPaymentHandler.cs +++ b/src/Services/EcommerceDDD.PaymentProcessing/Application/RequestingPayment/RequestPaymentHandler.cs @@ -22,6 +22,6 @@ await _paymentWriteRepository .AppendEventsAsync(payment, cancellationToken); return await _commandBus.SendAsync( - ProcessPayment.Create(payment.Id), cancellationToken); + ProcessPayment.Create(payment.Id, command.OrderId), cancellationToken); } } diff --git a/src/Services/EcommerceDDD.ShipmentProcessing.Tests/Application/ShipPackageHandlerTests.cs b/src/Services/EcommerceDDD.ShipmentProcessing.Tests/Application/ShipPackageHandlerTests.cs index 5895d708..974dce8c 100644 --- a/src/Services/EcommerceDDD.ShipmentProcessing.Tests/Application/ShipPackageHandlerTests.cs +++ b/src/Services/EcommerceDDD.ShipmentProcessing.Tests/Application/ShipPackageHandlerTests.cs @@ -21,7 +21,7 @@ public async Task ShipPackage_WithCommand_ShouldShipPackage() var shipment = shipmentWriteRepository.AggregateStream.First().Aggregate; Assert.NotNull(shipment); - var shipPackage = ProcessShipment.Create(shipment.Id); + var shipPackage = ProcessShipment.Create(shipment.Id, orderId); var shipPackageHandler = new ProcessShipmentHandler(shipmentWriteRepository); // When diff --git a/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipment.cs b/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipment.cs index 86f00229..fed59722 100644 --- a/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipment.cs +++ b/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipment.cs @@ -1,19 +1,26 @@ -namespace EcommerceDDD.ShipmentProcessing.Application.ProcessingShipment; +namespace EcommerceDDD.ShipmentProcessing.Application.ProcessingShipment; -public record class ProcessShipment : ICommand +public record class ProcessShipment : ICommand, ITraceable { public ShipmentId ShipmentId { get; private set; } + public OrderId OrderId { get; private set; } - public static ProcessShipment Create(ShipmentId shipmentId) + public static ProcessShipment Create(ShipmentId shipmentId, OrderId orderId) { if (shipmentId is null) throw new ArgumentNullException(nameof(shipmentId)); + if (orderId is null) + throw new ArgumentNullException(nameof(orderId)); - return new ProcessShipment(shipmentId); + return new ProcessShipment(shipmentId, orderId); } - private ProcessShipment(ShipmentId shipmentId) + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; + + private ProcessShipment(ShipmentId shipmentId, OrderId orderId) { ShipmentId = shipmentId; + OrderId = orderId; } -} \ No newline at end of file +} diff --git a/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipmentHandler.cs b/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipmentHandler.cs index e70fab48..f52c950b 100644 --- a/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipmentHandler.cs +++ b/src/Services/EcommerceDDD.ShipmentProcessing/Application/ProcessingShipment/ProcessShipmentHandler.cs @@ -16,7 +16,6 @@ public async Task HandleAsync(ProcessShipment command, CancellationToken if (shipment is null) return Result.Fail($"The shipment {command.ShipmentId} was not found."); - Activity.Current?.SetTag("order.id", shipment.OrderId.Value.ToString()); try { shipment.Complete(); diff --git a/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipment.cs b/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipment.cs index de55922b..364d0ec1 100644 --- a/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipment.cs +++ b/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipment.cs @@ -17,8 +17,8 @@ public static RequestShipment Create( return new RequestShipment(orderId, productItems); } - public IEnumerable> GetSpanTags() => - [new("order.id", OrderId.Value.ToString())]; + public IEnumerable> GetSpanTags() => + [new(TelemetryTags.OrderId, OrderId.Value)]; private RequestShipment( OrderId orderId, diff --git a/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipmentHandler.cs b/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipmentHandler.cs index f952952b..231ad36e 100644 --- a/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipmentHandler.cs +++ b/src/Services/EcommerceDDD.ShipmentProcessing/Application/RequestingShipment/RequestShipmentHandler.cs @@ -19,6 +19,6 @@ await _shipmentWriteRepository .AppendEventsAsync(shipment, cancellationToken); return await _commandBus - .SendAsync(ProcessShipment.Create(shipment.Id), cancellationToken); + .SendAsync(ProcessShipment.Create(shipment.Id, command.OrderId), cancellationToken); } }