UNPKG

@dolittle/sdk.aggregates

Version:

Dolittle is a decentralized, distributed, event-driven microservice platform built to harness the power of events.

154 lines 10.8 kB
"use strict"; // Copyright (c) Dolittle. All rights reserved. // Licensed under the MIT license. See LICENSE file in the project root for full license information. Object.defineProperty(exports, "__esModule", { value: true }); exports.AggregateRoot = void 0; const rudiments_1 = require("@dolittle/rudiments"); const sdk_events_1 = require("@dolittle/sdk.events"); const AggregateRootIdentifierNotSet_1 = require("./AggregateRootIdentifierNotSet"); const AppliedEvent_1 = require("./AppliedEvent"); const EventTypesNotSet_1 = require("./EventTypesNotSet"); const onDecorator_1 = require("./onDecorator"); /** * Represents the aggregate root. */ class AggregateRoot { /** * Initialises a new instance of the {@link AggregateRoot} class. * @param {EventSourceId} eventSourceId - The event source id of the aggregate root. */ constructor(eventSourceId) { this.eventSourceId = eventSourceId; this._appliedEvents = []; this._version = sdk_events_1.AggregateRootVersion.initial; this._aggregateRootType = Object.getPrototypeOf(this).constructor; } /** * Gets aggregate root id. */ get aggregateRootId() { if (!this._aggregateRootId) { throw new AggregateRootIdentifierNotSet_1.AggregateRootIdentifierNotSet(); } return this._aggregateRootId; } /** * Sets the aggregate root id - internal use. */ set aggregateRootId(value) { this._aggregateRootId = value; } /** * Sets the event types - internal use. */ set eventTypes(value) { this._eventTypes = value; } /** * Gets the version of the aggregate root. */ get version() { return this._version; } /** * Gets all applied events. */ get appliedEvents() { return this._appliedEvents; } /** * Apply an event to the aggregate root that will be committed to the event store. * @param {any} event - Event type apply. * @param {EventType} [eventType] - Optional type of event to apply. */ apply(event, eventType) { this.applyImplementation(event, eventType, false); } /** * Apply a public event to the aggregate root that will be committed to the event store. * @param {any} event - Event type apply. * @param {EventType} [eventType] - Optional type of event to apply. */ applyPublic(event, eventType) { this.applyImplementation(event, eventType, true); } /** * Re-applies the committed aggregate events to rehydrate the state of the aggregate root by calling on()-methods and incrementing the in-memory version. * @param {CommittedAggregateEvents} committedEvents - The events to re-apply. */ reApply(committedEvents) { this.throwIfEventWasAppliedToOtherEventSource(committedEvents); this.throwIfEventWasAppliedByOtherAggreateRoot(committedEvents); const hasState = (0, onDecorator_1.getOnDecoratedMethods)(this._aggregateRootType).length > 0; for (const event of committedEvents) { this.throwIfAggregateRootVersionIsOutOfOrder(event); this.nextVersion(); if (hasState) { const onMethod = this.getOnMethodFor(event, event.type); if (onMethod) { onMethod.method.call(this, event.content); } } } } /** * Move to next version. */ nextVersion() { this._version = this._version.next(); } applyImplementation(event, eventType, isPublic) { this.throwIfEventContentIsNullOrUndefined(event); this._appliedEvents.push(new AppliedEvent_1.AppliedEvent(event, eventType, isPublic)); this.nextVersion(); this.invokeOnMethod(event, eventType); } invokeOnMethod(event, eventType) { if (this._eventTypes === undefined) { throw new EventTypesNotSet_1.EventTypesNotSet(); } const hasState = (0, onDecorator_1.getOnDecoratedMethods)(this._aggregateRootType).length > 0; if (!hasState) { return; } const onMethod = this.getOnMethodFor(event, eventType); if (onMethod) { onMethod.method.call(this, event); } } throwIfEventContentIsNullOrUndefined(event) { if (!event) { throw new sdk_events_1.EventContentNeedsToBeDefined(); } } getOnMethodFor(event, eventType) { return (0, onDecorator_1.getOnDecoratedMethods)(this._aggregateRootType).find(_ => { let decoratorEventTypeId = sdk_events_1.EventTypeId.from(rudiments_1.Guid.empty); if (_.eventTypeOrId instanceof Function) { decoratorEventTypeId = this._eventTypes.getFor(_.eventTypeOrId).id; } else { decoratorEventTypeId = sdk_events_1.EventTypeId.from(_.eventTypeOrId); } const appliedEventType = this._eventTypes.resolveFrom(event, eventType); return appliedEventType.id.equals(decoratorEventTypeId); }); } throwIfAggregateRootVersionIsOutOfOrder(event) { if (event.aggregateRootVersion.value !== this.version.value) { throw new sdk_events_1.AggregateRootVersionIsOutOfOrder(event.aggregateRootVersion, this.version); } } throwIfEventWasAppliedByOtherAggreateRoot(event) { if (!event.aggregateRootId.equals(this.aggregateRootId)) { throw new sdk_events_1.EventWasAppliedByOtherAggregateRoot(event.aggregateRootId, this.aggregateRootId); } } throwIfEventWasAppliedToOtherEventSource(event) { if (!event.eventSourceId.equals(this.eventSourceId)) { throw new sdk_events_1.EventWasAppliedToOtherEventSource(event.eventSourceId, this.eventSourceId); } } } exports.AggregateRoot = AggregateRoot; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiQWdncmVnYXRlUm9vdC5qcyIsInNvdXJjZVJvb3QiOiIuLi8iLCJzb3VyY2VzIjpbIkFnZ3JlZ2F0ZVJvb3QudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IjtBQUFBLCtDQUErQztBQUMvQyxxR0FBcUc7OztBQUVyRyxtREFBMkM7QUFHM0MscURBQTRUO0FBRTVULG1GQUFnRjtBQUNoRixpREFBOEM7QUFFOUMseURBQXNEO0FBQ3RELCtDQUFzRDtBQUV0RDs7R0FFRztBQUNILE1BQWEsYUFBYTtJQU90Qjs7O09BR0c7SUFDSCxZQUFxQixhQUE0QjtRQUE1QixrQkFBYSxHQUFiLGFBQWEsQ0FBZTtRQVJ6QyxtQkFBYyxHQUFtQixFQUFFLENBQUM7UUFDcEMsYUFBUSxHQUF5QixpQ0FBb0IsQ0FBQyxPQUFPLENBQUM7UUFRbEUsSUFBSSxDQUFDLGtCQUFrQixHQUFHLE1BQU0sQ0FBQyxjQUFjLENBQUMsSUFBSSxDQUFDLENBQUMsV0FBVyxDQUFDO0lBQ3RFLENBQUM7SUFFRDs7T0FFRztJQUNILElBQUksZUFBZTtRQUNmLElBQUksQ0FBQyxJQUFJLENBQUMsZ0JBQWdCLEVBQUU7WUFDeEIsTUFBTSxJQUFJLDZEQUE2QixFQUFFLENBQUM7U0FDN0M7UUFDRCxPQUFPLElBQUksQ0FBQyxnQkFBaUIsQ0FBQztJQUNsQyxDQUFDO0lBRUQ7O09BRUc7SUFDSCxJQUFJLGVBQWUsQ0FBQyxLQUFzQjtRQUN0QyxJQUFJLENBQUMsZ0JBQWdCLEdBQUcsS0FBSyxDQUFDO0lBQ2xDLENBQUM7SUFFRDs7T0FFRztJQUNILElBQUksVUFBVSxDQUFDLEtBQWtCO1FBQzdCLElBQUksQ0FBQyxXQUFXLEdBQUcsS0FBSyxDQUFDO0lBQzdCLENBQUM7SUFFRDs7T0FFRztJQUNILElBQUksT0FBTztRQUNQLE9BQU8sSUFBSSxDQUFDLFFBQVEsQ0FBQztJQUN6QixDQUFDO0lBRUQ7O09BRUc7SUFDSCxJQUFJLGFBQWE7UUFDYixPQUFPLElBQUksQ0FBQyxjQUFjLENBQUM7SUFDL0IsQ0FB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