Hi,
I’ve read the thread on snapshotting and figured that the EventStore way of having snapshots is using an extra stream (that is, if I want to use the EventStore as my snapshot storage facility). Now, I’m trying to incorporate this guidance in AggregateSource[AS] (a little pet project that integrates with EventStore). I’ve come up with a couple of abstractions that will probably serve X% of the use cases out there but I have some holes that need filling. Hence why I turned here.
-
For one I should be able to rehydrate an aggregate’s root from a snapshot. So I added an ISnapshottable { void RestoreSnapshot(object snapshot); object TakeSnapshot(); } - one of many approaches I could have chosen - that an aggregate’s root must implement. No sweat.
-
When the time comes to load up an aggregate I resolve the snapshot stream name using a IStreamNameResolver { string Resolve(string identifier); } which is just an easy way for people to impose their own convention. Now, as I start reading the snapshot stream, it could be empty, deleted, not found, or found. I’m using the EventStoreConnection’s ReadStreamEventsBackward since I presume people will only want to read the most recent snapshot. [Q1]What do I pass in as a value for the start parameter? Int32.MaxValue or 1?
-
Assuming I get a slice of the stream back, I’ll have a snapshot (the sole event in that slice) I’ll be able to deserialize using my IResolvedEventDeserializer { object Deserialize(ResolvedEvent resolvedEvent); }. [Q2] Do people ever upgrade their snapshots like one has an upconverter for events? Intuitively, I’m inclined to say “just store a new snapshot” and not provide any support for such a thing. OTOH, if you were to deploy newer and older code side-by-side that could prove useful, but I doubt people would be using AS for that. I’d expect their integration with the EventStore to be much tighter than what I’m offering. Kind of a rhetoric question.
-
Now, I’ve gotten my snapshot and restored it into the aggregate’s root. [Q3]Where does one usually put ‘version’ information? With version I’m not talking about the version of the snapshot’s schema, I’m talking about the ‘version’ of the stream/aggregate this snapshot represents and from which point onwards events should be read. I would assume that it would go either on the payload itself or the meta data of the event. Alternatively I could provide a wrapper around the actual snapshot in the form of SnapshotInfo { Int32 Version { get; } Object Snapshot { get; } }. As it is I’m inclined to provide a SnapshotVersionSelector { Int32 Select(ResolvedEvent resolvedEvent); } which will allow a decent amount of flexibility (I may have to tune it a bit if deserialization were to happy twice, resulting in a SnapshotInfoDeserializer/-Reader/-Whatever).
I’m fully aware that this kind of integration is highly subjective. Not trying to ‘framework’ it, just trying to provide sane defaults (examples if you will) with a certain degree of pluggability (which is beyond the scope of the questions I’m asking really).
Thanks for reading,
Thanks a million for replying,
Yves.