Exemple #1
0
 public SyncProjection Apply(UpdatedEvent @event, SyncProjection current)
 {
     return(current with
     {
         Value = @event.Value
     });
 }
Exemple #2
0
 public void UpdatePosition(string Projection,
                            double North, double East, double Altitude)
 {
     Position = new GPSPosition(Projection, North, East, Altitude);
     PositionUpdatedEvent?.Invoke(Position);
     UpdatedEvent?.Invoke();
 }
Exemple #3
0
        public async Task UpdateAsync(params T[] items)
        {
            Throw.IfNullOrEmpty(() => items);

            await _dataProviderWrapper.UpdateAsync(items);

            UpdatedEvent?.Invoke(items);
        }
        private void OnUpdatedEvent()
        {
            if (_groups.Any(g => !g.Updated))
            {
                return;
            }

            UpdatedEvent?.Invoke();
        }
Exemple #5
0
        protected override void Append(log4net.Core.LoggingEvent loggingEvent)
        {
            // Append the event as usual
            base.Append(loggingEvent);

            // Then alert the Updated event that an event has occurred
            Updated?.Invoke(this, loggingEvent.RenderedMessage);
            UpdatedEvent?.Invoke(this, loggingEvent);
        }
        private void OnUpdatedEvent()
        {
            if (tags.Any(t => !t.Updated))
            {
                return;
            }

            Updated = true;
            UpdatedEvent?.Invoke();
        }
Exemple #7
0
 public void Apply(UpdatedEvent e)
 {
     if (Counts.ContainsKey(e.Key))
     {
         Counts[e.Key] += e.Amount;
     }
     else
     {
         Counts.Add(e.Key, e.Amount);
     }
 }
Exemple #8
0
        /// <summary>
        /// Handle a DELETE command which specifies that an aggregate should be marked as deleted
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task <CommandResult <Guid> > Handle(DeleteCommand <T> request, CancellationToken cancellationToken)
        {
            // Validate input
            if (request.EventStreamId == Guid.Empty)
            {
                return(new CommandResult <Guid>(ResultType.BadRequest));
            }

            if (await GetSpecificAggregateRoot(request.EventStreamId) == null)
            {
                return(new CommandResult <Guid>(ResultType.NothingFound));
            }

            // Call extension point to get the action authorised for the user in question, and the specific resource
            var authResult = await this.AuthoriseDelete(request.EventStreamId);

            if (authResult.ResultType == ResultType.AccessDenied)
            {
                // TODO: Move the Access Denied audit log creation to here, from the child classes?
                return(new CommandResult <Guid>(authResult.ResultType));
            }

            // Create a domain event record for this aggregate, and this entity (This is an UPDATE for the aggregate as we're not DELETING the record physically)
            string eventData = new JObject()
            {
                new JProperty("Status", EntityStatus.Cancelled.ToString())
            }.ToString();
            DomainEventType eventType   = (DomainEventType)Enum.Parse(typeof(DomainEventType), ($"Modify{typeof(T).Name}Event"));
            DomainEvent     domainEvent = new DomainEvent(eventData, _currentUser.UserName, eventType, request.EventStreamId);

            // Save the domain event
            _dc.DomainEvents.Add(domainEvent);
            await _dc.SaveChangesAsync();

            // Publish domain event notification - this is published as a MODIFY on the aggregate as we are not physically deleting the record, rather we're changing its status.
            UpdatedEvent <T> eventNotification = new UpdatedEvent <T>(eventData, _currentUser.UserName, domainEvent.EventStreamId, domainEvent.Id);
            await _mediator.Publish(eventNotification);

            // Drop an AuditLogEvent onto the mediator, to dispatch a request to update the system audit log. Again, we're not going to wait for the outcome of this event. Just fire and forget.
            // We are going to audit this as a DELETE even though it's enacted as a modify, for clarity
            AuditLogEvent auditLogNotification = new AuditLogEvent((DomainEventType)Enum.Parse(typeof(DomainEventType), ($"Delete{typeof(T).Name}Event")), _currentUser.UserName, domainEvent.EventStreamId, domainEvent.Id);
            await _mediator.Publish(auditLogNotification);

            // Return new command result, with the PARENT's event stream id.
            return(new CommandResult <Guid>());
        }
