A microservices approach to software development results in small, reusable components that teams can use to assemble...
software. Microservices enable code repurposing (to be adaptive), which allows teams to rebuild web applications for iOS or Android or anything else quickly and cheaply.
But there's a different aspect of microservices worth exploring -- how they can be testable, lead to less regressions in production and enable continuous delivery. A smart microservices approach can lead to higher code quality for free. Here's why the approach works so well and also how to get there.
Contrasting sample applications
The web applications of the previous decade connected to a database, executed a query to get the information that should appear on the page and printed the page. Some applications combined all the pages into a single compiled file. Complex applications had spillover, where a change in one area of the code could break something somewhere else in the application, which required retesting everything between releases.
These inner services provide plain text lists – such as books, employees and posts. Sprinkle on a few services to get a book's description, price and image, and services for functions like login, search and tag, and suddenly building new features out of services is more like sewing a patchwork quilt and less like hand knitting.
This approach can lead to testing microservices and regression testing.
Advantages for regression testing
Imagine a login function that needs a wording change on error. You don't want a hacker to realize they have the correct account, so you make the invalid password and the invalid user ID message match. Both of these could probably be changed, recompiled and shipped.
If the service is truly isolated, you test the service, put the service in staging, test again and ship the code to production. If it is not, then the code requires a full compile. Full compiles and cutover are generally expensive. Teams are more likely to make several changes at a time, which introduces spillover, leading to regression and testable activity.
Truly isolated components greatly reduce, if not eliminate, spillover.
Consider our e-commerce example again. When "new for you" fails, it simply takes up zero space. The outer shell adjusts and prints the rest of the elements. While this won't work for login, search or other core services, it does mean that pages that consist of multiple services can suffer outages with less impact.
A pattern for testing microservices
In Alistair Cockburn's hexagonal architecture, services are the line that extends from the application to the database. This makes it possible to do two kinds of tests.
First, isolate the service, send it various types of data and compare the expected results to the actual results. Ideally, record the interactions to allow automatic checking. When that step is complete, it is possible to record those interactions and place them in a mock, or stub service. Then the entire application can be exercised quickly, standing up against the mock. The advantage here is that teams that change the service and see the checks passing can deploy the service without retesting the entire application.
If the service continues to provide results that are acceptable to the application, then new versions can be swapped out on demand. These sorts of cutovers take tenths of a second, not seconds or minutes. They affect the user less while enabling faster releases with less defects escaping, and less impact when they do.
Moving toward microservices
The challenge with moving to microservices is typically "where to start?" It is tempting to propose a complete website redesign or to create a "microservices" team or department. Doing a reboot, however, means the existing website still needs to be maintained. If the website is ever finished, it will likely either be based on an out-of-date specification, be over-budget due to changes or both. The change also creates two levels of staff -- the new programmers and the maintainers -- and implies an adversarial relationship between the two. If the new programmers ever finish, the future of the maintainers is uncertain.
You can think of microservices as little slices of a business process. A microservice at an insurance company, for example, might tell if a member has coverage of a certain type on a certain date. Another might return a list of claims for a given member or group over a date range. Those sorts of lookups already exist, and could be copied, pasted and reinvented over and over again in reports, applications, on the website in claim lookup and perhaps in the data warehouse.
To get started, identify a logical service and an owner. This service should be the one most likely to be reused. For claims, that might be the electronic data interchange team or a reporting team. Start with a guide to services at the company, have the team create the service and add it to a public repository -- a sort of phone book for services.
Over time, other teams can adjust their code to use the service.
In the final analysis
While the examples started with a website, microservices can really be used to capture any business process. They reduce regression testing because they are isolated, which means they make just the service testable, not the entire end-to-end system. Testing microservices is also easier to due to the input-expected response nature of the services. Companies that move to a microservices approach will find they are identifying and eliminating redundant code -- code that is just different enough that one version must have some sort of error.
It is a long journey, but testing microservices has the potential to directly improve software quality while reducing testing time. It is a testable potential worth investigating.
At the intersection of containers and microservices is DevOps
Testing microservices can be a bit easier if you sign on to SOA
Are you an expert on SOA and microservices? Find out.