Refactoring design based on Axon

This is a question related to practicality… as the design of few iterations is when things to be more domain oriented (as read in Eric Evans Book).

Basic any good design comes from some iterations of refactoring.

I have a major refactor design decision and questions on this with Axon apps. Unfortunately good design comes from major refactors and with persisted data in production is becoming a challenge with non traditional sql table type infrastructure with heavy serialization usage.

  1. changing of packaging names, Class names and hierarchy structures of aggregates, sagas, command apis and Events i.e. Best practice for how to handle movement of package hierarchies, spilt jars for physical componentization and evolve a better design with data persisted in production for current version.

This typically occurs when new bounded contexts appear after some design has been rolled out and refactoring is required or extraction of framework patterns also for better abstraction and better dependency design.

  1. Changing of Event name and attributes i.e. adding and removing fields in addition to changing name or package structure.

  2. For query side also, JPA should be easier as there are no namespace conflicts. One of the challenges is that we have serialized object heirarchy with JPA and changing those signatures of package hierarchies and the package name changes could be a major challenge, nothing to do with Axon, but any thoughts on best practice on how to refactor.

Was thinking through this before doing some refactoring, however am trying to qualifying any challenges with existing data persisted in Event Store and Saga Persistance along with Query DB.

Appreciate any thoughts and what others have experienced learned on these topics.

Thanks and Cheers…

Hi,

unfortunately, I don’t have the time right now to respond extensively. I’ll do that a little later this week.

The support for refactoring is the responsibility of upcasters. But to some extent, the XStreamSerializer can support you as well. You can use XStream’s aliases to configure field renames and moved packages. The more complex things can be done with upcasters.
In Axon 2, refactoring should become easier, as Axon doesn’t intrude the Event’s model anymore.

More soon…

Cheers,

Allard

Hi,

it took a little longer than expected, but I’m picking up the “regular” routines again…

In Axon 1, you can assign a list of Upcasters to the XStreamSerializer. In Axon 2, the upcaster should be assigned to the Event Store instead.
The XStreamSerializer Upcasters represent events as Dom4J documents. This allows you to easily change the document structure using Dom4j API. Axon 2 will allow you to use any representation for which converters are available.

What I generally do myself is create an alias for the main package of my application. Imagin all my Commands and Events are in com.mycompany.myapp.api.*. I would then create an alias “myapp” for that package. An Event called com.mycompany.myapp.api.customer.CustomerCreatedEvent would the be stored as <myapp.customer.CustomerCreatedEvent>…</…>. You can also create aliases for class names. You could then get, for example, …</…>. Although that requires you to create an alias for each event.

To accomodate a renamed field, for example, you should add an alias twice. The first time to the old name, and another one to the new. This ensures that old events can be read, while the new events are written using the correct new field name.
Changing “foo” to “bar” would require the following aliases:

  • addAlias(“foo”, “bar”)
  • addAlias(“bar”, “bar”)

Check out http://xstream.codehaus.org/ for more details.

Cheers,

Allard

Very helpful insight… Suggest this get into Axon reference documentation as I am sure this could be a best practice strategy for Refactoring in the spirit of domain driven design for Axon apps… Thanks and Cheers…