Online / Offline Spectrum

O

When designing systems, there is no one size fits all solution.

That's because these systems need be used in different contexts and therefore need to showcase different characteristics.

The same goes for the offline characteristic of software capabilities. There is a spectrum of online / offline needs that each require a different design.

Online offline spectrum

Here are my recommendations, when it comes to architectural styles for designing systems that need to run offline:

Changing contexts

These style recommendations are very usefull when you know the exact context that a capability will be used in.

Certain capabilities however will be used in different contexts and need to adapt their behavior accordingly.

One such example in ClubManagement is booking orders in the fundraising capability.

When people book orders there are 3 possible contexts that this capability is used in

  • Always online: When people place their orders via the club website, remote validation is required to prevent them from cheating (e.g. by adjusting item prices). Therefor CQRS is the best style to use in this context.
  • Occasionally offline/Occasionally online: When the fundraising manager is booking orders on behalf of other people via her administrative app, then validation can happen on the client side. As I can trust this person, as she is working on orders for her own club and has full control of the data anyway, the design could gravitate more to the occasionally online side of the spectrum. Yet near realtime feedback of incoming orders is desired.
  • Occasionally online: When the checkin clerck is processing orders on the fundraising event itself, and a last minute order comes in, the capability needs to work offline for up to 8 hours and will only go online again after the fundraising event ended. Therefor the client side validation is a must, and so is replication as conflicts in this 8 hour time window are likely.

So now the question becomes, is it possible to mix and match these styles to accomodate for changing needs?

Connection points

In short: Yes! It is possible to combine the architectural styles when you have to.

The drawing below shows all of them together, with two sections highlighted using dotted rectangles.

These are the points where you can connect the styles together.

Connection points

Registry & cache aside

On the client an occasionally offline read side, implemented by the cache aside pattern, can be combined with an occasionally online write side, implemented by client side event sourcing which uses the cache aside as a registry.

This combination is great for contexts where you can trust the user, e.g. the management app used by the fundraising manager. By combining these patterns, the fundraising manager would get new bookings from the club website as they come in while she's online, but when her connection would drop she can still continue entering other bookings without any impact.

Note: For the checkin clerck's app, this design is also an option, but you'd have to add a way to manually refresh the data in the registry instead of trying to refresh it on every cache hit/miss. That load operation would be timing out for 8h straight, which is quite a waste of time and resources.

Aggregate Root

Combining an always online context with an occasionally offline one, can be done server side by adding both command handling and event replication capabilities to the aggregate root.

When exposing the same capabilities to different contexts, it is likely to run into conflicts. How to resolve these conflicts between the two sides depends on the nature of the capability. But usually, the side where event replication can be supported will also be the side with more trustworthiness and authority, allowing you to more often than not resolve the conflict by 'rebaseing' the replicated events on top of the event emitted by handling the command.

In the above example this means that the events emitted by the administrative apps would be appended after the events emitted by the public website, and therefor they would overrule the commands result.

Keep it simple

Note: It's not because you can combine all these patterns together that you also should.

Keep it as simple as the context(s) require!

About the author

YVES GOELEVEN

I've been a software architect for over 20 years.

My main areas of expertise are large scale distributed systems, progressive web applications, event driven architecture, domain driven design, event sourcing, messaging, and the Microsoft Azure platform.

As I've transitioned into the second half of my career, I made it my personal goal to train the next generation of software architects.

Get in touch

Want to get better at software architecture?

Sign up to my newsletter and get regular advice to improve your architecture skills.

You can unsubscribe at any time by clicking the link in the footer of your emails. I use Mailchimp as my marketing platform. By clicking subscribe, you acknowledge that your information will be transferred to Mailchimp for processing. Learn more about Mailchimp's privacy practices here.