Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: store event operators in EventBus allowing publish sync #1929

Open
wants to merge 2 commits into
base: master
Choose a base branch
from

Conversation

lucas-gregoire
Copy link

PR Checklist

Please check if your PR fulfills the following requirements:

PR Type

What kind of change does this PR introduce?

  • Bugfix
  • Feature
  • Code style update (formatting, local variables)
  • Refactoring (no functional changes, no api changes)
  • Build related changes
  • CI related changes
  • Other... Please describe:

What is the current behavior?

Issue Number: Discord discussion

What is the new behavior?

The EventBus now exposes a new property named eventOperators which is an array of event handlers functions in order to be used / subscribed somewhere else than from the EventBus.
This an easy way I found, without introducing breaking changes, to open the event bus to be able to call event handlers synchronously.
Ex:

export class SyncPublisher<EventBase extends IEvent> implements IEventPublisher<EventBase> {
  private eventOperators: EventOperator<EventBase>[] = [];

  async publish<T extends EventBase>(event: T) {
    const event$ = of(event);

    await lastValueFrom(
      merge(
        event$.pipe(map(() => undefined)),
        ...this.eventOperators.map((operator) => event$.pipe(operator)),
      ),
    );
  }

  setEventOperators<T extends EventBase>(eventOperators: EventOperator<T>[]) {
    this.eventOperators = eventOperators;
  }
}

@Module({
  imports: [
    CqrsModule.forRoot({
      eventPublisher: new SyncPublisher(),
    }),
  ],
  // [...]
})
export class AppModule implements OnModuleInit {
  constructor(private readonly eventBus: EventBus) {}

  onModuleInit() {
    (this.eventBus.publisher as SyncPublisher<IEvent>).setEventOperators(
      this.eventBus.eventOperators,
    );
  }
}

Does this PR introduce a breaking change?

  • Yes
  • No

Other information

Comment on lines +47 to +51
await eventBus.publish(event);

expect(heroFoundItemEnded).not.toHaveBeenCalled();
expect(heroKilledDragonEnded).not.toHaveBeenCalled();
expect(heroKilledDragon2Ended).not.toHaveBeenCalled();
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Awaiting asynchronous event publisher => end method not called

Comment on lines +87 to +90
await eventBus.publish(event);

expect(heroFoundItemEnded).toHaveBeenCalledTimes(1);
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Awaiting synchronous event publisher => end method called

@lucas-gregoire lucas-gregoire changed the title feat: Improve EventBus to store event operators feat: store event operators in EventBus allowing publish sync Feb 15, 2025
@lucas-gregoire lucas-gregoire force-pushed the feat/improve-event-bus-flexibility branch from 8d9a9d8 to 2a7ac7b Compare February 15, 2025 21:23
* Store event operators functions (observable unary function). This can provide a way to handle events synchronuously
@lucas-gregoire lucas-gregoire force-pushed the feat/improve-event-bus-flexibility branch from 2a7ac7b to d376cd6 Compare February 17, 2025 10:38
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

1 participant