Exemple #9
0
        /// <summary>
        /// Handle a CREATE command which specifies that a new entity should be added to a child collection on an aggregate
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task <CommandResult <Guid> > Handle(CreateChildCommand <T> request, CancellationToken cancellationToken)
        {
            // Validate input
            if (string.IsNullOrWhiteSpace(request.EventData) || request.ParentEventStreamId == Guid.Empty)
            {
                return(new CommandResult <Guid>(ResultType.BadRequest));
            }

            if (await GetSpecificAggregateRoot(request.ParentEventStreamId) == null)
            {
                return(new CommandResult <Guid>(ResultType.NothingFound));
            }

            // Call extension point to get the action authorised for the user in question, and the specific resource
            var authResult = await this.AuthoriseModify(request.EventData, request.ParentEventStreamId, request.ChildEntityType);

            if (authResult.ResultType == ResultType.AccessDenied)
            {
                // TODO: Move the Access Denied audit log creation to here, from the child classes?
                return(new CommandResult <Guid>(authResult.ResultType));
            }
            else
            {
                // Create a domain event record for this aggregate, and this new child entity (This is an UPDATE for the aggregate, recorded as a Create of the new child)
                DomainEventType eventType   = (DomainEventType)Enum.Parse(typeof(DomainEventType), string.Format("Create{0}Event", request.ChildEntityType.Name));
                DomainEvent     domainEvent = new DomainEvent(request.EventData, _currentUser.UserName, eventType, request.ParentEventStreamId);

                // Save the domain event
                _dc.DomainEvents.Add(domainEvent);
                await _dc.SaveChangesAsync();

                // Publish domain event notification - this is published as a MODIFY on the aggregate as this will direct it to the correct Aggregate's domain serivce.
                UpdatedEvent <T> eventNotification = new UpdatedEvent <T>(request.EventData, _currentUser.UserName, domainEvent.EventStreamId, domainEvent.Id);
                await _mediator.Publish(eventNotification);

                // Drop an AuditLogEvent onto the mediator, to dispatch a request to update the system audit log. Again, we're not going to wait for the outcome of this event. Just fire and forget.
                AuditLogEvent auditLogNotification = new AuditLogEvent(domainEvent.DomainEventType, _currentUser.UserName, domainEvent.EventStreamId, domainEvent.Id);
                await _mediator.Publish(auditLogNotification);

                // Return new command result, with the PARENT's event stream id.
                return(new CommandResult <Guid>(request.ParentEventStreamId));
            }
        }
Exemple #10
0
        public override void OnEvent(CqEvent <TKey, TResult> ev)
        {
            Debug.WriteLine("CqListener::OnEvent called");
            var  val = ev.getNewValue() as Position;
            TKey key = ev.getKey();

            switch (ev.getQueryOperation())
            {
            case CqOperation.OP_TYPE_REGION_CLEAR:
                RegionClearEvent.Set();
                break;

            case CqOperation.OP_TYPE_CREATE:
                CreatedEvent.Set();
                break;

            case CqOperation.OP_TYPE_UPDATE:
                UpdatedEvent.Set();
                break;

            case CqOperation.OP_TYPE_INVALIDATE:
                InvalidatedEvent.Set();
                break;

            case CqOperation.OP_TYPE_DESTROY:
                if (val == null)
                {
                    DestroyedNullEvent.Set();
                }
                else
                {
                    DestroyedNonNullEvent.Set();
                }
                break;

            default:
                ReceivedUnknownEventType = true;
                break;
            }
        }
 public override void WriteLine(string format, params object[] arg)
 {
     UpdatedEvent?.Invoke();
     base.WriteLine(format, arg);
 }
 public override void WriteLine(string format, object arg0, object arg1, object arg2)
 {
     UpdatedEvent?.Invoke();
     base.WriteLine(format, arg0, arg1, arg2);
 }
 public override void WriteLine(string value)
 {
     UpdatedEvent?.Invoke();
     base.WriteLine(value);
 }
 public override void WriteLine()
 {
     UpdatedEvent?.Invoke();
     base.WriteLine();
 }
