Thursday, November 7, 2019

Scott Wlaschin - Domain Modeling Made Functional

Notes for Scott Wlaschin book Domain Modeling Made Functional - Tackle Software Complexity with Domain-Driven Design and F#.

Previous DDD books I've read: Domain Driven Design (Eric Evans) & Implementing Domain-Driven Design

As a summary I enjoyed this book. The writing was pretty clear and compact and made me consider F# as an interesting option for building software.

Rough structure of the book

First part of the book was introducing DDD & it's main concepts.

Second part went through types & functions especially in F# context, how to use types to model domain and how to model workflows as pipelines.

Third part discussed first how to implement the domain model, types and pipelines. After that implementation related concepts were discussed: error handling, serialization and persistence.

Fine-grained type system & DDD

F# kind of type system seems to make it quite cheap/easy to introduce lots of types which allows to represent domain on a quite fine-grained way.

Some question marks for me:

  • How difficult it might get with naming if there are very much small types?
  • How much boilerplate code it might require to transfer e.g. an order through a pipeline of types like UnvalidatedOrder, ValidatedOrder, PricedOrder & PricedOrderWithShippingMethod etc.

It would be interesting to try.

Summary of things & practices discussed

DDD

  • Aim to develop a deep shared understanding of the domain
  • Partition the solution space into autonomous, decoupled bounded contexts

DDD with F# kind of language

  • Before implementation, aim to capture the requirements with a type-based notation with both the nouns and the verbs
    • Nouns will usually be represented by an algebraic type system
    • Verbs will usually be represented by functions
  • Aim to capture business rules & constraints in the type system whenever possible.
    • "Make illegal states unpresentable"
  • Aim to design functions pure and total

Summary of FP techniques

  • Compose workflows from smaller functions
  • Parameterize functions when there's a dependency
  • Bake dependencies into a function using partial application
    • Allows to compose functions more easily & hide implementation details
  • Use special functions transforming functions into needed shapes
  • Solve type mismatch problems by lifting types into a common type

No comments: