SlideShare a Scribd company logo
Your tests are trying
to tell you something
by Victor Rentea at
9 design hints you were missing
Read the article:
https://victorrentea.ro/blog/design-insights-from-unit-testing/
Get the code:
https://github.com/victorrentea/unit-testing.git Branch: 9hints_talk
victorrentea.ro
Hi, I'm Victor Rentea
Java Champion – drinking since 2006
Trainer – 3000+ devs in 80+ companies
Speaker – Conferences & Meetups
Hibernate
Spring Advanced FP
Java Performance Secure Coding
Reactive
Architecture Clean Code Unit Testing
pro
Hibernate
Spring Advanced FP
Architecture Clean Code Unit Testing
Masterclass
Company
Training
Video
Lessons
@victorrentea
VictorRentea.ro
victorrentea@gmail.com
Java Performance Secure Coding
Reactive
victorrentea.ro/community
Join My
Community
YouTube
Channel
youtube.com/user/vrentea
335 © VictorRentea.ro
a training by
&
(referring to an old Romanian saying)
- NO COMMENT -
336 © VictorRentea.ro
a training by
▪Better Signatures ⌨= code
▪Immutable Objects ⌨
▪CQS Principle ⌨
▪Functional Core / Imperative Shell ⌨
▪Separation by Layers of Abstraction ⌨
▪Decouple Unrelated Complexity ⌨
▪Role-based Design
▪Onion Architecture
▪Breakdown Data Objects ⌨
Design Improvements hinted by Unit Tests
337 © VictorRentea.ro
a training by
Are you agile?
"Emergent Architecture"
Ever heard of the
338 © VictorRentea.ro
a training by
Are you agile?
Tests give you hints
on how to break
and design complex logic
"Emergent Architecture"
that never emerges 
Under-design is the default today?
339 © VictorRentea.ro
a training by
Do you write Tests
BEFORE the implementation?
Writing #responsible Unit Tests will 🚀 YOUR design skills
If you would, you'd get
✔ more real coverage => courage
✔ more early design feedback
The point of this talk
→ Mocks
340 © VictorRentea.ro
a training by
Mocks make our tests...
Repeatable
isolated from external systems
Fast ✔
DB, external APIs
Reasonably Complex ✔
When facing high cyclomatic complexity ➔
Alternatives:
in-memory DB (H2)
Testcontainers
WireMock
341 © VictorRentea.ro
a training by
Logic
to test
Cyclomatic Complexity
= number of independent paths through code
Test
Test
Test
Test
Test
Test
Test
CC=5 CC=6
f(a) g(b)
calls
CC=30
Too Many
To cover all branches
Too Heavy
in setup and input data (a and b)
End-to-end tests grow...
342 © VictorRentea.ro
a training by
⛔
If there's not much complexity,
avoid mocks
A B
Instead,
test clusters of objects
Internal refactoring
won't break tests 👍
343 © VictorRentea.ro
a training by
(The rest of the talk assumes we have serious complexity)
Unit Testing intensifies design
around complex logic
344 © VictorRentea.ro
a training by
345 © VictorRentea.ro
a training by
Precise Signatures
Methods taking less data as arguments are easier to understand; ✔
and less coupled
method(heavyObject)
HeavyObject having dozens of fields
method(part1, part2)
only takes necessary parts of HeavyObject
Tests will get simpler
new HeavyObject(..)
346 © VictorRentea.ro
a training by
Immutable Objects ✔
eg. Mutating a parameter often causes awkward bugs.
method(obj) {
obj.setX(..);
}
method(..) {
return x;
}
when(b.method(..)).thenReturn("stub");
doAnswer(invocation -> .. obj.setX("stub"))
.when(b).method(any());
Mocking such a method is painful:
347 © VictorRentea.ro
a training by
do side-effects
return void sendEmail(Email):void
Command-Query Separation
setActive(true):void
return results
search(criteria):List
computePrice(flight):int
Bertrand Meyer, in 1994:
Pure Functions
348 © VictorRentea.ro
a training by
No side effects
(doesn't change anything)
No INSERTs, POSTs, queues, files, NO Fields changed,…
𝑒𝑔: 𝑀𝑎𝑡ℎ𝑒𝑚𝑎𝑡𝑖𝑐𝑎𝑙 𝐹𝑢𝑛𝑐𝑡𝑖𝑜𝑛𝑠: 𝑓 𝑥, 𝑦 = 𝑥2
+ 𝑦
+
Referential Transparent
(same inputs produce the same output)
No current time, random, GET, SELECT…
Pure Functions
349 © VictorRentea.ro
a training by
Command-Query Separation Principle
A method should be either
a query (pure function, returning data), or
a command (side-effecting, returning void)
If you need to both stub (when...) and verify the same method,
you are breaking CQS:
Exception: external calls should happen ONCE
eg. REST/WSDL calls that are critical, cost money, or take time
when(b.query(..)).thenReturn(X);
prod.call();
verify(b).command(Y);
when(b.god(..)).thenReturn(X);
prod.call();
verify(b).god(Y);
Apply inside core logic
https://martinfowler.com/articles/mocksArentStubs.html
350 © VictorRentea.ro
a training by
Functional Core / Imperative Shell Segregation
The heavier some logic is, the less dependencies it should have.
Keep complex logic in pure functions. ✔
Complex logic requires many tests.
Shrink these tests by limiting mocks.
=> loose coupling
when.thenReturn(..);
when.thenReturn(..);
when.thenReturn(x);
when.thenReturn(y);
prod.complex();
verify(..).f(z);
verify(..).g();
verify(..).h();
x7=😖
when.thenReturn(..); // ideally 0 mocks
z = prod.complex(x, y);
assert..(z...);
351 © VictorRentea.ro
a training by
Dependencies
Heavy complexity
Side-effects
FUNCTIONAL CORE
PURE
FUNCTION
352 © VictorRentea.ro
a training by
Design the Most Complex Parts of Logic
as Pure Functions 💘
Easier to Understand Easier to Test
353 © VictorRentea.ro
a training by
Separation by Layers of Abstraction
You have two complex functions in the same class, f() calling g()
Move g() in a separate class ✔
You test g() separately.
When testing f(), you don't want it to call g(), as g was tested
Using partial mocks (@Spy) leads to horrid tests. Solution:
class Big {
f() {
//complex
g();
}
g() {
//complex
}
}
class HighLevel {
LowLevel low;
f() {
//complex
low.g();
}
}
class LowLevel {
g() {
//complex
}
}
354 © VictorRentea.ro
a training by
▪Better Signatures
▪Immutable Objects
▪CQS Principle
▪Functional Core / Imperative Shell
▪Separation by Layers of Abstraction
▪Decouple Unrelated Complexity
▪Role-based Design
▪Onion Architecture
▪Breakdown Data Objects
Design Improvements hinted by Unit Tests
355 © VictorRentea.ro
a training by
Fixture Creep
2 complex functions in the same class, use different sets of dependencies.
Break unrelated complexity for clarity and loose coupling. ✔
// prod code
class Wide {
A a;
B b;
complex1() {
//uses a
}
complex2() {
//uses b
}
}
class WideTest {
@Mock A a;
@Mock B b;
@InjectMocks Wide wide;
@BeforeEach
init() {//shared fixture
when(a..).then
when(b..).then
}
// 5 tests for complex1
// 4 tests for complex2
}
class Complex1Test {
@Mock A a;
@Mock B b;
}
class Complex2Test {
@Mock B b;
@Mock C c;
}
Testing both in the same Test class leads to a
bloated fixture ("Before").
Hard to trace later what's used by one test.
Break the test class.
Also: Hierarchical Tests.
356 © VictorRentea.ro
a training by
Mock Roles, not Objects
Bad Habit: You finish the implementation, then you write tests.
You [blindly] @Mock all dependencies.
Two years later, your tests are fragile and slow you down.
Before mocking a dependency, clarify its role. ✔
And test earlier.
http://jmock.org/oopsla2004.pdf
357 © VictorRentea.ro
a training by
Problem: You allow external APIs, DTOs, and ugly frameworks
to enter freely in your core logic.
Testing your core logic now requires creating foreign objects,
or mocking an awkward library.
Onion Architecture
Pull core logic in an Agnostic Domain ✔
So most tests talk in terms of your internal Domain Model ✔
https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html
application
Value Object
Entity
id
Domain
Service
Domain
Service
(agnostic)
domain
DTO
External
API
DTO
UI,
Client
External
Systems
Façade
Controller
IRepo
Clean Pragmatic Architecture
at Devoxx Ukraine 2021
Curious for more?
↓
IAdapter
Adapter
⛔
⛔
359 © VictorRentea.ro
a training by
Creepy Object Mother
You use large data structures in your core logic.
If the structures enforce their internal consistency,
(it's not an anemic model only having getters and setters)
then creating test data instances becomes cumbersome,
(unrelated fields to set)
so you share a global "TestData" class that builds correct instances.
TestData gets bloated and couples your tests together.
Break TestData🪓 in several classes
Break data structures🪓 in separate Bounded Contexts?
ie packages>modular monolith>microservices🤞
https://martinfowler.com/bliki/ObjectMother.html (2006)
360 © VictorRentea.ro
a training by
362 © VictorRentea.ro
a training by
▪More Calls from Tests > Better Signatures, Better Skills
▪Immutable Objects 🤘 (rock)
▪when.then xor verify > Command-Query Separation
▪More Tests ➔ ↓Mocks > Functional Core / Imperative Shell
▪Partial Mocks > Separation by Layers of Abstraction
▪Bloated Fixture > Break Test > Decouple Unrelated Complexity
▪Mock Roles not Objects > Role-based Design
▪Keep most tests on Domain > Onion Architecture
▪Creepy Object Mother > Break Data Objects
> 2 Bounded Contexts?
Recap
363 © VictorRentea.ro
a training by

More Related Content

What's hot

Clean Pragmatic Architecture - Avoiding a Monolith
Clean Pragmatic Architecture - Avoiding a MonolithClean Pragmatic Architecture - Avoiding a Monolith
Clean Pragmatic Architecture - Avoiding a MonolithVictor Rentea
 
Clean architecture
Clean architectureClean architecture
Clean architectureLieven Doclo
 
clean code book summary - uncle bob - English version
clean code book summary - uncle bob - English versionclean code book summary - uncle bob - English version
clean code book summary - uncle bob - English versionsaber tabatabaee
 
A testing strategy for hexagonal applications
A testing strategy for hexagonal applicationsA testing strategy for hexagonal applications
A testing strategy for hexagonal applicationsMatthias Noback
 
Test-Driven Design Insights@DevoxxBE 2023.pptx
Test-Driven Design Insights@DevoxxBE 2023.pptxTest-Driven Design Insights@DevoxxBE 2023.pptx
Test-Driven Design Insights@DevoxxBE 2023.pptxVictor Rentea
 
Integration testing with spring @snow one
Integration testing with spring @snow oneIntegration testing with spring @snow one
Integration testing with spring @snow oneVictor Rentea
 
React JS - Parte 1
React JS - Parte 1React JS - Parte 1
React JS - Parte 1Bruno Catão
 
The Art of Clean code
The Art of Clean codeThe Art of Clean code
The Art of Clean codeVictor Rentea
 
Vertical Slicing Architectures
Vertical Slicing ArchitecturesVertical Slicing Architectures
Vertical Slicing ArchitecturesVictor Rentea
 
Writing Clean Code (Recommendations by Robert Martin)
Writing Clean Code (Recommendations by Robert Martin)Writing Clean Code (Recommendations by Robert Martin)
Writing Clean Code (Recommendations by Robert Martin)Shirish Bari
 
Clean Code I - Best Practices
Clean Code I - Best PracticesClean Code I - Best Practices
Clean Code I - Best PracticesTheo Jungeblut
 
Unit Testing like a Pro - The Circle of Purity
Unit Testing like a Pro - The Circle of PurityUnit Testing like a Pro - The Circle of Purity
Unit Testing like a Pro - The Circle of PurityVictor Rentea
 
Social Engineering the Windows Kernel by James Forshaw
Social Engineering the Windows Kernel by James ForshawSocial Engineering the Windows Kernel by James Forshaw
Social Engineering the Windows Kernel by James ForshawShakacon
 
Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...
Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...
Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...Zohirul Alam Tiemoon
 

What's hot (20)

Clean Pragmatic Architecture - Avoiding a Monolith
Clean Pragmatic Architecture - Avoiding a MonolithClean Pragmatic Architecture - Avoiding a Monolith
Clean Pragmatic Architecture - Avoiding a Monolith
 
Clean architecture
Clean architectureClean architecture
Clean architecture
 
clean code book summary - uncle bob - English version
clean code book summary - uncle bob - English versionclean code book summary - uncle bob - English version
clean code book summary - uncle bob - English version
 
A testing strategy for hexagonal applications
A testing strategy for hexagonal applicationsA testing strategy for hexagonal applications
A testing strategy for hexagonal applications
 
Test-Driven Design Insights@DevoxxBE 2023.pptx
Test-Driven Design Insights@DevoxxBE 2023.pptxTest-Driven Design Insights@DevoxxBE 2023.pptx
Test-Driven Design Insights@DevoxxBE 2023.pptx
 
Integration testing with spring @snow one
Integration testing with spring @snow oneIntegration testing with spring @snow one
Integration testing with spring @snow one
 
XXE
XXEXXE
XXE
 
React JS - Parte 1
React JS - Parte 1React JS - Parte 1
React JS - Parte 1
 
Clean Code
Clean CodeClean Code
Clean Code
 
Clean code
Clean codeClean code
Clean code
 
The Art of Clean code
The Art of Clean codeThe Art of Clean code
The Art of Clean code
 
Vertical Slicing Architectures
Vertical Slicing ArchitecturesVertical Slicing Architectures
Vertical Slicing Architectures
 
Writing Clean Code (Recommendations by Robert Martin)
Writing Clean Code (Recommendations by Robert Martin)Writing Clean Code (Recommendations by Robert Martin)
Writing Clean Code (Recommendations by Robert Martin)
 
Clean Code I - Best Practices
Clean Code I - Best PracticesClean Code I - Best Practices
Clean Code I - Best Practices
 
Subdomain Takeover
Subdomain TakeoverSubdomain Takeover
Subdomain Takeover
 
Clean code
Clean codeClean code
Clean code
 
Unit Testing like a Pro - The Circle of Purity
Unit Testing like a Pro - The Circle of PurityUnit Testing like a Pro - The Circle of Purity
Unit Testing like a Pro - The Circle of Purity
 
Social Engineering the Windows Kernel by James Forshaw
Social Engineering the Windows Kernel by James ForshawSocial Engineering the Windows Kernel by James Forshaw
Social Engineering the Windows Kernel by James Forshaw
 
Clean code
Clean code Clean code
Clean code
 
Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...
Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...
Overview on TDD (Test Driven Development) & ATDD (Acceptance Test Driven Deve...
 

Similar to Unit testing - 9 design hints

Don't Be Mocked by your Mocks - Best Practices using Mocks
Don't Be Mocked by your Mocks - Best Practices using MocksDon't Be Mocked by your Mocks - Best Practices using Mocks
Don't Be Mocked by your Mocks - Best Practices using MocksVictor Rentea
 
Pure functions and immutable objects @dev nexus 2021
Pure functions and immutable objects @dev nexus 2021Pure functions and immutable objects @dev nexus 2021
Pure functions and immutable objects @dev nexus 2021Victor Rentea
 
The Proxy Fairy and the Magic of Spring @JAX Mainz 2021
The Proxy Fairy and the Magic of Spring @JAX Mainz 2021The Proxy Fairy and the Magic of Spring @JAX Mainz 2021
The Proxy Fairy and the Magic of Spring @JAX Mainz 2021Victor Rentea
 
Testing Microservices @DevoxxBE 23.pdf
Testing Microservices @DevoxxBE 23.pdfTesting Microservices @DevoxxBE 23.pdf
Testing Microservices @DevoxxBE 23.pdfVictor Rentea
 
Pure Functions and Immutable Objects
Pure Functions and Immutable ObjectsPure Functions and Immutable Objects
Pure Functions and Immutable ObjectsVictor Rentea
 
The Proxy Fairy, and The Magic of Spring Framework
The Proxy Fairy, and The Magic of Spring FrameworkThe Proxy Fairy, and The Magic of Spring Framework
The Proxy Fairy, and The Magic of Spring FrameworkVictor Rentea
 
How and what to unit test
How and what to unit testHow and what to unit test
How and what to unit testEugenio Lentini
 
PHP Barcelona 2010 - Architecture and testability
PHP Barcelona 2010 - Architecture and testabilityPHP Barcelona 2010 - Architecture and testability
PHP Barcelona 2010 - Architecture and testabilityGiorgio Sironi
 
Neal Ford Emergent Design And Evolutionary Architecture
Neal Ford Emergent Design And Evolutionary ArchitectureNeal Ford Emergent Design And Evolutionary Architecture
Neal Ford Emergent Design And Evolutionary ArchitectureThoughtworks
 
Integration testing with spring @JAX Mainz
Integration testing with spring @JAX MainzIntegration testing with spring @JAX Mainz
Integration testing with spring @JAX MainzVictor Rentea
 
Python mocking intro
Python mocking introPython mocking intro
Python mocking introHans Jones
 
Troubleshooting tips from docker support engineers
Troubleshooting tips from docker support engineersTroubleshooting tips from docker support engineers
Troubleshooting tips from docker support engineersDocker, Inc.
 
Javascript unit testing, yes we can e big
Javascript unit testing, yes we can   e bigJavascript unit testing, yes we can   e big
Javascript unit testing, yes we can e bigAndy Peterson
 
Java Performance Tuning
Java Performance TuningJava Performance Tuning
Java Performance TuningMinh Hoang
 
Evolving a Clean, Pragmatic Architecture - A Craftsman's Guide
Evolving a Clean, Pragmatic Architecture - A Craftsman's GuideEvolving a Clean, Pragmatic Architecture - A Craftsman's Guide
Evolving a Clean, Pragmatic Architecture - A Craftsman's GuideVictor Rentea
 
Testing the frontend
Testing the frontendTesting the frontend
Testing the frontendHeiko Hardt
 
Linq 1224887336792847 9
Linq 1224887336792847 9Linq 1224887336792847 9
Linq 1224887336792847 9google
 

Similar to Unit testing - 9 design hints (20)

Don't Be Mocked by your Mocks - Best Practices using Mocks
Don't Be Mocked by your Mocks - Best Practices using MocksDon't Be Mocked by your Mocks - Best Practices using Mocks
Don't Be Mocked by your Mocks - Best Practices using Mocks
 
Pure functions and immutable objects @dev nexus 2021
Pure functions and immutable objects @dev nexus 2021Pure functions and immutable objects @dev nexus 2021
Pure functions and immutable objects @dev nexus 2021
 
The Proxy Fairy and the Magic of Spring @JAX Mainz 2021
The Proxy Fairy and the Magic of Spring @JAX Mainz 2021The Proxy Fairy and the Magic of Spring @JAX Mainz 2021
The Proxy Fairy and the Magic of Spring @JAX Mainz 2021
 
Testing Microservices @DevoxxBE 23.pdf
Testing Microservices @DevoxxBE 23.pdfTesting Microservices @DevoxxBE 23.pdf
Testing Microservices @DevoxxBE 23.pdf
 
Pure Functions and Immutable Objects
Pure Functions and Immutable ObjectsPure Functions and Immutable Objects
Pure Functions and Immutable Objects
 
The Proxy Fairy, and The Magic of Spring Framework
The Proxy Fairy, and The Magic of Spring FrameworkThe Proxy Fairy, and The Magic of Spring Framework
The Proxy Fairy, and The Magic of Spring Framework
 
How and what to unit test
How and what to unit testHow and what to unit test
How and what to unit test
 
PHP Barcelona 2010 - Architecture and testability
PHP Barcelona 2010 - Architecture and testabilityPHP Barcelona 2010 - Architecture and testability
PHP Barcelona 2010 - Architecture and testability
 
Neal Ford Emergent Design And Evolutionary Architecture
Neal Ford Emergent Design And Evolutionary ArchitectureNeal Ford Emergent Design And Evolutionary Architecture
Neal Ford Emergent Design And Evolutionary Architecture
 
Integration testing with spring @JAX Mainz
Integration testing with spring @JAX MainzIntegration testing with spring @JAX Mainz
Integration testing with spring @JAX Mainz
 
Python mocking intro
Python mocking introPython mocking intro
Python mocking intro
 
Troubleshooting tips from docker support engineers
Troubleshooting tips from docker support engineersTroubleshooting tips from docker support engineers
Troubleshooting tips from docker support engineers
 
Modern Python Testing
Modern Python TestingModern Python Testing
Modern Python Testing
 
Javascript unit testing, yes we can e big
Javascript unit testing, yes we can   e bigJavascript unit testing, yes we can   e big
Javascript unit testing, yes we can e big
 
Java Performance Tuning
Java Performance TuningJava Performance Tuning
Java Performance Tuning
 
Evolving a Clean, Pragmatic Architecture - A Craftsman's Guide
Evolving a Clean, Pragmatic Architecture - A Craftsman's GuideEvolving a Clean, Pragmatic Architecture - A Craftsman's Guide
Evolving a Clean, Pragmatic Architecture - A Craftsman's Guide
 
Testing the frontend
Testing the frontendTesting the frontend
Testing the frontend
 
Spock
SpockSpock
Spock
 
Linq 1224887336792847 9
Linq 1224887336792847 9Linq 1224887336792847 9
Linq 1224887336792847 9
 
Java Performance Tuning
Java Performance TuningJava Performance Tuning
Java Performance Tuning
 

More from Victor Rentea

Finding Java's Hidden Performance Traps @ DevoxxUK 2024
Finding Java's Hidden Performance Traps @ DevoxxUK 2024Finding Java's Hidden Performance Traps @ DevoxxUK 2024
Finding Java's Hidden Performance Traps @ DevoxxUK 2024Victor Rentea
 
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024Victor Rentea
 
Microservice Resilience Patterns @VoxxedCern'24
Microservice Resilience Patterns @VoxxedCern'24Microservice Resilience Patterns @VoxxedCern'24
Microservice Resilience Patterns @VoxxedCern'24Victor Rentea
 
Distributed Consistency.pdf
Distributed Consistency.pdfDistributed Consistency.pdf
Distributed Consistency.pdfVictor Rentea
 
Clean Code @Voxxed Days Cluj 2023 - opening Keynote
Clean Code @Voxxed Days Cluj 2023 - opening KeynoteClean Code @Voxxed Days Cluj 2023 - opening Keynote
Clean Code @Voxxed Days Cluj 2023 - opening KeynoteVictor Rentea
 
From Web to Flux @DevoxxBE 2023.pptx
From Web to Flux @DevoxxBE 2023.pptxFrom Web to Flux @DevoxxBE 2023.pptx
From Web to Flux @DevoxxBE 2023.pptxVictor Rentea
 
Profiling your Java Application
Profiling your Java ApplicationProfiling your Java Application
Profiling your Java ApplicationVictor Rentea
 
Software Craftsmanship @Code Camp Festival 2022.pdf
Software Craftsmanship @Code Camp Festival 2022.pdfSoftware Craftsmanship @Code Camp Festival 2022.pdf
Software Craftsmanship @Code Camp Festival 2022.pdfVictor Rentea
 
Refactoring blockers and code smells @jNation 2021
Refactoring   blockers and code smells @jNation 2021Refactoring   blockers and code smells @jNation 2021
Refactoring blockers and code smells @jNation 2021Victor Rentea
 
Hibernate and Spring - Unleash the Magic
Hibernate and Spring - Unleash the MagicHibernate and Spring - Unleash the Magic
Hibernate and Spring - Unleash the MagicVictor Rentea
 
Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...
Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...
Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...Victor Rentea
 
Definitive Guide to Working With Exceptions in Java
Definitive Guide to Working With Exceptions in JavaDefinitive Guide to Working With Exceptions in Java
Definitive Guide to Working With Exceptions in JavaVictor Rentea
 
Extreme Professionalism - Software Craftsmanship
Extreme Professionalism - Software CraftsmanshipExtreme Professionalism - Software Craftsmanship
Extreme Professionalism - Software CraftsmanshipVictor Rentea
 
Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...
Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...
Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...Victor Rentea
 

More from Victor Rentea (16)

Finding Java's Hidden Performance Traps @ DevoxxUK 2024
Finding Java's Hidden Performance Traps @ DevoxxUK 2024Finding Java's Hidden Performance Traps @ DevoxxUK 2024
Finding Java's Hidden Performance Traps @ DevoxxUK 2024
 
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
Modular Monolith - a Practical Alternative to Microservices @ Devoxx UK 2024
 
Microservice Resilience Patterns @VoxxedCern'24
Microservice Resilience Patterns @VoxxedCern'24Microservice Resilience Patterns @VoxxedCern'24
Microservice Resilience Patterns @VoxxedCern'24
 
Distributed Consistency.pdf
Distributed Consistency.pdfDistributed Consistency.pdf
Distributed Consistency.pdf
 
Clean Code @Voxxed Days Cluj 2023 - opening Keynote
Clean Code @Voxxed Days Cluj 2023 - opening KeynoteClean Code @Voxxed Days Cluj 2023 - opening Keynote
Clean Code @Voxxed Days Cluj 2023 - opening Keynote
 
From Web to Flux @DevoxxBE 2023.pptx
From Web to Flux @DevoxxBE 2023.pptxFrom Web to Flux @DevoxxBE 2023.pptx
From Web to Flux @DevoxxBE 2023.pptx
 
Profiling your Java Application
Profiling your Java ApplicationProfiling your Java Application
Profiling your Java Application
 
OAuth in the Wild
OAuth in the WildOAuth in the Wild
OAuth in the Wild
 
Software Craftsmanship @Code Camp Festival 2022.pdf
Software Craftsmanship @Code Camp Festival 2022.pdfSoftware Craftsmanship @Code Camp Festival 2022.pdf
Software Craftsmanship @Code Camp Festival 2022.pdf
 
Refactoring blockers and code smells @jNation 2021
Refactoring   blockers and code smells @jNation 2021Refactoring   blockers and code smells @jNation 2021
Refactoring blockers and code smells @jNation 2021
 
Hibernate and Spring - Unleash the Magic
Hibernate and Spring - Unleash the MagicHibernate and Spring - Unleash the Magic
Hibernate and Spring - Unleash the Magic
 
TDD Mantra
TDD MantraTDD Mantra
TDD Mantra
 
Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...
Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...
Definitive Guide to Working With Exceptions in Java - takj at Java Champions ...
 
Definitive Guide to Working With Exceptions in Java
Definitive Guide to Working With Exceptions in JavaDefinitive Guide to Working With Exceptions in Java
Definitive Guide to Working With Exceptions in Java
 
Extreme Professionalism - Software Craftsmanship
Extreme Professionalism - Software CraftsmanshipExtreme Professionalism - Software Craftsmanship
Extreme Professionalism - Software Craftsmanship
 
Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...
Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...
Engaging Isolation - What I've Learned Delivering 250 Webinar Hours during CO...
 

Recently uploaded

AI/ML Infra Meetup | ML explainability in Michelangelo
AI/ML Infra Meetup | ML explainability in MichelangeloAI/ML Infra Meetup | ML explainability in Michelangelo
AI/ML Infra Meetup | ML explainability in MichelangeloAlluxio, Inc.
 
Crafting the Perfect Measurement Sheet with PLM Integration
Crafting the Perfect Measurement Sheet with PLM IntegrationCrafting the Perfect Measurement Sheet with PLM Integration
Crafting the Perfect Measurement Sheet with PLM IntegrationWave PLM
 
Studiovity film pre-production and screenwriting software
Studiovity film pre-production and screenwriting softwareStudiovity film pre-production and screenwriting software
Studiovity film pre-production and screenwriting softwareinfo611746
 
Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...
Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...
Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...Shahin Sheidaei
 
Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...
Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...
Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...rajkumar669520
 
GraphAware - Transforming policing with graph-based intelligence analysis
GraphAware - Transforming policing with graph-based intelligence analysisGraphAware - Transforming policing with graph-based intelligence analysis
GraphAware - Transforming policing with graph-based intelligence analysisNeo4j
 
Breaking the Code : A Guide to WhatsApp Business API.pdf
Breaking the Code : A Guide to WhatsApp Business API.pdfBreaking the Code : A Guide to WhatsApp Business API.pdf
Breaking the Code : A Guide to WhatsApp Business API.pdfMeon Technology
 
Vitthal Shirke Microservices Resume Montevideo
Vitthal Shirke Microservices Resume MontevideoVitthal Shirke Microservices Resume Montevideo
Vitthal Shirke Microservices Resume MontevideoVitthal Shirke
 
Advanced Flow Concepts Every Developer Should Know
Advanced Flow Concepts Every Developer Should KnowAdvanced Flow Concepts Every Developer Should Know
Advanced Flow Concepts Every Developer Should KnowPeter Caitens
 
top nidhi software solution freedownload
top nidhi software solution freedownloadtop nidhi software solution freedownload
top nidhi software solution freedownloadvrstrong314
 
Accelerate Enterprise Software Engineering with Platformless
Accelerate Enterprise Software Engineering with PlatformlessAccelerate Enterprise Software Engineering with Platformless
Accelerate Enterprise Software Engineering with PlatformlessWSO2
 
Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...
Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...
Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...Abortion Clinic
 
How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?
How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?
How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?XfilesPro
 
AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...
AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...
AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...Alluxio, Inc.
 
Beyond Event Sourcing - Embracing CRUD for Wix Platform - Java.IL
Beyond Event Sourcing - Embracing CRUD for Wix Platform - Java.ILBeyond Event Sourcing - Embracing CRUD for Wix Platform - Java.IL
Beyond Event Sourcing - Embracing CRUD for Wix Platform - Java.ILNatan Silnitsky
 
Prosigns: Transforming Business with Tailored Technology Solutions
Prosigns: Transforming Business with Tailored Technology SolutionsProsigns: Transforming Business with Tailored Technology Solutions
Prosigns: Transforming Business with Tailored Technology SolutionsProsigns
 
TROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERROR
TROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERRORTROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERROR
TROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERRORTier1 app
 
Cyaniclab : Software Development Agency Portfolio.pdf
Cyaniclab : Software Development Agency Portfolio.pdfCyaniclab : Software Development Agency Portfolio.pdf
Cyaniclab : Software Development Agency Portfolio.pdfCyanic lab
 

Recently uploaded (20)

AI/ML Infra Meetup | ML explainability in Michelangelo
AI/ML Infra Meetup | ML explainability in MichelangeloAI/ML Infra Meetup | ML explainability in Michelangelo
AI/ML Infra Meetup | ML explainability in Michelangelo
 
Crafting the Perfect Measurement Sheet with PLM Integration
Crafting the Perfect Measurement Sheet with PLM IntegrationCrafting the Perfect Measurement Sheet with PLM Integration
Crafting the Perfect Measurement Sheet with PLM Integration
 
Studiovity film pre-production and screenwriting software
Studiovity film pre-production and screenwriting softwareStudiovity film pre-production and screenwriting software
Studiovity film pre-production and screenwriting software
 
Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...
Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...
Gamify Your Mind; The Secret Sauce to Delivering Success, Continuously Improv...
 
Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...
Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...
Facemoji Keyboard released its 2023 State of Emoji report, outlining the most...
 
GraphAware - Transforming policing with graph-based intelligence analysis
GraphAware - Transforming policing with graph-based intelligence analysisGraphAware - Transforming policing with graph-based intelligence analysis
GraphAware - Transforming policing with graph-based intelligence analysis
 
Breaking the Code : A Guide to WhatsApp Business API.pdf
Breaking the Code : A Guide to WhatsApp Business API.pdfBreaking the Code : A Guide to WhatsApp Business API.pdf
Breaking the Code : A Guide to WhatsApp Business API.pdf
 
Corporate Management | Session 3 of 3 | Tendenci AMS
Corporate Management | Session 3 of 3 | Tendenci AMSCorporate Management | Session 3 of 3 | Tendenci AMS
Corporate Management | Session 3 of 3 | Tendenci AMS
 
Vitthal Shirke Microservices Resume Montevideo
Vitthal Shirke Microservices Resume MontevideoVitthal Shirke Microservices Resume Montevideo
Vitthal Shirke Microservices Resume Montevideo
 
Advanced Flow Concepts Every Developer Should Know
Advanced Flow Concepts Every Developer Should KnowAdvanced Flow Concepts Every Developer Should Know
Advanced Flow Concepts Every Developer Should Know
 
top nidhi software solution freedownload
top nidhi software solution freedownloadtop nidhi software solution freedownload
top nidhi software solution freedownload
 
Accelerate Enterprise Software Engineering with Platformless
Accelerate Enterprise Software Engineering with PlatformlessAccelerate Enterprise Software Engineering with Platformless
Accelerate Enterprise Software Engineering with Platformless
 
Top Mobile App Development Companies 2024
Top Mobile App Development Companies 2024Top Mobile App Development Companies 2024
Top Mobile App Development Companies 2024
 
Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...
Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...
Abortion ^Clinic ^%[+971588192166''] Abortion Pill Al Ain (?@?) Abortion Pill...
 
How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?
How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?
How Does XfilesPro Ensure Security While Sharing Documents in Salesforce?
 
AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...
AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...
AI/ML Infra Meetup | Improve Speed and GPU Utilization for Model Training & S...
 
Beyond Event Sourcing - Embracing CRUD for Wix Platform - Java.IL
Beyond Event Sourcing - Embracing CRUD for Wix Platform - Java.ILBeyond Event Sourcing - Embracing CRUD for Wix Platform - Java.IL
Beyond Event Sourcing - Embracing CRUD for Wix Platform - Java.IL
 
Prosigns: Transforming Business with Tailored Technology Solutions
Prosigns: Transforming Business with Tailored Technology SolutionsProsigns: Transforming Business with Tailored Technology Solutions
Prosigns: Transforming Business with Tailored Technology Solutions
 
TROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERROR
TROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERRORTROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERROR
TROUBLESHOOTING 9 TYPES OF OUTOFMEMORYERROR
 
Cyaniclab : Software Development Agency Portfolio.pdf
Cyaniclab : Software Development Agency Portfolio.pdfCyaniclab : Software Development Agency Portfolio.pdf
Cyaniclab : Software Development Agency Portfolio.pdf
 

Unit testing - 9 design hints

  • 1. Your tests are trying to tell you something by Victor Rentea at 9 design hints you were missing Read the article: https://victorrentea.ro/blog/design-insights-from-unit-testing/ Get the code: https://github.com/victorrentea/unit-testing.git Branch: 9hints_talk victorrentea.ro
  • 2. Hi, I'm Victor Rentea Java Champion – drinking since 2006 Trainer – 3000+ devs in 80+ companies Speaker – Conferences & Meetups Hibernate Spring Advanced FP Java Performance Secure Coding Reactive Architecture Clean Code Unit Testing
  • 3. pro Hibernate Spring Advanced FP Architecture Clean Code Unit Testing Masterclass Company Training Video Lessons @victorrentea VictorRentea.ro victorrentea@gmail.com Java Performance Secure Coding Reactive victorrentea.ro/community Join My Community YouTube Channel youtube.com/user/vrentea
  • 4. 335 © VictorRentea.ro a training by & (referring to an old Romanian saying) - NO COMMENT -
  • 5. 336 © VictorRentea.ro a training by ▪Better Signatures ⌨= code ▪Immutable Objects ⌨ ▪CQS Principle ⌨ ▪Functional Core / Imperative Shell ⌨ ▪Separation by Layers of Abstraction ⌨ ▪Decouple Unrelated Complexity ⌨ ▪Role-based Design ▪Onion Architecture ▪Breakdown Data Objects ⌨ Design Improvements hinted by Unit Tests
  • 6. 337 © VictorRentea.ro a training by Are you agile? "Emergent Architecture" Ever heard of the
  • 7. 338 © VictorRentea.ro a training by Are you agile? Tests give you hints on how to break and design complex logic "Emergent Architecture" that never emerges  Under-design is the default today?
  • 8. 339 © VictorRentea.ro a training by Do you write Tests BEFORE the implementation? Writing #responsible Unit Tests will 🚀 YOUR design skills If you would, you'd get ✔ more real coverage => courage ✔ more early design feedback The point of this talk → Mocks
  • 9. 340 © VictorRentea.ro a training by Mocks make our tests... Repeatable isolated from external systems Fast ✔ DB, external APIs Reasonably Complex ✔ When facing high cyclomatic complexity ➔ Alternatives: in-memory DB (H2) Testcontainers WireMock
  • 10. 341 © VictorRentea.ro a training by Logic to test Cyclomatic Complexity = number of independent paths through code Test Test Test Test Test Test Test CC=5 CC=6 f(a) g(b) calls CC=30 Too Many To cover all branches Too Heavy in setup and input data (a and b) End-to-end tests grow...
  • 11. 342 © VictorRentea.ro a training by ⛔ If there's not much complexity, avoid mocks A B Instead, test clusters of objects Internal refactoring won't break tests 👍
  • 12. 343 © VictorRentea.ro a training by (The rest of the talk assumes we have serious complexity) Unit Testing intensifies design around complex logic
  • 14. 345 © VictorRentea.ro a training by Precise Signatures Methods taking less data as arguments are easier to understand; ✔ and less coupled method(heavyObject) HeavyObject having dozens of fields method(part1, part2) only takes necessary parts of HeavyObject Tests will get simpler new HeavyObject(..)
  • 15. 346 © VictorRentea.ro a training by Immutable Objects ✔ eg. Mutating a parameter often causes awkward bugs. method(obj) { obj.setX(..); } method(..) { return x; } when(b.method(..)).thenReturn("stub"); doAnswer(invocation -> .. obj.setX("stub")) .when(b).method(any()); Mocking such a method is painful:
  • 16. 347 © VictorRentea.ro a training by do side-effects return void sendEmail(Email):void Command-Query Separation setActive(true):void return results search(criteria):List computePrice(flight):int Bertrand Meyer, in 1994: Pure Functions
  • 17. 348 © VictorRentea.ro a training by No side effects (doesn't change anything) No INSERTs, POSTs, queues, files, NO Fields changed,… 𝑒𝑔: 𝑀𝑎𝑡ℎ𝑒𝑚𝑎𝑡𝑖𝑐𝑎𝑙 𝐹𝑢𝑛𝑐𝑡𝑖𝑜𝑛𝑠: 𝑓 𝑥, 𝑦 = 𝑥2 + 𝑦 + Referential Transparent (same inputs produce the same output) No current time, random, GET, SELECT… Pure Functions
  • 18. 349 © VictorRentea.ro a training by Command-Query Separation Principle A method should be either a query (pure function, returning data), or a command (side-effecting, returning void) If you need to both stub (when...) and verify the same method, you are breaking CQS: Exception: external calls should happen ONCE eg. REST/WSDL calls that are critical, cost money, or take time when(b.query(..)).thenReturn(X); prod.call(); verify(b).command(Y); when(b.god(..)).thenReturn(X); prod.call(); verify(b).god(Y); Apply inside core logic https://martinfowler.com/articles/mocksArentStubs.html
  • 19. 350 © VictorRentea.ro a training by Functional Core / Imperative Shell Segregation The heavier some logic is, the less dependencies it should have. Keep complex logic in pure functions. ✔ Complex logic requires many tests. Shrink these tests by limiting mocks. => loose coupling when.thenReturn(..); when.thenReturn(..); when.thenReturn(x); when.thenReturn(y); prod.complex(); verify(..).f(z); verify(..).g(); verify(..).h(); x7=😖 when.thenReturn(..); // ideally 0 mocks z = prod.complex(x, y); assert..(z...);
  • 20. 351 © VictorRentea.ro a training by Dependencies Heavy complexity Side-effects FUNCTIONAL CORE PURE FUNCTION
  • 21. 352 © VictorRentea.ro a training by Design the Most Complex Parts of Logic as Pure Functions 💘 Easier to Understand Easier to Test
  • 22. 353 © VictorRentea.ro a training by Separation by Layers of Abstraction You have two complex functions in the same class, f() calling g() Move g() in a separate class ✔ You test g() separately. When testing f(), you don't want it to call g(), as g was tested Using partial mocks (@Spy) leads to horrid tests. Solution: class Big { f() { //complex g(); } g() { //complex } } class HighLevel { LowLevel low; f() { //complex low.g(); } } class LowLevel { g() { //complex } }
  • 23. 354 © VictorRentea.ro a training by ▪Better Signatures ▪Immutable Objects ▪CQS Principle ▪Functional Core / Imperative Shell ▪Separation by Layers of Abstraction ▪Decouple Unrelated Complexity ▪Role-based Design ▪Onion Architecture ▪Breakdown Data Objects Design Improvements hinted by Unit Tests
  • 24. 355 © VictorRentea.ro a training by Fixture Creep 2 complex functions in the same class, use different sets of dependencies. Break unrelated complexity for clarity and loose coupling. ✔ // prod code class Wide { A a; B b; complex1() { //uses a } complex2() { //uses b } } class WideTest { @Mock A a; @Mock B b; @InjectMocks Wide wide; @BeforeEach init() {//shared fixture when(a..).then when(b..).then } // 5 tests for complex1 // 4 tests for complex2 } class Complex1Test { @Mock A a; @Mock B b; } class Complex2Test { @Mock B b; @Mock C c; } Testing both in the same Test class leads to a bloated fixture ("Before"). Hard to trace later what's used by one test. Break the test class. Also: Hierarchical Tests.
  • 25. 356 © VictorRentea.ro a training by Mock Roles, not Objects Bad Habit: You finish the implementation, then you write tests. You [blindly] @Mock all dependencies. Two years later, your tests are fragile and slow you down. Before mocking a dependency, clarify its role. ✔ And test earlier. http://jmock.org/oopsla2004.pdf
  • 26. 357 © VictorRentea.ro a training by Problem: You allow external APIs, DTOs, and ugly frameworks to enter freely in your core logic. Testing your core logic now requires creating foreign objects, or mocking an awkward library. Onion Architecture Pull core logic in an Agnostic Domain ✔ So most tests talk in terms of your internal Domain Model ✔ https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html
  • 28. 359 © VictorRentea.ro a training by Creepy Object Mother You use large data structures in your core logic. If the structures enforce their internal consistency, (it's not an anemic model only having getters and setters) then creating test data instances becomes cumbersome, (unrelated fields to set) so you share a global "TestData" class that builds correct instances. TestData gets bloated and couples your tests together. Break TestData🪓 in several classes Break data structures🪓 in separate Bounded Contexts? ie packages>modular monolith>microservices🤞 https://martinfowler.com/bliki/ObjectMother.html (2006)
  • 30.
  • 31. 362 © VictorRentea.ro a training by ▪More Calls from Tests > Better Signatures, Better Skills ▪Immutable Objects 🤘 (rock) ▪when.then xor verify > Command-Query Separation ▪More Tests ➔ ↓Mocks > Functional Core / Imperative Shell ▪Partial Mocks > Separation by Layers of Abstraction ▪Bloated Fixture > Break Test > Decouple Unrelated Complexity ▪Mock Roles not Objects > Role-based Design ▪Keep most tests on Domain > Onion Architecture ▪Creepy Object Mother > Break Data Objects > 2 Bounded Contexts? Recap