Exemple #15
0
 public void OnUpdated()
 {
     UpdatedEvent?.Invoke();
 }
Exemple #16
0
 /// <summary>
 /// Handle the UpdatedEvent for objects of type T
 /// </summary>
 /// <param name="notification">The event to handle</param>
 /// <param name="cancellationToken">A cancellation token</param>
 public async Task Handle(UpdatedEvent <T> notification, CancellationToken cancellationToken)
 {
     await HandleNotifications(notification);
 }
Exemple #17
0
        /// <summary>
        /// Handle a PATCh command which specifies updates on a child entity of the aggregate root
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task <CommandResult <Guid> > Handle(ModifyChildCommand <T> request, CancellationToken cancellationToken)
        {
            // Validate input
            if (request.ParentEventStreamId == Guid.Empty || request.ChildEntityId < 1 || request.ChildEntityType == null || string.IsNullOrWhiteSpace(request.EventData))
            {
                return(new CommandResult <Guid>(ResultType.BadRequest));
            }

            T aggregateRoot = await GetSpecificAggregateRoot(request.ParentEventStreamId);

            // find the child collection
            var         childCollectionProperty = aggregateRoot?.GetType().GetProperties().Where(p => p.PropertyType.GenericTypeArguments.Contains(request.ChildEntityType)).First();
            IEnumerable childCollection         = (IEnumerable)childCollectionProperty?.GetMethod.Invoke(aggregateRoot, null);
            int         childCollectionCount    = childCollectionProperty == null || childCollection == null ? 0 : (int)childCollectionProperty.PropertyType.GetProperty("Count").GetValue(childCollection);

            bool childIdFound = false;

            if (childCollection != null)
            {
                foreach (dynamic child in childCollection)
                {
                    if (child.Id == request.ChildEntityId)
                    {
                        childIdFound = true;
                        break;
                    }
                }
            }

            // TODO: Return nothing found if the childentityId is not in the collection
            if (aggregateRoot == null || childCollection == null || childCollectionCount == 0 || childIdFound == false)
            {
                return(new CommandResult <Guid>(ResultType.NothingFound));
            }

            // Call extension point to get the action authorised for the user in question, and the specific resource.
            // This is a modify on a child entity, we're going to rely on the permission for modification of the parent entity for this.
            var authResult = await this.AuthoriseModify(request.EventData, request.ParentEventStreamId, request.ChildEntityType);

            if (authResult.ResultType == ResultType.AccessDenied)
            {
                // TODO: Move the Access Denied audit log creation to here, from the child classes?
                return(new CommandResult <Guid>(authResult.ResultType));
            }

            // Create a domain event record for this aggregate, and this entity (This is an UPDATE for the aggregate, since it's updating child data owned by this aggregate root)
            DomainEventType eventType   = (DomainEventType)Enum.Parse(typeof(DomainEventType), ($"Modify{request.ChildEntityType.Name}Event"));
            DomainEvent     domainEvent = new DomainEvent(request.EventData, _currentUser.UserName, eventType, request.ParentEventStreamId, request.ChildEntityId);

            // Save the domain event
            _dc.DomainEvents.Add(domainEvent);
            await _dc.SaveChangesAsync();

            // Publish domain event notification - this is published as a MODIFY on the aggregate as we are not physically deleting the record, rather we're changing its status.
            UpdatedEvent <T> eventNotification = new UpdatedEvent <T>(request.EventData, _currentUser.UserName, domainEvent.EventStreamId, domainEvent.Id);
            await _mediator.Publish(eventNotification);

            // Drop an AuditLogEvent onto the mediator, to dispatch a request to update the system audit log. Again, we're not going to wait for the outcome of this event. Just fire and forget.
            // We are going to audit this as a DELETE even though it's enacted as a modify, for clarity
            AuditLogEvent auditLogNotification = new AuditLogEvent((DomainEventType)Enum.Parse(typeof(DomainEventType), ($"Modify{request.ChildEntityType.Name}Event")), _currentUser.UserName, domainEvent.EventStreamId, domainEvent.Id);
            await _mediator.Publish(auditLogNotification);

            // Return new command result, with the PARENT's event stream id.
            return(new CommandResult <Guid>());
        }