コード例 #1
0
        public IEnumerable <AggregateCommit> Apply(AggregateCommit current)
        {
            if (ShouldApply(current))
            {
                var urnRaw = Urn.Parse(Encoding.UTF8.GetString(current.AggregateRootId));
                var urn    = AggregateUrn.Parse(urnRaw.Value);
                var fooId  = new FooId(urn.Id, urn.Tenant);
                LoadFromEventStore(fooId);
                aggregateMaxRevision[fooId]++;

                var newFooEvents = new List <IEvent>();
                foreach (IEvent @event in current.Events)
                {
                    if (@event.GetType() == typeof(TestCreateEventBar))
                    {
                        newFooEvents.Add(new TestCreateEventFoo(fooId));
                    }
                    else if (@event.GetType() == typeof(TestUpdateEventBar))
                    {
                        var theEvent = @event as TestUpdateEventBar;
                        newFooEvents.Add(new TestUpdateEventFoo(fooId, theEvent.UpdatedFieldValue));
                    }
                }
                var aggregateCommitFooBar = new AggregateCommit(fooId.RawId, aggregateMaxRevision[fooId], newFooEvents);
                yield return(aggregateCommitFooBar);
            }
            else
            {
                yield return(current);
            }
        }
コード例 #2
0
        public IEnumerable <AggregateCommit> Apply(AggregateCommit current)
        {
            if (ShouldApply(current))
            {
                var    urnRaw = Urn.Parse(Encoding.UTF8.GetString(current.AggregateRootId));
                var    urn    = AggregateUrn.Parse(urnRaw.Value);
                string currentAggregateName = urn.AggregateRootName;

                if (currentAggregateName == targetAggregateFoo)
                {
                    var fooBarId        = new FooBarId("1234", "elders");
                    var newFooBarEvents = new List <IEvent>();
                    foreach (IEvent @event in current.Events)
                    {
                        if (@event.GetType() == typeof(TestCreateEventFoo))
                        {
                            newFooBarEvents.Add(new TestCreateEventFooBar(fooBarId));
                        }
                        else if (@event.GetType() == typeof(TestUpdateEventFoo))
                        {
                            var theEvent = @event as TestUpdateEventFoo;
                            newFooBarEvents.Add(new TestUpdateEventFooBar(fooBarId, theEvent.UpdatedFieldValue));
                        }
                    }

                    HandleMaxRevision(fooBarId);
                    var aggregateCommitFooBar = new AggregateCommit(fooBarId.RawId, aggregateMaxRevision[fooBarId], newFooBarEvents);
                    yield return(aggregateCommitFooBar);
                }
                else
                {
                    var fooBarId        = new FooBarId("1234", "elders");
                    var newFooBarEvents = new List <IEvent>();
                    foreach (IEvent @event in current.Events)
                    {
                        if (@event.GetType() == typeof(TestCreateEventBar))
                        {
                            newFooBarEvents.Add(new TestCreateEventFooBar(fooBarId));
                        }
                        else if (@event.GetType() == typeof(TestUpdateEventBar))
                        {
                            var theEvent = @event as TestUpdateEventBar;
                            newFooBarEvents.Add(new TestUpdateEventFooBar(fooBarId, theEvent.UpdatedFieldValue));
                        }
                    }
                    HandleMaxRevision(fooBarId);
                    var aggregateCommitFooBar = new AggregateCommit(fooBarId.RawId, aggregateMaxRevision[fooBarId], newFooBarEvents);
                    yield return(aggregateCommitFooBar);
                }
            }
            else
            {
                yield return(current);
            }
        }
コード例 #3
0
        public bool ShouldApply(AggregateCommit current)
        {
            var    urnRaw = Urn.Parse(Encoding.UTF8.GetString(current.AggregateRootId));
            var    urn    = AggregateUrn.Parse(urnRaw.Value);
            string currentAggregateName = urn.AggregateRootName;

            if (currentAggregateName == targetAggregateName)
            {
                return(true);
            }

            return(false);
        }
コード例 #4
0
        public void Handle(CreateSimpleMessage command)
        {
            var arResult = repository.Load <SimpleMessageAggregate>(AggregateUrn.Parse(command.Id.Value));

            if (arResult.IsSuccess)
            {
                return;
            }
            else
            {
                var notFound = new SimpleMessageAggregate(command.Id, command.Timestamp);
                repository.Save(notFound);
            }
        }
コード例 #5
0
        bool TryResolve(byte[] id, out string tenant)
        {
            tenant = string.Empty;
            var          urn = System.Text.Encoding.UTF8.GetString(id);
            AggregateUrn aggregateUrn;

            if (AggregateUrn.TryParse(urn, out aggregateUrn))
            {
                tenant = aggregateUrn.Tenant;
                return(true);
            }

            return(false);
        }
コード例 #6
0
        public async Task <IActionResult> Explore([FromQuery] RequestModel model)
        {
            AggregateDto result = new AggregateDto();

            try
            {
                result = await _eventExplorer.ExploreAsync(AggregateUrn.Parse(model.Id, Urn.Uber));
            }
            catch (Exception ex)
            {
                logger.ErrorException(ex, () => $"Failed to explore aggregate for {model.Id}");
            }

            return(new OkObjectResult(new ResponseResult <AggregateDto>(result)));
        }
