Principles
Software design is primarily concerned with managing complexity. The following principles help to manage complexity.
Separation of Concerns
Perhaps the most important principle of managing complexity is to separate concerns. At a high level, we separate microsites from microservices. Within microsites and micoservices, we use logical layers to separate concerns. Within layers, we use classes with a single responsibility each.
Simplicity
Each module of software, whether as broad as a microservice or as fine-grained as a class, should be as simple as possible, but no simpler.
A helpful engineering concept is that a complex machine which works is based on a simple machine which works. At a high level we use the existing machinery of HTTP to connect our microsites and microsites. Within microsites and micoservices, we use existing design patterns to coordinate between classes.
Flexibility
Conventions can be very helpful in managing complexity in software; however rigid adherence to a convention can increase compexity by forcing components to be more complex than they need to be, or by using the wrong technology to solve a problem.
In Kleenheat’s web architecture, we encourage flexibility in technology choices wherever a new choice would enhance simplicity or be the right technology to solve a problem.
Power of Two
To gain the benefits of conventions while avoiding the drawbacks of rigidly adhering to conventions, we often aim for the power of two: one simple convention and one more complex convention.
An example is that some microservices might expose a simple RESTful API, while other microservices might expose a more complex OData API. Another example is that some microservices might use the simple PetaPoco ORM, while other microservices might use the more complex Entity Framework.
Next section: Overview