This blogpost is part of a larger blog post series. Get the overview of the content here.
Immutable data is unchangeable once it is written. An immutable data needs an identifier which allows to always return the same data no matter when it is requested or where it is request. Immutable data can be found everywhere in the real world. For example the information published in your local newspaper on the 18th March 2014 is unchangeable. Some data is not by definition immutable. Sometimes you can apply Versioning as a technique for creating immutable sets with unique identifiers. With versioning it is possible to retrieve a specific version of data or the latest and greatest version. The information retrieved is immutable because it represents the data available at a specific version. As soon as the data changes a new version is generated. Contracts and Schema shared and consumed by a “thing” must be immutable. For example the content of a message must never change even if it is redelivered multiple times. With those constraints in mind we can for example cache messages without running into the risk that a cache might get out of date. Immutability isn’t enough. The information contained in the contracts must be understood and therefore it must be stable. For example, a reference to President Bush made in 2003 means something different than a reference to President Bush made in 1990. You need an unambiguous interpretation across space and time. So you have to come up with values inside the message with do not change or get reassigned for other purposes. In summary we can say that distributed data must be both immutable and stable, this also applies to the schema where to data is written to.
Designing and naming contracts is a big challenge. In transition to Service Oriented Architecture you need to know the notion of time and how it differs whether you are inside a service or outside a service. Inside a “thing” the business logic deals with the latest and greatest view of the “thing”’s private data. Therefore the logic is deeply tied to the “now” of the service and its private data. Outside the service one can only observe what has happened in the past. We are dealing with the “then” outside the service. So data on the outside, living in the “then”, is stale (or eventual consistent) by definition. Which leads us to events and commands.
Commands are living in the “now”. It is a request for business functions to be performed. The sender is hoping the business function will be performed in the not-too-distant future. Because commands are living in the “now” they should be named in present tense and only used inside the “thing” boundary. Good commands are inherently asynchronous and can be answered with “Thank you for your request. Confirmation will arrive shortly.” Commands should be potentially good which means successful in the majority of cases. Events on the other hand are living in the “then”. They indicate something that has already occurred. They therefore are named in past tense. When you define your commands (inside) and events (outside) you have to stay away from DB thinking, think about business status changes!