コード例 #7
0
        public async Task <IActionResult> Republish([FromBody] RepublishRequest model)
        {
            var arId = AggregateUrn.Parse(model.Id, Urn.Uber);

            if (model.IsPublicEvent)
            {
                IPublicEvent @event = await _eventExplorer.FindPublicEventAsync(arId, model.CommitRevision, model.EventPosition);

                if (@event is null)
                {
                    return(BadRequest("Event not found"));
                }

                Dictionary <string, string> headers = new Dictionary <string, string>()
                {
                    { MessageHeader.AggregateRootId, arId.ToBase64() }
                };

                publicPublisher.Publish(@event, headers);
            }
            else
            {
                IEvent @event = await _eventExplorer.FindEventAsync(arId, model.CommitRevision, model.EventPosition);

                if (@event is null)
                {
                    return(BadRequest("Event not found"));
                }

                string recipientHandlers = ConcatRecipientHandlers(model.RecipientHandlers);

                Dictionary <string, string> headers = new Dictionary <string, string>()
                {
                    { MessageHeader.AggregateRootId, arId.ToBase64() },
                    { MessageHeader.AggregateRootRevision, model.CommitRevision.ToString() },
                    { MessageHeader.AggregateRootEventPosition, model.EventPosition.ToString() },
                    { MessageHeader.RecipientHandlers, string.Join(',', recipientHandlers) }
                };

                publisher.Publish(@event, headers);
            }

            return(new OkObjectResult(new ResponseResult()));
        }
コード例 #8
0
        public override AggregateRootId Convert(string value, Type objectType, IEnumerable <System.Security.Claims.Claim> claims)
        {
            if (string.IsNullOrEmpty(value.ToString()))
            {
                return(null);
            }

            string urn = value;

            if (urn.CanUrlDecode())
            {
                urn = urn.UrlDecode();
            }

            if (urn.IsBase64String())
            {
                urn = urn.Base64Decode();
            }

            var urnParsed = AggregateUrn.Parse(urn);

            return(new AggregateRootId(urnParsed.AggregateRootName, urnParsed));
        }
コード例 #9
0
        IAggregateRootId GetAggregateRootId(string mess)
        {
            var parts = mess.Split(new[] { "||" }, StringSplitOptions.RemoveEmptyEntries);

            foreach (var part in parts)
            {
                AggregateUrn urn;
                if (AggregateUrn.TryParse(part, out urn))
                {
                    return(new AggregateRootId(urn.AggregateRootName, urn));
                }
                else
                {
                    byte[] raw       = Convert.FromBase64String(part);
                    string urnString = Encoding.UTF8.GetString(raw);
                    if (AggregateUrn.TryParse(urnString, out urn))
                    {
                        return(new AggregateRootId(urn.AggregateRootName, urn));
                    }
                }
            }

            throw new ArgumentException($"Invalid aggregate root id: {mess}", nameof(mess));
        }
コード例 #10
0
        protected override async Task <JobExecutionStatus> RunJobAsync(IClusterOperations cluster, CancellationToken cancellationToken = default)
        {
            Dictionary <int, string> processedAggregates = new Dictionary <int, string>();

            string eventTypeId    = Data.SourceEventTypeId;
            bool   hasMoreRecords = true;

            while (hasMoreRecords && Data.IsCompleted == false)
            {
                string paginationToken = Data.EventTypePaging?.PaginationToken;
                LoadIndexRecordsResult indexRecordsResult = await eventToAggregateIndex.EnumerateRecordsAsync(eventTypeId, paginationToken).ConfigureAwait(false);

                IEnumerable <IndexRecord> indexRecords = indexRecordsResult.Records;
                Type          publicEventType          = typeof(IPublicEvent);
                ReplayOptions opt = new ReplayOptions()
                {
                    AggregateIds = indexRecordsResult.Records.Select(indexRecord => AggregateUrn.Parse(Convert.ToBase64String(indexRecord.AggregateRootId), Urn.Base64)),
                    ShouldSelect = commit =>
                    {
                        bool result = (from publicEvent in commit.PublicEvents
                                       let eventType = publicEvent.GetType()
                                                       where publicEventType.IsAssignableFrom(eventType)
                                                       where eventType.GetContractId().Equals(eventTypeId)
                                                       select publicEvent)
                                      .Any();

                        return(result);
                    },
                    After  = Data.After,
                    Before = Data.Before
                };
                LoadAggregateCommitsResult foundAggregateCommits = await eventStorePlayer.LoadAggregateCommitsAsync(opt).ConfigureAwait(false);

                foreach (AggregateCommit arCommit in foundAggregateCommits.Commits)
                {
                    if (cancellationToken.IsCancellationRequested)
                    {
                        logger.Info(() => $"Job has been cancelled.");
                        return(JobExecutionStatus.Running);
                    }

                    foreach (IPublicEvent publicEvent in arCommit.PublicEvents)
                    {
                        if (publicEvent.GetType().GetContractId().Equals(eventTypeId))
                        {
                            var headers = new Dictionary <string, string>()
                            {
                                { MessageHeader.RecipientBoundedContext, Data.RecipientBoundedContext },
                                { MessageHeader.RecipientHandlers, Data.RecipientHandlers }
                            };
                            publicEventPublisher.Publish(publicEvent, headers);
                        }
                    }
                }

                var progress = new ReplayPublicEvents_JobData.EventTypePagingProgress(eventTypeId, indexRecordsResult.PaginationToken, 0, 0);
                Data.MarkEventTypeProgress(progress);
                Data.Timestamp = DateTimeOffset.UtcNow;
                Data           = await cluster.PingAsync(Data, cancellationToken).ConfigureAwait(false);

                hasMoreRecords = indexRecordsResult.Records.Any();
            }

            Data.IsCompleted = true;
            Data.Timestamp   = DateTimeOffset.UtcNow;

            Data = await cluster.PingAsync(Data).ConfigureAwait(false);

            logger.Info(() => $"The job has been completed.");

            return(JobExecutionStatus.Completed);
        }