public async Task <IAggregateRoot> RefreshAggregateFromEventStoreAsync(string aggregateRootTypeName, string aggregateRootId) { try { var aggregateRootType = _typeNameProvider.GetType(aggregateRootTypeName); if (aggregateRootType == null) { _logger.ErrorFormat("Could not find aggregate root type by aggregate root type name [{0}].", aggregateRootTypeName); return(null); } var aggregateRoot = await _aggregateStorage.GetAsync(aggregateRootType, aggregateRootId); if (aggregateRoot != null) { ResetAggregateRootCache(aggregateRoot); return(aggregateRoot); } return(null); } catch (Exception ex) { _logger.Error(string.Format("Refresh aggregate from event store has unknown exception, aggregateRootTypeName:{0}, aggregateRootId:{1}", aggregateRootTypeName, aggregateRootId), ex); return(null); } }
/// <summary> /// Start /// </summary> /// <returns></returns> public DomainExceptionConsumer Start() { _consumer.OnMessageReceived += (sender, e) => { try { var exceptionType = _typeNameProvider.GetType(e.Context.GetMessageType()); var exceptionMessage = _jsonSerializer.Deserialize <DomainExceptionMessage>(Encoding.UTF8.GetString(e.Context.GetBody())); var exception = FormatterServices.GetUninitializedObject(exceptionType) as IDomainException; exception.Id = exceptionMessage.UniqueId; exception.Timestamp = exceptionMessage.Timestamp; exception.Items = exceptionMessage.Items; exception.RestoreFrom(exceptionMessage.SerializableInfo); _logger.DebugFormat("ENode domain exception message received, messageId: {0}, exceptionType: {1}", exceptionMessage.UniqueId, exceptionType.Name); _messageDispatcher.DispatchMessageAsync(exception).ContinueWith(x => { e.Context.Ack(); }); } catch (Exception ex) { _logger.Error($"ENode domain exception message handle failed: {ex.Message}, exception message: {Encoding.UTF8.GetString(e.Context.GetBody())}", ex); } }; _consumer.Start(); return(this); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var applicationMessageType = _typeNameProvider.GetType(queueMessage.Tag); var message = _jsonSerializer.Deserialize(Encoding.UTF8.GetString(queueMessage.Body), applicationMessageType) as IApplicationMessage; var processContext = new EQueueProcessContext(queueMessage, context); var processingMessage = new ProcessingApplicationMessage(message, processContext); _processor.Process(processingMessage); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var applicationMessageType = _typeNameProvider.GetType(queueMessage.Tag); var message = _jsonSerializer.Deserialize(Encoding.UTF8.GetString(queueMessage.Body), applicationMessageType) as IApplicationMessage; var processContext = new EQueueProcessContext(queueMessage, context); var processingMessage = new ProcessingApplicationMessage(message, processContext); _logger.InfoFormat("ENode application message received, messageId: {0}, routingKey: {1}", message.Id, message.GetRoutingKey()); _processor.Process(processingMessage); }
void IKafkaMessageHandler.Handle(KafkaMessage message, IKafkaMessageContext context) { var eNodeMessage = _jsonSerializer.Deserialize <ENodeMessage>(message.Value); var applicationMessageType = _typeNameProvider.GetType(eNodeMessage.Tag); var applicationMessage = _jsonSerializer.Deserialize(eNodeMessage.Body, applicationMessageType) as IApplicationMessage; var processContext = new KafkaMessageProcessContext(message, context); var processingMessage = new ProcessingApplicationMessage(applicationMessage, processContext); _logger.InfoFormat("ENode application message received, messageId: {0}, routingKey: {1}", applicationMessage.Id, applicationMessage.GetRoutingKey()); _processor.Process(processingMessage); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var applicationMessageType = _typeNameProvider.GetType(queueMessage.Tag); var message = _jsonSerializer.Deserialize(Encoding.UTF8.GetString(queueMessage.Body), applicationMessageType) as IApplicationMessage; _logger.DebugFormat("ENode application message received, messageId: {0}, messageType: {1}", message.Id, message.GetType().Name); _messageDispatcher.DispatchMessageAsync(message).ContinueWith(x => { context.OnMessageHandled(queueMessage); }); }
public async Task HandleAsync(KafkaMessage kafkaMessage, IKafkaMessageContext context) { var eNodeMessage = _jsonSerializer.Deserialize <ENodeMessage>(kafkaMessage.Message.Value); var applicationMessageType = _typeNameProvider.GetType(eNodeMessage.Tag); var applicationMessage = _jsonSerializer.Deserialize(eNodeMessage.Body, applicationMessageType) as IApplicationMessage; _logger.DebugFormat("ENode application message received, messageId: {0}, messageType: {1}", applicationMessage.Id, applicationMessage.GetType().Name); await _messageDispatcher.DispatchMessageAsync(applicationMessage).ContinueWith(x => { context.OnMessageHandled(kafkaMessage); }); }
public IEnumerable <TEvent> Deserialize <TEvent>(IDictionary <string, string> data) where TEvent : class, IDomainEvent { var evnts = new List <TEvent>(); foreach (var entry in data) { var eventType = _typeNameProvider.GetType(entry.Key); var evnt = _jsonSerializer.Deserialize(entry.Value, eventType) as TEvent; evnts.Add(evnt); } return(evnts); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var applicationMessageString = Encoding.UTF8.GetString(queueMessage.Body); _logger.InfoFormat("Received application message equeue message: {0}, applicationMessage: {1}", queueMessage, applicationMessageString); var applicationMessageType = _typeNameProvider.GetType(queueMessage.Tag); var message = _jsonSerializer.Deserialize(applicationMessageString, applicationMessageType) as IApplicationMessage; _messageDispatcher.DispatchMessageAsync(message).ContinueWith(x => { context.OnMessageHandled(queueMessage); }); }
public Task <IAggregateRoot> RefreshAggregateFromEventStoreAsync(string aggregateRootTypeName, object aggregateRootId) { if (aggregateRootTypeName == null) { throw new ArgumentNullException("aggregateRootTypeName"); } var aggregateRootType = _typeNameProvider.GetType(aggregateRootTypeName); if (aggregateRootType == null) { _logger.ErrorFormat("Could not find aggregate root type by aggregate root type name [{0}].", aggregateRootTypeName); return(null); } return(RefreshAggregateFromEventStoreAsync(aggregateRootType, aggregateRootId)); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var applicationMessageType = _typeNameProvider.GetType(queueMessage.Tag); var message = _jsonSerializer.Deserialize(Encoding.UTF8.GetString(queueMessage.Body), applicationMessageType) as IApplicationMessage; var processContext = new EQueueProcessContext(queueMessage, context); var processingMessage = new ProcessingApplicationMessage(message, processContext); _logger.DebugFormat("ENode application message received, messageId: {0}", message.Id); Task.Factory.StartNew(obj => { _messageDispatcher.DispatchMessageAsync(((ProcessingApplicationMessage)obj).Message).ContinueWith(x => { processingMessage.Complete(); }); }, processingMessage); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var exceptionType = _typeNameProvider.GetType(queueMessage.Tag); var exceptionMessage = _jsonSerializer.Deserialize <PublishableExceptionMessage>(Encoding.UTF8.GetString(queueMessage.Body)); var exception = FormatterServices.GetUninitializedObject(exceptionType) as IPublishableException; exception.Id = exceptionMessage.UniqueId; exception.Timestamp = exceptionMessage.Timestamp; exception.Items = exceptionMessage.Items; exception.RestoreFrom(exceptionMessage.SerializableInfo); _logger.DebugFormat("ENode publishable exception message received, messageId: {0}, exceptionType: {1}", exceptionMessage.UniqueId, exceptionType.Name); _messageDispatcher.DispatchMessageAsync(exception).ContinueWith(x => { context.OnMessageHandled(queueMessage); }); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var exceptionType = _typeNameProvider.GetType(queueMessage.Tag); var domainExceptionString = Encoding.UTF8.GetString(queueMessage.Body); _logger.InfoFormat("Received domain exception equeue message: {0}, domainExceptionMessage: {1}", queueMessage, domainExceptionString); var exceptionMessage = _jsonSerializer.Deserialize <DomainExceptionMessage>(domainExceptionString); var exception = FormatterServices.GetUninitializedObject(exceptionType) as IDomainException; exception.Id = exceptionMessage.UniqueId; exception.Timestamp = exceptionMessage.Timestamp; exception.Items = exceptionMessage.Items; exception.RestoreFrom(exceptionMessage.SerializableInfo); _messageDispatcher.DispatchMessageAsync(exception).ContinueWith(x => { context.OnMessageHandled(queueMessage); }); }
public async Task HandleAsync(KafkaMessage kafkaMessage, IKafkaMessageContext context) { var eNodeMessage = _jsonSerializer.Deserialize <ENodeMessage>(kafkaMessage.Message.Value); var exceptionMessage = _jsonSerializer.Deserialize <DomainExceptionMessage>(eNodeMessage.Body); var exceptionType = _typeNameProvider.GetType(eNodeMessage.Tag); var exception = FormatterServices.GetUninitializedObject(exceptionType) as IDomainException; exception.Id = exceptionMessage.UniqueId; exception.Timestamp = exceptionMessage.Timestamp; exception.Items = exceptionMessage.Items; exception.RestoreFrom(exceptionMessage.SerializableInfo); _logger.DebugFormat("ENode domain exception message received, messageId: {0}, exceptionType: {1}", exceptionMessage.UniqueId, exceptionType.Name); await _messageDispatcher.DispatchMessageAsync(exception).ContinueWith(x => { context.OnMessageHandled(kafkaMessage); }); }
public void RefreshAggregateFromEventStore(string aggregateRootTypeName, string aggregateRootId) { try { var aggregateRootType = _typeNameProvider.GetType(aggregateRootTypeName); if (aggregateRootType == null) { _logger.ErrorFormat("Could not find aggregate root type by aggregate root type name [{0}].", aggregateRootTypeName); return; } var aggregateRoot = _aggregateStorage.Get(aggregateRootType, aggregateRootId); if (aggregateRoot != null) { SetInternal(aggregateRoot); } } catch (Exception ex) { _logger.Error(string.Format("Refresh aggregate from event store has unknown exception, aggregateRootTypeName:{0}, aggregateRootId:{1}", aggregateRootTypeName, aggregateRootId), ex); } }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var exceptionMessage = _jsonSerializer.Deserialize <PublishableExceptionMessage>(Encoding.UTF8.GetString(queueMessage.Body)); var exceptionType = _typeNameProvider.GetType(queueMessage.Tag); var exception = FormatterServices.GetUninitializedObject(exceptionType) as IPublishableException; exception.Id = exceptionMessage.UniqueId; exception.Timestamp = exceptionMessage.Timestamp; exception.RestoreFrom(exceptionMessage.SerializableInfo); var sequenceMessage = exception as ISequenceMessage; if (sequenceMessage != null) { sequenceMessage.AggregateRootTypeName = exceptionMessage.AggregateRootTypeName; sequenceMessage.AggregateRootStringId = exceptionMessage.AggregateRootId; } var processContext = new EQueueProcessContext(queueMessage, context); var processingMessage = new ProcessingPublishableExceptionMessage(exception, processContext); _publishableExceptionProcessor.Process(processingMessage); }
void IQueueMessageHandler.Handle(QueueMessage queueMessage, IMessageContext context) { var exceptionMessage = _jsonSerializer.Deserialize <PublishableExceptionMessage>(Encoding.UTF8.GetString(queueMessage.Body)); var exceptionType = _typeNameProvider.GetType(queueMessage.Tag); var exception = FormatterServices.GetUninitializedObject(exceptionType) as IPublishableException; exception.Id = exceptionMessage.UniqueId; exception.Timestamp = exceptionMessage.Timestamp; exception.RestoreFrom(exceptionMessage.SerializableInfo); var processContext = new EQueueProcessContext(queueMessage, context); var processingMessage = new ProcessingPublishableExceptionMessage(exception, processContext); _logger.DebugFormat("ENode exception message received, messageId: {0}, aggregateRootId: {1}, aggregateRootType: {2}", exceptionMessage.UniqueId, exceptionMessage.AggregateRootId, exceptionMessage.AggregateRootTypeName); Task.Factory.StartNew(obj => { _messageDispatcher.DispatchMessageAsync(((ProcessingPublishableExceptionMessage)obj).Message).ContinueWith(x => { processingMessage.Complete(); }); }, processingMessage); }
private void RefreshAggregateMemoryCache(DomainEventStream aggregateFirstEventStream) { try { var aggregateRootType = _typeNameProvider.GetType(aggregateFirstEventStream.AggregateRootTypeName); var aggregateRoot = _memoryCache.Get(aggregateFirstEventStream.AggregateRootId, aggregateRootType); if (aggregateRoot == null) { aggregateRoot = _aggregateRootFactory.CreateAggregateRoot(aggregateRootType); aggregateRoot.ReplayEvents(new DomainEventStream[] { aggregateFirstEventStream }); _memoryCache.Set(aggregateRoot); if (_logger.IsDebugEnabled) { _logger.DebugFormat("Aggregate added into memory, commandId:{0}, aggregateRootType:{1}, aggregateRootId:{2}, aggregateRootVersion:{3}", aggregateFirstEventStream.CommandId, aggregateRootType.Name, aggregateRoot.UniqueId, aggregateRoot.Version); } } } catch (Exception ex) { _logger.Error(string.Format("Refresh memory cache by aggregate first event stream failed, {0}", aggregateFirstEventStream), ex); } }
public void Handle(KafkaMessage message, IKafkaMessageContext context) { var eNodeMessage = _jsonSerializer.Deserialize <ENodeMessage>(message.Value); var exceptionMessage = _jsonSerializer.Deserialize <PublishableExceptionMessage>(eNodeMessage.Body); var exceptionType = _typeNameProvider.GetType(eNodeMessage.Tag); var exception = FormatterServices.GetUninitializedObject(exceptionType) as IPublishableException; exception.Id = exceptionMessage.UniqueId; exception.Timestamp = exceptionMessage.Timestamp; exception.RestoreFrom(exceptionMessage.SerializableInfo); var sequenceMessage = exception as ISequenceMessage; if (sequenceMessage != null) { sequenceMessage.AggregateRootTypeName = exceptionMessage.AggregateRootTypeName; sequenceMessage.AggregateRootStringId = exceptionMessage.AggregateRootId; } var processContext = new KafkaMessageProcessContext(message, context); var processingMessage = new ProcessingPublishableExceptionMessage(exception, processContext); _logger.InfoFormat("ENode exception message received, messageId: {0}, aggregateRootId: {1}, aggregateRootType: {2}", exceptionMessage.UniqueId, exceptionMessage.AggregateRootId, exceptionMessage.AggregateRootTypeName); _publishableExceptionProcessor.Process(processingMessage); }
/// <summary> /// Start /// </summary> /// <returns></returns> public ApplicationMessageConsumer Start() { _consumer.OnMessageReceived += (sender, e) => { try { var applicationMessageType = _typeNameProvider.GetType(e.Context.GetMessageType()); var message = _jsonSerializer.Deserialize(Encoding.UTF8.GetString(e.Context.GetBody()), applicationMessageType) as IApplicationMessage; _logger.DebugFormat("ENode application message received, messageId: {0}, messageType: {1}", message.Id, message.GetType().Name); _messageDispatcher.DispatchMessageAsync(message).ContinueWith(x => { e.Context.Ack(); }); } catch (Exception ex) { _logger.Error($"ENode application message handle failed: {ex.Message}, body: {Encoding.UTF8.GetString(e.Context.GetBody())}, messageType: {e.Context.GetMessageType()}", ex); } }; _consumer.Start(); return(this); }
public async Task <AsyncTaskResult> UpdatePublishedVersionAsync(string processorName, string aggregateRootTypeName, string aggregateRootId, int publishedVersion) { if (publishedVersion == 1) { var record = new PublishedVersion() { ProcessorName = processorName, AggregateRootTypeName = aggregateRootTypeName, AggregateRootId = aggregateRootId, Version = 1, CreatedOn = DateTime.UtcNow }; try { await _publishedVersionCollection.GetCollection(aggregateRootId).InsertOneAsync(record); return(AsyncTaskResult.Success); } catch (MongoWriteException ex) { if (ex.WriteError.Code == 11000 && ex.Message.Contains(nameof(record.ProcessorName)) && ex.Message.Contains(nameof(record.AggregateRootId)) && ex.Message.Contains(nameof(record.Version))) { return(AsyncTaskResult.Success); } _logger.Error("Insert aggregate published version has write exception.", ex); return(new AsyncTaskResult(AsyncTaskStatus.IOException, ex.Message)); } catch (Exception ex) { _logger.Error("Insert aggregate published version has unknown exception.", ex); return(new AsyncTaskResult(AsyncTaskStatus.Failed, ex.Message)); } } else { try { var builder = Builders <PublishedVersion> .Filter; var filter = builder.Eq(e => e.ProcessorName, processorName) & builder.Eq(e => e.AggregateRootId, aggregateRootId) & builder.Eq(e => e.Version, publishedVersion - 1); var update = Builders <PublishedVersion> .Update .Set(e => e.Version, publishedVersion) .Set(e => e.CreatedOn, DateTime.UtcNow); await _publishedVersionCollection.GetCollection(aggregateRootId) .UpdateOneAsync(filter, update); await _savableAggregateSnapshotter.SaveSnapshotAsync(aggregateRootId, _typeNameProvider.GetType(aggregateRootTypeName), publishedVersion); return(AsyncTaskResult.Success); } catch (MongoException ex) { _logger.Error("Update aggregate published version has update exception.", ex); return(new AsyncTaskResult(AsyncTaskStatus.IOException, ex.Message)); } catch (Exception ex) { _logger.Error("Update aggregate published version has unknown exception.", ex); return(new AsyncTaskResult(AsyncTaskStatus.Failed, ex.Message)); } } }
/// <summary> /// Save /// </summary> /// <param name="snapshotHeaders"></param> /// <returns></returns> public async Task SaveAsync(IEnumerable <AggregateSnapshotHeader> snapshotHeaders) { var queue = new ConcurrentQueue <AggregateSnapshotData>(); foreach (var snapshotHeader in snapshotHeaders) { try { var aggregateRootType = _typeNameProvider.GetType(snapshotHeader.AggregateRootTypeName); IAggregateRoot aggregateRoot = null; IEnumerable <DomainEventStream> eventStreams = null; var lastSnapshotData = await _snapshotStore.FindLatestAsync(snapshotHeader.AggregateRootId, snapshotHeader.AggregateRootTypeName); if (lastSnapshotData != null) { try { using (var ms = new MemoryStream()) { await ms.WriteAsync(lastSnapshotData.Data, 0, lastSnapshotData.Data.Length); await ms.FlushAsync(); ms.Position = 0; aggregateRoot = _binaryFormatter.Deserialize(ms) as IAggregateRoot; } } catch { aggregateRoot = null; } } if (aggregateRoot == null) { // 无快照 aggregateRoot = _aggregateRootFactory.CreateAggregateRoot(aggregateRootType); eventStreams = await _eventStore.QueryAggregateEventsAsync(snapshotHeader.AggregateRootId, snapshotHeader.AggregateRootTypeName, 1, snapshotHeader.Version); } else { eventStreams = await _eventStore.QueryAggregateEventsAsync(snapshotHeader.AggregateRootId, snapshotHeader.AggregateRootTypeName, lastSnapshotData.Version + 1, snapshotHeader.Version); } if (eventStreams != null && eventStreams.Any()) { aggregateRoot.ReplayEvents(eventStreams); using (var ms = new MemoryStream()) { _binaryFormatter.Serialize(ms, aggregateRoot); await ms.FlushAsync(); ms.Position = 0; byte[] buffer = new byte[ms.Length]; await ms.ReadAsync(buffer, 0, buffer.Length); queue.Enqueue(new AggregateSnapshotData(snapshotHeader.AggregateRootId, snapshotHeader.AggregateRootTypeName, aggregateRoot.Version, buffer)); } } } catch (Exception ex) { _logger.Error($"Save snapshot fail:{ex.Message}. AggregateRootId={snapshotHeader.AggregateRootId},AggregateRootTypeName={snapshotHeader.AggregateRootTypeName}", ex); } } var snapshotDataList = new List <AggregateSnapshotData>(); while (queue.TryDequeue(out AggregateSnapshotData snapshotData)) { snapshotDataList.Add(snapshotData); if (snapshotDataList.Count == _batchSaveSize) { try { await _snapshotStore.BatchSaveAsync(snapshotDataList); } catch (Exception ex) { _logger.Error($"Save snapshot fail:{ex.Message}.", ex); } finally { snapshotDataList.Clear(); } } } }
public async Task UpdatePublishedVersionAsync(string processorName, string aggregateRootTypeName, string aggregateRootId, int publishedVersion) { if (publishedVersion == 1) { var record = new PublishedVersion() { ProcessorName = processorName, AggregateRootTypeName = aggregateRootTypeName, AggregateRootId = aggregateRootId, Version = 1, CreatedOn = DateTime.UtcNow }; try { await _publishedVersionCollection.GetCollection(aggregateRootId).InsertOneAsync(record); } catch (MongoWriteException ex) { if (ex.WriteError.Code == 11000 && ex.Message.Contains(nameof(PublishedVersion.ProcessorName)) && ex.Message.Contains(nameof(PublishedVersion.AggregateRootId)) && ex.Message.Contains(nameof(PublishedVersion.Version))) { return; } var errorMessage = string.Format("Insert aggregate published version has mongo exception, aggregateRootType: {0}, aggregateRootId: {1}", aggregateRootTypeName, aggregateRootId); _logger.Error(errorMessage, ex); throw; } catch (Exception ex) { var errorMessage = string.Format("Insert aggregate published version has unknown exception, aggregateRootType: {0}, aggregateRootId: {1}", aggregateRootTypeName, aggregateRootId); _logger.Error(errorMessage, ex); throw; } } else { try { var builder = Builders <PublishedVersion> .Filter; var filter = builder.Eq(e => e.ProcessorName, processorName) & builder.Eq(e => e.AggregateRootId, aggregateRootId) & builder.Eq(e => e.Version, publishedVersion - 1); var update = Builders <PublishedVersion> .Update .Set(e => e.Version, publishedVersion) .Set(e => e.CreatedOn, DateTime.UtcNow); await _publishedVersionCollection.GetCollection(aggregateRootId) .UpdateOneAsync(filter, update); await _aggregateSnapshotSaver.SaveAsync(aggregateRootId, _typeNameProvider.GetType(aggregateRootTypeName), publishedVersion); } catch (MongoException ex) { var errorMessage = string.Format("Update aggregate published version has mongo exception, aggregateRootType: {0}, aggregateRootId: {1}", aggregateRootTypeName, aggregateRootId); _logger.Error(errorMessage, ex); throw; } catch (Exception ex) { var errorMessage = string.Format("Update aggregate published version has unknown exception, aggregateRootType: {0}, aggregateRootId: {1}", aggregateRootTypeName, aggregateRootId); _logger.Error(errorMessage, ex); throw; } } }