Axon Server send all events each time same client reconnect to the application

Hello,

As a newcomer & player with Axon Server (SE edition for now) i have made a simple micro service application.
This application looks like any simple example project we can find on the net, so organized like that:

  • 1 aggregate
  • 1 creation command
  • 1 created event
  • 2 queries (find 1 & find all)
  • 1 component which handle the event & the queries. It maintains a view of the aggregate state in a simple memory Map. Very basic stuff, just listen to the created event and add it to the map if it does not exists yet.

I used docker compose to run the server and the micro service.

After starting, stopping, rebuilding the micro service, etc. several times to improve my test scenario, i observe that the micro service after starting get all the events which previously happened.
Thus, my view is now in memory so i don’t really care, but this is clearly not the behavior i was expecting by default.

Can someone explain me this behavior and how i can change it ?
Is it because my client ID is not setup in my client application file and then generated & different after each reboot ?

Thanks in advance for your help.

Hi,

According to this documentation: https://docs.axoniq.io/reference-guide/configuring-infrastructure-components/event-processing/event-processors

I have to provide a Token Store, else as in my case the InMemory one the used, it lead to my current behavior.

General question: does each service has to provide it own token store, or the token store can be a shared one, like a common database somewhere?

By adding @ProcessingGroup(“somegroupname”) on a bean containing @EventHandler, and deploying N instance of this same service, do each service update the token for this group concurrently so that none of the instance process a same event twice ?

Hi Nicolas,

are you using Spring Boot? In that case, the Spring Boot Autoconfiguration component for Axon will automatically set you up with sensible defaults based on your configuration. If, instead, you bootstrap your components using the Configurer API from Axon, consider using the DefaultConfiguration.jpaConfiguration(…) method to set all defaults to JPA based components.

Regarding the location of the TokenStore, we very heavily recommend placing the TokenStore in the same database as the one where the projections for that application are stored. That allows updates to the projections and updates to the tokens (which indicate up to where the projection has been updated) to be committed in the same transaction.

Hope this helps.
Cheers,

Allard Buijze

CTO

Hi Allard,

Thank you for your reply. Your assumption is correct, i’m using spring boot auto configuration.
Ok, i was wondering why most of tutorial looks like working (for example your official start tutorial) but fails in my case.
That’s because i did not provide proper database access components, then the Token Store cannot initialize and is setup with default configuration leading to what i observe.
I understand thank you, i will update using a database for the view as well as the token store.

I just saw that axon also provide mongodb implementation for token store, perfect, i will use it for my use case.

Many thanks for your support Allard!

Hi again,

Well, even after using real database, i still observe this full exchange when my application startup.
The Fetched token is null and the server send all events.
Surprisingly event if the event handler on my view is receiving all events, data does not looks to be persisted again as no unique constraint violation is thrown and no duplicated data is on the database.

Here are few logs when the application startup:

`

myapp-service | 15:05:17.346 INFO j.c.g.g.z.s.myappServiceApplication#logStarted : Started myappServiceApplication in 12.486 seconds (JVM running for 13.043)
myapp-service | 15:05:17.496 INFO o.a.e.TrackingEventProcessor#lambda$run$1 : Worker assigned to segment Segment[0/3] for processing
myapp-service | 15:05:17.659 INFO o.a.e.TrackingEventProcessor#run : Dispatching new tracking segment worker: TrackingSegmentWorker{processor=myapp-accounts, segment=Segment[0/3]}
myapp-service | 15:05:17.675 INFO o.a.e.TrackingEventProcessor#lambda$run$1 : Worker assigned to segment Segment[1/3] for processing
myapp-service | 15:05:17.850 INFO a.e.TrackingEventProcessor#ensureEventStreamOpened: Fetched token: null for segment: Segment[0/3]
myapp-service | 15:05:17.865 INFO o.a.a.c.event.axon.AxonServerEventStore#openStream: open stream: 0
myapp-service | 15:05:17.927 INFO o.a.e.TrackingEventProcessor#run : Using current Thread for last segment worker: TrackingSegmentWorker{processor=myapp-accounts, segment=Segment[1/3]}
myapp-service | Security framework of XStream not initialized, XStream is probably vulnerable.
myapp-service | 15:05:18.005 INFO j.c.g.g.z.s.query.AccountProjector#on : Event received: myappAccountCreatedEvent(myappAccountId=d4d267e5-c9be-461d-a149-5219def203ef, legacyId=null)
myapp-service | 15:05:18.065 INFO a.e.TrackingEventProcessor#ensureEventStreamOpened: Fetched token: null for segment: Segment[1/3]
myapp-service | 15:05:18.066 INFO o.a.a.c.event.axon.AxonServerEventStore#openStream: open stream: 0
myapp-service | 15:05:18.387 INFO j.c.g.g.z.s.query.AccountProjector#on : Event received: myappAccountCreatedEvent(myappAccountId=44c18571-e6b2-4f3f-b74d-24bc8ea1a195, legacyId=dark vador)

`

And this is the token_entry table content: (my application has @ProcessingGroup with ‘myapp-accounts’ and is configured to as in the official start tutorial)

`