Slide 1

Slide 1 text

Modulithic Applications
 with Spring Boot Building better monoliths Oliver Drotbohm ƀ [email protected] / odrotbohm

Slide 2

Slide 2 text

2

Slide 3

Slide 3 text

Monolith VS. Microservice 3 Module
 A Module
 B Module
 C Module
 B Module
 C Module
 A Bounded Context Deployment Unit Internal invocation External invocation

Slide 4

Slide 4 text

Monolith 4 The application packages the implementation of multiple Bounded Contexts as a single deployment unit. Easy to refactor Easy to test the overall system Likely to degrade unless explicitly managed Harder to test individual Bounded Contexts

Slide 5

Slide 5 text

Microservices 5 A bounded context defines the boundaries of the deployment artifact. Often parts of the context are even deployed as separate processes. ○ Bounded Context interaction is remote ○ Testing individual modules Hard to refactor context boundaries Hard to test the overall system

Slide 6

Slide 6 text

The Sample Codebase 6

Slide 7

Slide 7 text

7 Orders Business
 Time Catalog Inventory Component Dependency Type dependency

Slide 8

Slide 8 text

Moduliths https://github.com/odrotbohm/moduliths Binaries available from https://repo.spring.io 8

Slide 9

Slide 9 text

Moduliths 9 1. A convention to map contexts to packages Packages directly nested underneath the main application package are considered context ones.

Slide 10

Slide 10 text

Package Conventions 10 ….modulith ….modulith.moduleA ….modulith.moduleB Visibility modifiers and the compiler enough to hide internals.

Slide 11

Slide 11 text

11 package com.acme @Modulith // Instead of @SpringBootApplication class MyApplication { … } Applies package conventions

Slide 12

Slide 12 text

Package structure DEMO 12

Slide 13

Slide 13 text

Moduliths 13 1. A convention to map contexts to packages Packages directly nested underneath the main application package are considered context ones. 2. Test support to bootstrap modules Integration with Spring test context framework and Spring Boot integration test support to limit bootstrap (component & entity scanning) to only the involved packages.

Slide 14

Slide 14 text

Web Business logic Data access @Data…Test Module A Module B Module C @WebMvcTest @…Test ?

Slide 15

Slide 15 text

15 package com.acme @Modulith // Instead of @SpringBootApplication class MyApplication { … } package com.acme.moduleA @ModuleTest // Instead of @SpringBootTest class MyModuleTests { … } Applies package conventions Bootstraps single module for test

Slide 16

Slide 16 text

16 Orders Business
 Time Catalog Inventory Component Dependency Type dependency

Slide 17

Slide 17 text

17 Orders Business
 Time Catalog Inventory Component Dependency Type dependency

Slide 18

Slide 18 text

Single module bootstrap DEMO 18

Slide 19

Slide 19 text

19 Orders Business
 Time Catalog Inventory Component Dependency Type dependency

Slide 20

Slide 20 text

20 Orders Business
 Time Catalog Inventory Component Dependency Type dependency

Slide 21

Slide 21 text

21 Orders Business
 Time Catalog Inventory Component Dependency Type dependency

Slide 22

Slide 22 text

Detect and remove violation DEMO 22

Slide 23

Slide 23 text

23 Orders Business
 Time Catalog Inventory Component Dependency Type dependency 
 Event Event publication

Slide 24

Slide 24 text

Dependency types 24 1. Simple type dependency References to aggregates and entities of other modules. 2. Component dependency References to other Spring beans, required to bootstrap the module 3. Events & event listeners Dependency on some other module’s event type. Interesting as they’re great hooks for testing.

Slide 25

Slide 25 text

Dependency types 25 1. Simple type dependency References to aggregates and entities of other modules. 2. Component dependency References to other Spring beans, required to bootstrap the module 3. Events & event listeners Dependency on some other module’s event type. Interesting as they’re great hooks for testing. ☝Avoid!

Slide 26

Slide 26 text

26 Orders Business
 Time Catalog Inventory Component Dependency Type dependency 
 Event Event publication

Slide 27

Slide 27 text

Multi module bootstrap DEMO 27

Slide 28

Slide 28 text

