A question on how to force axon to create snapshots for all my aggregates. I have created a SnapshotTriggerDefinition which creates a snapshot after 50 events. This definition is only triggered when a new event comes in. That’s when the eventHandled method gets called and starts to count the number of events. We are expecting a big load in the next weeks which will affect all our aggregates. Is it possible to create a snaphot of each aggregate prior to this load, in some sort of batch? This will speed up loading the aggregates once this big load starts.
You can create a specific command that will trigger a snapshot of an Aggregate.
One of our colleagues already answered something similar on Stackoverflow and this is why I am linking it here instead of copying the solution.
I’m trying the approach described in the SO answer you pointed out and it does create a snapshot, but also throws an NPE at some point. I reckon (but I’m not 100% sure) this happens because the aggregate is not hydrates at the moment the command is processed. For what I can see, the issue might at some point the logic picks the ID of the aggregate as null, and that ends up causing the NPE.
This is the stack trace I get (we are using axon 4.3.0.1):
AbstractUnitOfWork : Rolling back Unit Of Work.java.lang.NullPointerException: null
at java.base/java.util.concurrent.ConcurrentHashMap.get(ConcurrentHashMap.java:936)
at org.axonframework.common.lock.PessimisticLockFactory.lockFor(PessimisticLockFactory.java:128)
at org.axonframework.common.lock.PessimisticLockFactory.obtainLock(PessimisticLockFactory.java:118)
at org.axonframework.modelling.command.LockingRepository.doCreateNew(LockingRepository.java:83)
at org.axonframework.modelling.command.LockingRepository.doCreateNew(LockingRepository.java:52)
at org.axonframework.modelling.command.AbstractRepository.newInstance(AbstractRepository.java:90)
at org.axonframework.modelling.command.AggregateAnnotationCommandHandler$AggregateConstructorCommandHandler.handle(AggregateAnnotationCommandHandler.java:327)
at org.axonframework.modelling.command.AggregateAnnotationCommandHandler$AggregateConstructorCommandHandler.handle(AggregateAnnotationCommandHandler.java:316)
at org.axonframework.modelling.command.AggregateAnnotationCommandHandler.handle(AggregateAnnotationCommandHandler.java:125)
at org.axonframework.modelling.command.AggregateAnnotationCommandHandler.handle(AggregateAnnotationCommandHandler.java:44)
at org.axonframework.messaging.DefaultInterceptorChain.proceed(DefaultInterceptorChain.java:57)
at org.axonframework.messaging.interceptors.CorrelationDataInterceptor.handle(CorrelationDataInterceptor.java:65)
at org.axonframework.messaging.DefaultInterceptorChain.proceed(DefaultInterceptorChain.java:55)
But looking at what you shared, I would also like to see the snippet of your configuration and also the Aggregate itself. That would help.
As a final remark, can you test with latest AF, which is 4.5 btw? I have a hunch that this problem is not present anymore and could be something we already fixed in the past.
I spent a bit more time looking at this and it was a ‘user’ problem. I ‘cloned’ a command handler that was applied to a constructor in the same class rather than a method, so Axon was creating an empty instance, which failed to be persisted in the cache as it didn’t have an aggregate id. The snapshot was successful as it applied to a different instance of the same aggregate.