/// <summary> /// Publisher /// </summary> protected TResponse Publish <TRequest, TResponse>(TRequest request, TimeSpan?ttl) { if (request == null) { throw new ArgumentNullException(nameof(request)); } if (!(request is Exception) && Descriptor.IsAsync) { throw new NotSupportedException(); } _consumer.Received += OnConsumerOnReceived; var requestBytes = _serializer.Serialize(request); var properties = GetBasicProperties(1, ttl); properties.CorrelationId = Guid.NewGuid().ToString(); properties.ReplyTo = _model.QueueDeclare().QueueName; _model.BasicConsume(properties.ReplyTo, true, _consumer); _model.BasicPublish(string.Empty, Descriptor.QueueName, properties, requestBytes); BasicDeliverEventArgs args; try { var ctx = new CancellationTokenSource(); Task.Delay(_config.GetResponseTimeout(), CancellationToken.None).ContinueWith(c => ctx.Cancel(), CancellationToken.None); args = _blockingCollection.Take(ctx.Token); } catch (OperationCanceledException) { throw new TimeoutException(); } if (true != args.BasicProperties?.Headers?.ContainsKey(nameof(Exception))) { var response = _serializer.Deserialize(typeof(TResponse), args.Body); return((TResponse)response); } var exception = _serializer.Deserialize(typeof(Exception), args.Body) as Exception ?? new SystemException(); throw exception; }