public static async Task PublishMessage(Message message, IPrincipal principal, IModel channel, QueueName queueName, string exchange = "", Encoding encoding = null, int attempts = 0) { if (message == null) throw new ArgumentNullException("message"); if (channel == null) throw new ArgumentNullException("channel"); if (encoding == null) { encoding = Encoding.UTF8; } var senderPrincipal = principal as SenderPrincipal; if (senderPrincipal == null && principal != null) { senderPrincipal = new SenderPrincipal(principal); } using (var stringWriter = new StringWriter()) using (var messageWriter = new MessageWriter(stringWriter)) { await messageWriter.WritePrincipal(senderPrincipal); await messageWriter.WriteMessage(message); var messageBody = stringWriter.ToString(); var properties = channel.CreateBasicProperties(); properties.SetPersistent(true); properties.ContentEncoding = Encoding.UTF8.HeaderName; properties.ContentType = message.Headers.ContentType; properties.MessageId = message.Headers.MessageId.ToString(); properties.CorrelationId = message.Headers.RelatedTo.ToString(); var headers = properties.Headers; if (headers == null) { headers = new Dictionary<string, object>(); properties.Headers = headers; } headers["x-platibus-attempts"] = attempts; var body = encoding.GetBytes(messageBody); var ex = exchange ?? ""; var q = (string) queueName ?? ""; channel.BasicPublish(ex, q, properties, body); } }
private async Task HandleMessageImmediately(Message message, SenderPrincipal senderPrincipal, bool isReply) { var messageContext = new BusMessageContext(this, message.Headers, senderPrincipal); var handlers = _handlingRules .Where(r => r.Specification.IsSatisfiedBy(message)) .Select(rule => rule.MessageHandler) .ToList(); if (!handlers.Any() && isReply) { // TODO: Figure out what to do here. return; } await MessageHandler.HandleMessage(_messageNamingService, _serializationService, handlers, message, messageContext, _cancellationTokenSource.Token); if (!messageContext.MessageAcknowledged) { throw new MessageNotAcknowledgedException(); } }
protected virtual string SerializePrincipal(IPrincipal principal) { if (principal == null) return null; var senderPrincipal = new SenderPrincipal(principal); using (var memoryStream = new MemoryStream()) { var formatter = new BinaryFormatter(); formatter.Serialize(memoryStream, senderPrincipal); var base64String = Convert.ToBase64String(memoryStream.GetBuffer()); return base64String; } }
/// <summary> /// Called by the host when a new message arrives to handle the message /// </summary> /// <param name="message">The new message</param> /// <param name="principal">The sender principal</param> /// <returns>Returns a task that completes when message handling is complete</returns> public async Task HandleMessage(Message message, IPrincipal principal) { if (_messageJournalingService != null) { await _messageJournalingService.MessageReceived(message); } // Make sure that the principal is serializable before enqueuing var senderPrincipal = principal as SenderPrincipal; if (senderPrincipal == null && principal != null) { senderPrincipal = new SenderPrincipal(principal); } var tasks = new List<Task>(); var relatedToMessageId = message.Headers.RelatedTo; var isReply = relatedToMessageId != default(MessageId); if (isReply) { tasks.Add(NotifyReplyReceived(message)); } var importance = message.Headers.Importance; if (importance.RequiresQueueing) { // Message expiration handled in MessageHandlingListener tasks.AddRange(_handlingRules .Where(r => r.Specification.IsSatisfiedBy(message)) .Select(rule => rule.QueueName) .Distinct() .Select(q => _messageQueueingService.EnqueueMessage(q, message, senderPrincipal))); } else { tasks.Add(HandleMessageImmediately(message, senderPrincipal, isReply)); } await Task.WhenAll(tasks); }