My name is Tim Teulings. I live in Dortmund, Germany. I work as a software developer and software architect.
I’m currently implementing my backends using JavaEE. I used Glassfish for a while and switched to Widlfly/JBoss some time go.
I however recently also took a look at Spring, Spring Boot and Spring Cloud. While I like JavaEE since it always allowed me to get my tasks done in a simple way and I enjoy its good design, I have to admit that Spring is providing a much broader experience for the developer these days. The JavaEE specification process would have to speed up to hold the pace Spring currently has. So depending on the actual needs and constraints Spring may currently be the better choice for developers if you need more than what JavaEE provides. I do not think though that an application server is it itself a bad thing.
I would implement backend APIs using REST but also interacted with other system in the past using SOAP. I designed a number of well written APIs over my career.
I spent a lot of time in the past to implement rich client desktop and mobile frontends by writing sophisticated widget frameworks on top of the OS widgets or even on top of the naked OS rendering stack (In C++ on top of Win32 controls, in Oberon-2 on top of X11, bare Win32 API and Mac carbon APIs and then using C++ on top of Win32 API and X11 using Gtk theming). While doing this I thought a lot about how to design graphical user interfaces and reducing visible dirt and create a clean and simple look, resulting in easy to use interfaces. Since I’m not a designer I concentrated on the more technical aspects of good user interfaces.
Model driven development, custom programming languages, DSLs and code generation
The best code written is the code you do not need to write at all because some infrastructure already offers it for you. This infrastructure can either be some 3rd party (open source) software, a library or a framework.
The second best code written is the code that is created or extracted from some higher level source of abstraction. Since abstraction is the key of programming, developers should try to find a as high as possible abstraction level while describe their problem and and later implementing the resulting solution. May it be a new (simple) scripting language, a declarative domain specific language together with one or more code generators, a interpretation of a model - I have done them all and it was really fun. Depending on the needs and constraints I would either choose Coco/R, ANTLR or Xtext.
Developing frameworks makes even more fun than using them. Since there is not one frameworks for everything and frameworks tend to be better the more they are especially designed for a small, well defined problem area (I call it the Heisenberg principle of Software Design - a framework cannot offer a big productivity boost and on the same time be good for every purpose), there will always be a need for developing one more new framework or at least extending an existing one.
No software is dead if the code still lives, no software too old to not still do its purpose if it is well maintained. Writing new software is fun, but maintaining, refactoring and improving new software can also be fun (and yes, there are people out there that think different, I know). There are a number of technics and approaches one can apply and I know some of them. I already deleted more code in long maintained projects than some developers wrote over years.
Using DDD is one of the keys to design and maintain larger systems, by giving you technics to split software into smaller parts. It is also the key to define internal and external APIs for such systems. Key statements are:
- Bring domain and technical experts together
- Concentrate on the domain
- Find the “right” model of the domain, depending on domain, technical (development and operation) and organisatorial requirements and restrictions.
I experience DDD as very helful but - in all its details - also as difficult to master in its completeness.
Microservices try to solve performance problem of big monolithic projects on the organisatorial and technical level by splitting functionality into smaller, mainly independend parts that comunicate using small but well defined interfaces. An agile development process and rather independend teams are two other contrains that are required for sucessful microservice projets.
To find the “best” way to split, DDD is helpful, since it helps to find the application sub domains that are good candidates for microservices.
Developing a microservices-based system involves working with the effects of network, unreliability and eventual consistency. But it not only result in new concrete technical challenges but there are also more higher-level architectural challenges, too. While teams should be able to act independent of each other and thus also should have some technical and organisatorical freedom, the system in whole still must have strong restrictions regarding the behaviour of itself and each component. Only if all parts fullfull these strong high-level requirements, the system will work.
CQRS (with or without event sourcing) is an interesting design pattern that leads to a very clean application-internal software design. It also enforces thinking about eventual consistency very early in the software process explicitely - which is good, since in most modern systems - especially when using microservices - you have to care about the effects of eventual consistency. While it is a useful pattern for high-performance requirements in can be used outside of this, too. It implementation is in principle surprisingly simple, through tricky in details.
It can be useful within a microservice architecture. But since - especially if used together with event sourcing - it has some long term side effects that are important to understand, advantages and disadvantages should be weighted well.