Bootstrap modes 28 1. Standalone Bootstraps the module the test is contained in. Components in other modules the bootstrapped module depends on need to be provided through @MockBean. 2. Direct dependencies Bootstraps the module including the modules it directly depends on. Transitive dependencies have to be mocked just like in standalone mode. 3. All dependencies Bootstraps the entire sub-tree of modules starting from the current one.

Slide 29

Slide 29 text

Moduliths 29 1. A convention to map contexts to packages Packages directly nested underneath the main application package are considered context ones. 2. Test support to bootstrap modules Integration with Spring test context framework and Spring Boot integration test support to limit bootstrap (component & entity scanning) to only the involved packages. 3. Simple set of access rules and API to verify Only access components in module API packages.

Slide 30

Slide 30 text

Some conventions… 30 01 10 M M 01 10 Allowed by the compiler Allowed by Moduliths Rejected by the compiler Rejected by Moduliths Public Package protected Bounded Context Java Package

Slide 31

Slide 31 text

API Package Convention 31 ….modulith ….modulith.moduleA ….modulith.moduleB Visibility modifiers and the compiler enough to hide internals.

Slide 32

Slide 32 text

Module B moduleB Module A moduleA 32 ComponentA ComponentAImpl ComponentB ComponentBImpl Public Package protected Bounded Context Java Package 01 10 01 10

Slide 33

Slide 33 text

API Package Convention 33 ….modulith ….modulith.moduleA ….modulith.moduleB Visibility modifiers and the compiler enough to hide internals.

Slide 34

Slide 34 text

API Package Convention 34 ….modulith ….modulith.moduleA ….modulith.moduleA.internal ….modulith.moduleB ….modulith.moduleB.internal Access to components
 residing in internal packages
 forbidden and checked
 during tests.

Slide 35

Slide 35 text

Module A moduleA.foo Module B moduleB moduleA 35 ComponentA ComponentAImpl ComponentB ComponentBImpl moduleA.bar SupportA SupportAImpl 01 10 M 01 10 01 10 Public Package protected Bounded Context Java Package

Slide 36

Slide 36 text

Violation detection Module cycles / Internal components DEMO 36

Slide 37

Slide 37 text

Moduliths 37 1. A convention to map contexts to packages Packages directly nested underneath the main application package are considered context ones. 2. Test support to bootstrap modules Integration with Spring test context framework and Spring Boot integration test support to limit bootstrap (component & entity scanning) to only the involved packages. 3. Simple set of access rules and API to verify Only access components in module API packages. 4. Documentation support PlantUML integration via Simon Brown’s Structurizr to document module structure and dependency types.

Slide 38

Slide 38 text

Documentation DEMO 38

Slide 39

Slide 39 text

Tool ecosystem and alternative approaches 39

Slide 40

Slide 40 text

Multiple Artifacts 40 Every module port becomes a dedicated build artifact. Dedicated control over dependencies Test scope is defined by the artifact Potential explosion of number of artifacts Internal structure visible to the outside

Slide 41

Slide 41 text

Java Module System 41 Every module becomes a Java 9+ module. ○ Strong coupling between module and artifact ○ Semantics of the „opens“ keyword ○ No test support

Slide 42

Slide 42 text

External Tools 42 External tools (e.g. jQAssistant, Sonargraph, jDepend) integrated into the build and executed in the CI environment are used to signal structural violations. Most extensive option Distance to development workflow

Slide 43

Slide 43 text

Moduliths 43 1. A convention to map contexts to packages Packages directly nested underneath the main application package are considered context ones. 2. Test support to bootstrap modules Integration with Spring test context framework and Spring Boot integration test support to limit bootstrap (component & entity scanning) to only the involved packages. 3. Simple set of access rules and API to verify Only access components in module API packages. 4. Documentation support PlantUML integration via Simon Brown’s Structurizr to document module structure and dependency types.

Slide 44

Slide 44 text

Resources 44 Moduliths Project website on GitHub Majestic Modular Monoliths Video on Youtube Modular Monoliths Simon Brown – Video on YouTube Refactoring to a System of Systems Video on YouTube

Slide 45

Slide 45 text

Thank you! 45 Oliver Drotbohm ƀ [email protected] / odrotbohm