public NaosMessagingEchoController( ILogger <NaosMessagingEchoController> logger, IMessageBroker messageBroker, ISubscriptionMap subscriptionMap) { EnsureArg.IsNotNull(logger, nameof(logger)); this.logger = logger; this.messageBroker = messageBroker; this.subscriptionMap = subscriptionMap; }
public StorageQueueMessageBroker( ILogger <StorageQueueMessageBroker> logger, string storageConnectionString, IMessageHandlerFactory handlerFactory, ISubscriptionMap map = null) { EnsureArg.IsNotNull(logger, nameof(logger)); EnsureArg.IsNotNullOrEmpty(storageConnectionString, nameof(storageConnectionString)); EnsureArg.IsNotNull(handlerFactory, nameof(handlerFactory)); this.logger = logger; this.storageConnectionString = storageConnectionString; this.map = map ?? new SubscriptionMap(); this.handlerFactory = handlerFactory; // maybe not a good fit for a message broker // https://docs.microsoft.com/en-us/azure/service-bus-messaging/service-bus-azure-and-service-bus-queues-compared-contrasted // - no push style api (no onmessage()) // - single subscriber only (due to message.dequeue), has peek however }
#pragma warning disable SA1204 // Static elements should appear before instance elements #pragma warning disable SA1202 // Elements should be ordered by access /// <summary> /// Processes the message by invoking the message handler. /// </summary> public static async Task <bool> ProcessMessage( ILogger <ServiceBusMessageBroker> logger, ITracer tracer, ISubscriptionMap subscriptions, IMessageHandlerFactory handlerFactory, ISerializer serializer, string messageScope, IMediator mediator, Microsoft.Azure.ServiceBus.Message serviceBusMessage) #pragma warning restore SA1204 // Static elements should appear before instance elements #pragma warning restore SA1202 // Elements should be ordered by access { var processed = false; var messageName = serviceBusMessage.Label; if (subscriptions.Exists(messageName)) { foreach (var subscription in subscriptions.GetAll(messageName)) { var messageType = subscriptions.GetByName(messageName); if (messageType == null) { continue; } // get parent span infos from message ISpan parentSpan = null; if (serviceBusMessage.UserProperties.ContainsKey("TraceId") && serviceBusMessage.UserProperties.ContainsKey("SpanId")) { // dehydrate parent span parentSpan = new Span(serviceBusMessage.UserProperties["TraceId"] as string, serviceBusMessage.UserProperties["SpanId"] as string); } using (logger.BeginScope(new Dictionary <string, object> { [LogPropertyKeys.CorrelationId] = serviceBusMessage.CorrelationId, //[LogPropertyKeys.TrackId] = scope.Span.SpanId = allready done in Span ScopeManager (activate) })) using (var scope = tracer?.BuildSpan(messageName, LogKeys.AppMessaging, SpanKind.Consumer, parentSpan).Activate(logger)) { // map some message properties to the typed message //var jsonMessage = JsonConvert.DeserializeObject(Encoding.UTF8.GetString(serviceBusMessage.Body), messageType); // TODO: use ISerializer here, compacter messages //var message = jsonMessage as Domain.Message; if (!(serializer.Deserialize(serviceBusMessage.Body, messageType) is Domain.Message message)) { return(false); } // TODO: message can be null, skip if (message.Origin.IsNullOrEmpty()) { //message.CorrelationId = jsonMessage.AsJToken().GetStringPropertyByToken("CorrelationId"); message.Origin = serviceBusMessage.UserProperties.ContainsKey("Origin") ? serviceBusMessage.UserProperties["Origin"] as string : string.Empty; } logger.LogJournal(LogKeys.AppMessaging, $"message processed: {serviceBusMessage.Label} (id={{MessageId}}, service={{Service}}, origin={{MessageOrigin}}, size={serviceBusMessage.Body.Length.Bytes().ToString("#.##")})", LogPropertyKeys.TrackReceiveMessage, args: new[] { message?.Id, messageScope, message.Origin }); logger.LogTrace(LogKeys.AppMessaging, message.Id, serviceBusMessage.Label, LogTraceNames.Message); // construct the handler by using the DI container var handler = handlerFactory.Create(subscription.HandlerType); // should not be null, did you forget to register your generic handler (EntityMessageHandler<T>) var concreteType = typeof(IMessageHandler <>).MakeGenericType(messageType); var method = concreteType.GetMethod("Handle"); if (handler != null && method != null) { if (mediator != null) { await mediator.Publish(new MessageHandledDomainEvent(message, messageScope)).AnyContext(); } await((Task)method.Invoke(handler, new object[] { message as object })).AnyContext(); } else { logger.LogWarning("{LogKey:l} process failed, message handler could not be created. is the handler registered in the service provider? (name={MessageName}, service={Service}, id={MessageId}, origin={MessageOrigin})", LogKeys.AppMessaging, serviceBusMessage.Label, messageScope, message.Id, message.Origin); } } } processed = true; } else { logger.LogDebug($"{{LogKey:l}} unprocessed: {messageName}", LogKeys.AppMessaging); } return(processed); }
public ServiceBusMessageBrokerOptionsBuilder Map(ISubscriptionMap map) { this.Target.Map = map; return(this); }
public SignalRServerlessMessageBrokerOptionsBuilder Map(ISubscriptionMap map) { this.Target.Map = map; return(this); }
public RabbitMQMessageBrokerOptionsBuilder Subscriptions(ISubscriptionMap subscriptions) { this.Target.Subscriptions = subscriptions; return(this); }
public ServiceBusMessageBrokerOptionsBuilder Subscriptions(ISubscriptionMap subscriptions) { this.Target.Subscriptions = subscriptions; return(this); }
public SignalRServerlessMessageBrokerOptionsBuilder Subscriptions(ISubscriptionMap subscriptions) { this.Target.Subscriptions = subscriptions; return(this); }
public FileStorageMessageBrokerOptionsBuilder Subscriptions(ISubscriptionMap subscriptions) { this.Target.Subscriptions = subscriptions; return(this); }
public FileStorageMessageBrokerOptionsBuilder Map(ISubscriptionMap map) { this.Target.Map = map; return(this); }