Testing microservices is challenging. Dividing a system into components naturally creates inter-service dependencies, and each service has its own performance and fault-tolerance characteristics that need to be validated during development, the QA process, and continually in production. Join Daniel Bryant to learn about the theory, techniques and practices needed to overcome this challenge.
Learning Outcomes:
– Introduction to the challenges of testing distributed microservice systems
– Learn tactics for isolating tests within a complex microservice ecosystem
– Whistle stop tour of consumer-driven contract testing and API simulation
– Implementing fault-injection testing to validate nonfunctional requirements in development and QA
– An introduction and discussion of the need for continually validating microservice systems running in production, both through observability and practices like chaos engineering
2. tl;dr
● Testing microservices brings additional challenges
● Pay special attention to integration surfaces
● Isolate services for loosely coupled tests
● Include tests that resemble production
● Make security testing a priority
3. Who am I?
@danielbryantuk
Product Architect at Datawire
Consultant, Writer
Java Champion, Conference Tourist
@abrahammarin
Developer, Consultant, Writer
Associate of Equal Experts
Software Plumber
10. Testing Challenges with Microservices
● Cannot share a single environment: testing locally
● Full ecosystem unsuitable for local testing
● Lack of control over third-party dependencies
15. Isolating Parts: No Isolation
Third Party
https://www.continuousdeliveryconsulting.com/blog/end-to-end-testing-considered-harmful/
16. Wise words from Steve Smith
1. “The idea that testing a whole system will simultaneously
test its constituent parts is a Decomposition Fallacy.”
1. “The idea that testing a whole system will be cheaper than
testing its constituent parts is a Cheap Investment Fallacy.
https://www.continuousdeliveryconsulting.com/blog/end-to-end-testing-considered-harmful/
20. Test Doubles
Dummy objects: passed around but never actually used.
Fake objects: working implementations not suitable for production
Stubs: provide canned answers to calls made during the test
Spies: stubs that also record some information based on how they were called.
Mocks: objects pre-programmed with expectations which form a specification of the
calls they are expected to receive.
Virtualizations: emulation of services, with expectations (not suitable for production)
https://www.martinfowler.com/articles/mocksArentStubs.html
28. API Simulation Thoughts
● Useful when a dependency is “expensive” to mock
● Facilitates error handling tests when dependency failure
modes are challenging to recreate
● Simulations can be fragile and/or complicated
38. Consumer-Driven Contract Thoughts
● Useful in low-trust or low-communication organisations
○ Don’t use for blame: it’s a cue for a conversation
● Can be used to implement “TDD for the API”
● Resource intensive to create and maintain
46. Conclusion
● Testing microservices brings additional challenges
● Pay special attention to integration surfaces
● Isolate services for loosely coupled tests
● Include tests that resemble production
● Make security testing a priority
the whole is more than the sum of the parts, need to avoid silos
The quadrants hint at a number of challenges, which for microservices is even harder because… (and then bullet points)
Full ecosystem: too large, too diverse, too evolving
to avoid gaps:
expanding levels (concentric dotted lines, brittle, inefficient)
chained levels (overlapping dotted lines, requires more management)
All about trade-offsto avoid gaps:
expanding levels (concentric dotted lines, brittle, inefficient)
chained levels (overlapping dotted lines, requires more management)
the whole is more than the sum of the parts, need to avoid silos
no isolation, but closest to user experience. Necessary evil?
Checking implementation against requirements is not the same as checking intent against implementation, which means an end-to-end test will check the interactions between code pathways but not the behaviours within those pathways
Test execution time and non-determinism are directly proportional to System Under Test scope, which means an end-to-end test will be slow and prone to non-determinism
biggest fully-controlled test. Need to use test doubles for unowned components
Try to find better word for unowned
to avoid gaps:
expanding levels (concentric dotted lines, brittle, inefficient)
chained levels (overlapping dotted lines, requires more management)
“Copy” tl;dr
Extra challenges when workin with microservice
Test doubles, options
Careful with Long-running queries, different tools for isolation,e tc. (one liner)
security