Domain-Driven Design in PHP - Carlos Buenosvinos - E-Book

Domain-Driven Design in PHP E-Book

Carlos Buenosvinos

0,0
45,59 €

-100%
Sammeln Sie Punkte in unserem Gutscheinprogramm und kaufen Sie E-Books und Hörbücher mit bis zu 100% Rabatt.

Mehr erfahren.
Beschreibung

Real examples written in PHP showcasing DDD Architectural Styles, Tactical Design, and Bounded Context Integration

About This Book

  • Focuses on practical code rather than theory
  • Full of real-world examples that you can apply to your own projects
  • Shows how to build PHP apps using DDD principles

Who This Book Is For

This book is for PHP developers who want to apply a DDD mindset to their code. You should have a good understanding of PHP and some knowledge of DDD. This book doesn't dwell on the theory, but instead gives you the code that you need.

What You Will Learn

  • Correctly design all design elements of Domain-Driven Design with PHP
  • Learn all tactical patterns to achieve a fully worked-out Domain-Driven Design
  • Apply hexagonal architecture within your application
  • Integrate bounded contexts in your applications
  • Use REST and Messaging approaches

In Detail

Domain-Driven Design (DDD) has arrived in the PHP community, but for all the talk, there is very little real code. Without being in a training session and with no PHP real examples, learning DDD can be challenging. This book changes all that. It details how to implement tactical DDD patterns and gives full examples of topics such as integrating Bounded Contexts with REST, and DDD messaging strategies. In this book, the authors show you, with tons of details and examples, how to properly design Entities, Value Objects, Services, Domain Events, Aggregates, Factories, Repositories, Services, and Application Services with PHP. They show how to apply Hexagonal Architecture within your application whether you use an open source framework or your own.

Style and approach

This highly practical book shows developers how to apply domain-driven design principles to PHP. It is full of solid code examples to work through.

Sie lesen das E-Book in den Legimi-Apps auf:

Android
iOS
von Legimi
zertifizierten E-Readern

Seitenzahl: 376

Veröffentlichungsjahr: 2017

Bewertungen
0,0
0
0
0
0
0
Mehr Informationen
Mehr Informationen
Legimi prüft nicht, ob Rezensionen von Nutzern stammen, die den betreffenden Titel tatsächlich gekauft oder gelesen/gehört haben. Wir entfernen aber gefälschte Rezensionen.



Title Page

Domain-Driven Design in PHP

              

A Highly Practical Guide

           

Carlos Buenosvinos
Christian Soronellas
Keyvan Akbary

BIRMINGHAM - MUMBAI

Copyright

Domain-Driven Design in PHP

Copyright © 2017 Carlos Buenosvinos, Christian Soronellas, Keyvan Akbary

All rights reserved. No part of this book may be reproduced, stored in a retrieval system, or transmitted in any form or by any means, without the prior written permission of the publisher, except in the case of brief quotations embedded in critical articles or reviews.

Every effort has been made in the preparation of this book to ensure the accuracy of the information presented. However, the information contained in this book is sold without warranty, either express or implied. Neither the authors, nor Packt Publishing, and its dealers and distributors will be held liable for any damages caused or alleged to be caused directly or indirectly by this book.

Packt Publishing has endeavored to provide trademark information about all of the companies and products mentioned in this book by the appropriate use of capitals. However, Packt Publishing cannot guarantee the accuracy of this information.

First published: June 2017

Production reference: 1090617

Published by Packt Publishing Ltd.
Livery Place
35 Livery Street
Birmingham 
B3 2PB, UK.

ISBN 978-1-78728-494-4

www.packtpub.com

Credits

AuthorsCarlos Buenosvinos

Christian Soronellas

Keyvan Akbary

Technical Editor

Joel Wilfred D'souza

Acquisition Editor

Frank Pohlmann

Layout co-ordinator

Aparna Bhagat

Indexer

Pratik Shirodkar

  

Foreword

I must admit that when I first heard of the Domain-Driven Design in PHP initiative, I was a bit worried. The danger was twofold: first of all, when glancing over the table of contents, the subject matter looked like it was a rehash of content that was already available in several other Domain-Driven Design books. Second, writing a book on Domain-Driven Design targeted specifically toward the PHP community seemed needlessly narrowing, particularly as Domain-Driven Design itself is not language specific. As such, this might inhibit PHP developers from looking past the boundaries of their own community, especially when considering that there's a lot going on beyond the scope of PHP. In fact, even Domain-Driven Design is one of those things, as it didn't originate in the PHP community.

After reading the book, I'm happy to inform you that my worries have been invalidated!

With regard to my first concern: of course there is some overlap with previously published Domain-Driven Design books. Yet the authors have restrained themselves. The theoretical parts are exactly what you need to be able to understand what's going on in the code samples. Besides, if you never read another Domain-Driven Design book, this one gives you what you need to start applying some Domain-Driven Design principles and patterns in your code, as it's practical by nature.

My second concern — about the PHP aspect of this book — has been addressed very well. It turns out there are a lot of things to say about Domain-Driven Design in a PHP world. This book is specifically targeted at an audience consisting of PHP developers. The code samples resemble real-world PHP projects, and the authors use a programming style we know from projects using Symfony or Silex. For persisting Domain objects, Doctrine ORM — which is the de facto standard data mapper for PHP — is used.

This book also fulfills a need I've often seen in the PHP community: the need for concrete examples. It's not always easy for authors to come up with proper illustrations of how to apply certain ideas that have a low risk of being misinterpreted or abused in real-world projects. And in Domain-Driven Design, which is philosophical by nature, this is even more challenging.

In the case of this book, the authors haven't been afraid to show many useful examples, along with some interesting alternative solutions. They aren't just handwaving at solutions either; they take the time to provide detailed explanations — such as when they talk about saving snapshots for Aggregates with a large number of Domain Events, or when they discuss integrating Bounded Contexts using RabbitMQ. I can't recall having previously seen an implementation of these things in a book or article on Domain-Driven Design.

For me personally, Domain-Driven Design is one the most interesting subjects in software development today. There is so much to discover, and there are many subjects related to it: Agile software development, TDD, and BDD, but also living documentation, visualization, and knowledge crunching techniques. Once you start looking into all of this, you'll realize that Domain-Driven Design is an area of expertise worth investigating, as it enables you to add much more to your own worth as a software developer.

So, I guess what I want to say is this: dive into this book, learn from it, and then pick up another book (see the list of references at the end of this book for suggestions of future reading). Continuous learning is a fundamental part of keeping up to date in the software industry, so don't stop here.

Oh, and by the way: if you get a chance to go to Barcelona, make sure you take part in one of the many PHP or Symfony events. The community is big, friendly, and full of interesting ideas. You'll find the authors of this book there too. They are all invested in the local PHP community and are happy to share their insights and experiences with you!

Matthias Noback Author of A Year with Symfony

About the Authors

Carlos Buenosvinos is a PHP Extreme Programmer with more than 15 years of experience developing web applications and more than 10 years experience as a Tech Lead and CTO leading teams of between 20 and 100 people. He is a Certified ScrumMaster (CSM) and has coached and trained close to two dozen different companies in Agile practices, both as an employee and as a consultant. On the technical side, he is a Zend PHP Engineer, a Zend Framework Engineer, and MySQL certified. He is also a board member of the PHP Barcelona User Group. He has worked with e-commerce (Atrapalo and eBay), payment processing (Vendo), classifieds (Emagister), and B2B recruiting tools (XING). He is interested in JavaScript, DevOps, and Scala. He likes developing for mobile, Raspberry Pi, and games.

Twitter:

@buenosvinos

Web:

https://carlosbuenosvinos.com

GitHub:

https://github.com/carlosbuenosvinos

Christian Soronellas is a passionate Software Developer, Software Journeyman, and Craftsman Apprentice. He’s an Extreme Programmer soul with more than 10 years of experience in web development. He’s also a Zend PHP 5.3 Certified Engineer, a Zend Framework Certified Engineer, and a SensioLabs Certified Symfony Developer. He has worked as a freelancer, as well as at Privalia, Emagister, Atrapalo, and Enalquiler as a Software Architect.

Twitter:

@theUniC

GitHub:

https://github.com/theUniC

Keyvan Akbary is a polyglot Software Developer who loves Software fundamentals, the Craftsmanship movement, Extreme Programming, SOLID principles, Clean Code, Design Patterns, and Testing. He’s also a sporadic Functional Programmer. He understands technology as a medium for providing value. He has worked on countless projects as a freelancer, on video streaming (Youzee), and on an online marketplace (MyBuilder) — all in addition to founding a crowdfunding company (Funddy). Currently, Keyvan is working in FinTech as a Lead Developer at TransferWise London.

Twitter:

@keyvanakbary

Web:

http://keyvanakbary.com

GitHub:

https://github.com/keyvanakbary

Acknowledgments

First of all, we would like to thank all our friends and family. Without their support, writing this book would have been an even more difficult task. Thanks for accommodating our schedules and taking care of our children in order to free up time for us to focus on writing. You're wonderful, and part of this book is also yours.

We are three Spaniards who wrote a book in English, so if you'd guess our English is far from perfect, you'd be correct. Luckily for us, Edd Mann has supported us with the language since the beginning. He's not just a great collaborator but also a great friend, and we owe him a huge thanks. The final review was done by the professional copy editor Natalye Childress. She has done a great work rewriting our words to make them understandable. Thank you so much. Our book is easier and more enjoyable to read.

A group of PHP developers in Barcelona defends what we call el camino del rigor, or the path of rigor. It existed before the craftsmanship movement, and it means to struggle with everything stacked against us in order to build exceptional things in an exceptional way. Two particular developers and friends from that group are Albert Casademont and Ricard Clau, both of whom are extraordinary people committed to the community. Thank you so much for helping with the revision process. Your contributions have been incredibly valuable.

We would like to thank every developer who has worked with us in the companies where we've applied Domain-Driven Design. We know you've been struggling when learning and applying these concepts. Some of you weren't so open-minded at the beginning, but after using the basic building blocks for a while, you became evangelists. Thanks for your faith.

Our book was for sale from the moment we put the first chapters on Leanpub. Early adopters who bought the book in its beginning stages gave us the much needed love and support to get this done. Thanks for the motivation to keep going.

Thanks also to Matthias Noback for his foreword and feedback on the book. The end result is better because of his contributions.

A special mention to Vaughn Vernon — not just because his work was an incredible source of information and inspiration for us, but also because he helped us find a good publisher, gave us valuable advice, and shared ideas with us. Thanks so much for your help.

Last but not least, we'd like to express our gratitude to all the people who have reported issues, made suggestions, and otherwise contributed to our GitHub repository. To all of you, thank you. You've helped us make this book better. More importantly, you've helped the community grow and helped other developers be better developers. As Robert C. Martin wrote in his book, Clean Code: A Handbook of Agile Software Craftsmanship, "You are reading this book for two reasons. First, you are a programmer. Second, you want to be a better programmer. Good. We need better programmers." So thanks to Jordi Abad, Jonathan Wondrusch, César Rodríguez, Yannick Voyer, Victor Guardiola, Oriol González, Henry Snoek, Tom Jowitt, Sascha Schimke, Sven Herrmann, Daniel Abad, Luis Rovirosa, Luis Cordova, Raúl Ramos, Juan Maturana, Nil Portugués, Nikolai Zujev, Fernando Pradas, Raúl Araya, Neal Brooks, Hubert Béague, Aleksander Rekść, Sebastian Machuca, Nicolas Oelgart, Sebastiaan Stok, Vladimir Hraban, Vladas Dirzys, and Marc Aube.

www.PacktPub.com

For support files and downloads related to your book, please visit www.PacktPub.com.

Did you know that Packt offers eBook versions of every book published, with PDF and ePub files available? You can upgrade to the eBook version at www.PacktPub.com and as a print book customer, you are entitled to a discount on the eBook copy. Get in touch with us at [email protected] for more details.

At www.PacktPub.com, you can also read a collection of free technical articles, sign up for a range of free newsletters and receive exclusive discounts and offers on Packt books and eBooks.

https://www.packtpub.com/mapt

Get the most in-demand software skills with Mapt. Mapt gives you full access to all Packt books and video courses, as well as industry-leading tools to help you plan your personal development and advance your career.

Customer Feedback

Thanks for purchasing this Packt book. At Packt, quality is at the heart of our editorial process. 

If you'd like to join our team of regular reviewers, you can e-mail us at [email protected]. We award our regular reviewers with free eBooks and videos in exchange for their valuable feedback. Help us be relentless in improving our products!

Dedication

This book is dedicated to my dearest Vanessa, and to Valentina and Gabriela. Thanks for your love, your support, and your patience.                                                                                                                                – Carlos
To my dear Elena. Without your encouragement, your love, and your patience, this book would not have been possible.                                                                                                                             – Christian
To my parents, John and Mercedes, who raised me free of constraints. This will be the first book of many. To my love, Clara, for your unconditional support and infinite patience.                                                                                                                              –  Keyvan

Table of Contents

Foreword

Acknowledgments

Dedication

Preface

Who Should Read This Book

DDD and PHP Community

Summary of Chapters

Chapter 1: Getting Started with Domain-Driven Design

Chapter 2: Architectural Styles

Chapter 3: Value Objects

Chapter 4: Entities

Chapter 5: Domain Services

Chapter 6: Domain-Events

Chapter 7: Modules

Chapter 8: Aggregates

Chapter 9: Factories

Chapter 10: Repositories

Chapter 11: Application

Chapter 12: Integrating Bounded Contexts

Appendix: Hexagonal Architecture with PHP

Code and Examples

Getting Started with Domain-Driven Design

Why Domain-Driven Design Matters

The Three Pillars of Domain-Driven Design

Ubiquitous Language

Event Storming

Considering Domain-Driven Design

The Tricky Parts

Strategical Overview

Related Movements: Microservices and Self-Contained Systems

Wrap-Up

Architectural Styles

The Good Old Days

Layered Architecture

Model-View-Controller

Example of Layered Architecture

The View

The Controller

Inverting Dependencies: Hexagonal Architecture

The Dependency Inversion Principle (DIP)

Applying Hexagonal Architecture

Command Query Responsibility Segregation (CQRS)

The Write Model

The Read Model

Synchronizing the Write Model with the Read Model

Event Sourcing

Wrap-Up

Value Objects

Definition

Value Object vs. Entity

Currency and Money Example

Characteristics

Measures, Quantifies, or Describes

Immutability

Conceptual Whole

Value Equality

Replaceability

Side-Effect-Free Behavior

Basic Types

Testing Value Objects

Persisting Value Objects

Persisting Single Value Objects

Embedded Value with an Ad Hoc ORM

Embedded Value (Embeddables) with Doctrine >= 2.5.*

Embedded Value with Doctrine <= 2.4.*

Serialized LOB and Ad Hoc ORM

Improved Serialization with JMS Serializer

Serialized LOB with Doctrine

Doctrine Object Mapping Type

Doctrine Custom Types

Persisting a Collection of Value Objects

Collection Serialized into a Single Column

Collection Backed by a Join Table

Collection Backed by a Join Table with Doctrine

Collection Backed by a Join Table with an Ad Hoc ORM

Collection Backed by a Database Entity

NoSQL

PostgreSQL JSONB and MySQL JSON Type

Security

Wrap-Up

Entities

Introduction

Objects Vs. Primitive Types

Identity Operation

Persistence Mechanism Generates Identity

Surrogate Identity

Active Record Vs. Data Mapper for Rich Domain Models

Client Provides Identity

Application Generates Identity

Other Bounded Context Generates Identity

Persisting Entities

Setting Up Doctrine

Mapping Entities

Mapping Entities Using Annotated Code

Mapping Entities Using XML

Mapping Entity Identity

Final Mapping File

Testing Entities

DateTimes

Passing All Dates as Parameters

Test Class

External Fake

Reflection

Validation

Attribute Validation

Entire Object Validation

Decoupling Validation Messages

Validating Object Compositions

Entities and Domain Events

Wrap-Up

Services

Application Services

Domain Services

Domain Services and Infrastructure Services

An Issue of Code Reuse

Testing Domain Services

Anemic Domain Models Vs Rich Domain Models

Anemic Domain Model Breaks Encapsulation

Anemic Domain Model Brings a False Sense of Code Reuse

How to Avoid Anemic Domain Models

Wrap-Up

Domain-Events

Introduction

Definition

Short Story

Metaphor

Real-World Example

Characteristics

Naming Conventions

Domain Events and Ubiquitous Language

Immutability

Modeling Events

Doctrine Events

Persisting Domain Events

Event Store

Publishing Events from the Domain Model

Publishing a Domain Event from an Entity

Publishing your Domain Events from Domain or Application Services

How the Domain Event Publisher Works

Setting Up DomainEventListeners

Testing Domain Events

Spreading the news to Remote Bounded Contexts

Messaging

Syncing Domain Services with REST

Wrap-Up

Modules

General Overview

Leverage Modules in PHP

First-Level Namespacing

PEAR-Style Namespacing

PSR-0 and PSR-4 Namespacing

Bounded Contexts and Applications

Structuring Code in Modules

Design Guidelines

Modules in the Infrastructure Layer

Mixing Different Technologies

Modules in the Application Layer

Wrap-Up

Aggregates

Introduction

Key Concepts

ACID

Transactions

Isolation Levels

Referential Integrity

Locking

Concurrency

Pessimistic Concurrency Control (PCC)

With Doctrine

Optimistic Concurrency Control

With Elasticsearch

With Doctrine

What Is an Aggregate?

What Martin Fowler Says...

What Wikipedia Says...

Why Aggregates?

A Bit of History

Anatomy of an Aggregate

Aggregate Design Rules

Design Aggregates Based in Business True Invariants

Small Aggregates Vs. Big Aggregates

Reference Other Entities by Identity

Modify One Aggregate Per Transaction and Request

Sample Application Service: User and Wishes

No Invariant, Two Aggregates

No More Than Three Wishes Per User

Pessimistic Concurrency Control

Optimistic Concurrency Control

Transactions

Wrap Up

Factories

Factory Method on Aggregate Root

Forcing Invariants

Factory on Service

Building Specifications

Building Aggregates

Testing Factories

Object Mother

Test Data Builder

Wrap-Up

Repositories

Definition

Repositories Are Not DAOs

Collection-Oriented Repositories

In-Memory Implementation

Doctrine ORM

Object Mapping

Doctrine Custom Mapping Types

Entity Manager

DQL Implementation

Persistence-Oriented Repository

Redis Implementation

SQL Implementation

Extra Behavior

Querying Repositories

Specification Pattern

In-Memory Implementation

SQL Implementation

Managing Transactions

Testing Repositories

Testing Your Services with In-Memory Implementations

Wrap-Up

Application

Requests

Building Application Service Requests

Request Design

Use Primitives

Serializable

No Business Logic

No Tests

Anatomy of an Application Service

Dependency Inversion

Instantiating Application Services

Customize an Application Service

Execution

One Class Per Application Service

Multiple Application Service Methods per Class

Returning Values

DTO from Aggregate Instances

Data Transformers

Multiple Application Services on Compound Layouts

AJAX Content Integration

ESI Content Integration

Symfony Sub Requests

One Controller, Multiple Application Services

Testing Application Services

Transactions

Security

Domain Events

Command Handlers

Tactician Library and Other Options

Wrap-Up

Integrating Bounded Contexts

Integration Through the Data Store

Integration Relationships

Separate Ways

Conformist

Implementing Bounded Context Integrations

Modern RPC

Message Queues

Wrap-Up

Hexagonal Architecture with PHP

Introduction

First Approach

Repositories and the Persistence Edge

Decoupling Business and Persistence

Migrating our Persistence to Redis

Decouple Business and Web Framework

Rating an Idea Using the API

Console App Rating

Testing Rating an Idea UseCase

Testing Infrastructure

Arggg, So Many Dependencies!

Domain Services and Notification Hexagon Edge

Let's Recap

Hexagonal Architecture

Key Points

What's Next?

Bibliography

The End

Why subscribe?

Fully searchable across every book published by Packt

Copy and paste, print, and bookmark content

On demand and accessible via a web browser

Preface

In 2014, after two years of reading about and working with Domain-Driven Design, Carlos and Christian, friends and workmates, traveled to Berlin to participate in Vaughn Vernon's Implementing Domain-Driven Design Workshop. The training was fantastic, and all the concepts that were swirling around in their minds prior to the trip suddenly became very real. However, they were the only two PHP developers in a room full of Java and .NET developers.

Around the same time, php[tek], an annual PHP conference, opened its call for papers, and Carlos sent one about Hexagonal Architecture. His talk was rejected, but Eli White — of musketeers.me and php[architect] fame — got in touch with him a month later wondering if he was interested in writing an article about Hexagonal Architecture for the magazine php[architect]. So in June 2014, Hexagonal Architecture with PHP was published. That article, which you'll find in the Appendix, was the origin of this book.

In late 2014, Carlos and Christian talked about extending the article and sharing all their knowledge of and experience in applying Domain-Driven Design in production. They were very excited about the idea behind the book: helping the PHP community delve into Domain-Driven Design from a practical approach. At that time, concepts such as Rich Domain Models and framework-agnostic applications weren't so common in the PHP community. So in December 2014, the first commit to the GitHub book repository was pushed.

Around the same time, in a parallel universe, Keyvan co-founded Funddy, a crowdfunding platform for the masses built on top of the concepts and building blocks of Domain-Driven Design. Domain-Driven Design proved itself effective in the exploratory process and modeling of building an early-stage startup like Funddy. It also helped handle the complexity of the company, with its constantly changing environment and requirements. And after connecting with Carlos and Christian and discussing the book, Keyvan proudly signed on as the third writer.

Together, we've written the book we wanted to have when we started with Domain-Driven Design. It's full of examples, production-ready code, shortcuts, and our recommendations based on our experiences of what worked and what didn't for our respective teams. We arrived at Domain-Driven Design via its building blocks — Tactical Patterns — which is why this book is mainly about them. Reading it will help you learn them, write them, and implement them. You'll also discover how to integrate Bounded Contexts using synchronous and asynchronous approaches, which will open your world to strategic design — though the latter is a road you'll have to discover on your own.

This book is heavily inspired by Implementing Domain-Driven Design by Vaughn Vernon (aka the Red Book), and Domain-Driven Design: Tackling Complexity in the Heart of Software by Eric Evans (aka the Blue Book). You should buy both books. You should read them carefully. You should love them.

Who Should Read This Book

If you're a PHP Developer, Architect, or Tech Lead, we highly recommend this book. It will help you become a better professional. It will give you a new overview of and approach to the applications you're developing. If you're a Junior profile, getting into Value Objects, Entities, Repositories, and Domain Events is important in order to model any Domain you'll face in the future. For an average profile, understanding the benefits of Hexagonal Architecture and the boundaries between your framework and your Application is key for writing code that's easier to maintain in the real world (framework migrations, testing, etc.). More advanced readers will have fun both exploring how to use Domain Events in order to integrate Applications and delving deeper into Aggregate design.

Although Domain-Driven Design is not about technology, you still need it to make HTTP requests to access your Domain. Throughout the book, we recommend using specific PHP frameworks and libraries, such as Symfony, Silex, and Doctrine. For some examples, we also use specific technologies, such as MySQL, RabbitMQ, Redis, and Elasticsearch. However, most important are the behind-the-scenes concepts — concepts that are applicable regardless of the technology used to implement them.

Additionally, the book is loaded with tons of details and examples, such as how to properly design and implement all the building blocks of Domain-Driven Design — including Value Objects, Entities, Services, Domain Events, Aggregates, Factories, Repositories, and Application Services — with PHP. It explains what the role of the main PHP libraries and frameworks used in Domain-Driven Design are. The book also teaches how to apply Hexagonal Architecture within your application, regardless of whether you use an open source framework or your own one. Finally, it shows how to integrate Bounded Contexts using REST frameworks and messaging mechanisms. If you're interested in any of these subjects, this book is for you.

DDD and PHP Community

In 2016, Carlos and Christian went to the first official Domain-Driven Design conference, DDD Europe. They were really happy to see some PHP open source leaders, such as Marco Pivetta (Doctrine) and Sebastian Bergmann (PHPUnit), attending the conference.

Domain-Driven Design arrived in the PHP community two years prior to that conference. However, there's still a lack of documentation and real code examples. Why? We think not many people have worked with this kind of approach in production yet — even people in other more established communities such as Java. Maybe this is because their project complexity is low, or maybe it's because they don't know how to do it. Whatever the reason, this book is written for the community. One of our goals is to teach you how you can write an application that solves your Domain issues without being coupled to specific frameworks or technologies.

Summary of Chapters

The book is arranged with each chapter exploring a separate tactical building block of Domain-Driven Design. It also includes an introduction to Domain-Driven Design, information on how to integrate different Bounded Contexts or applications, and an appendix.

Chapter 1: Getting Started with Domain-Driven Design

What is Domain-Driven Design about? What role does it play in complex systems? Is it worth learning about and exploring? What are the main concepts a developer needs to know when jumping into it?

Chapter 2: Architectural Styles

Bounded Contexts can be implemented in different ways and using different approaches. However, two styles are getting more popular, and they are Hexagonal Architecture and CQRS + ES. In this chapter, we'll see these two main Architectural Styles, understand what their main strengths are, and discover when to use them.

Chapter 3: Value Objects

Value Objects are the basic pieces for rich modeling. We'll learn what their properties are and what makes them so important. We'll figure out how to persist them using Doctrine and custom ORMs. We'll show how to properly validate and unit test them. And finally, we'll see what a test case of testing immutability looks like.

Chapter 4: Entities

Entities are Domain-Driven Design building blocks that are uniquely identified and mutable. We'll see how to create and validate them and how to properly map them using a custom ORM and Doctrine. We'll also assess whether or not annotations are the best mapping approach for Entities and look at the different strategies for generating an Identity.

Chapter 5: Domain Services

In this chapter, you'll learn about what a Domain Service is and when to use it. We'll review what Anemic Domain Models and Rich Domain Models are. Lastly, we'll deal with Infrastructure issues when writing Domain Services.

Chapter 6: Domain-Events

Domain Events are a great Inversion of Control (IoC) mechanism. In Domain-Driven Design, they're important for communicating different Bounded Contexts asynchronously, improving your Application performance using eventual consistency, and decoupling your Application from its Infrastructure.

Chapter 7: Modules

With so many tactical building blocks, it's a bit difficult to know where to place them in code, especially if you're dealing with a framework like Symfony. We'll review how PHP namespaces can be used for implementing Modules. We'll also discover different hierarchies of folders for organizing Domain Model code, Application Code, and Infrastructure Code.

Chapter 8: Aggregates

Aggregates are probably the most difficult part of tactical Domain-Driven Design. We'll look at the key concepts when dealing with them and discover how to design them. We'll also propose a practical scenario where two Aggregates become one when adding a business rule, and we'll demonstrate how the rest of the objects must be refactored.

Chapter 9: Factories

Factory Methods and objects help us keep business invariants, which is why they're so important in Domain-Driven Design. Here, we'll also explore the relationship between Factories and Aggregates.

Chapter 10: Repositories

Repositories are key for retrieving and adding Entities and Aggregates to collections. We'll review the different types of Repositories and learn how to implement them using Doctrine, custom ORMs, and Redis.

Chapter 11: Application

An Application is the thin layer that connects outside clients to your Domain. In this chapter, we'll show you how to write your Application Services so that they're easy to test and keep thin. We'll also review how to prepare request objects, define dependencies, and return results.

Chapter 12: Integrating Bounded Contexts

We'll explore the different tactical approaches to communicate Bounded Contexts and see real implementations. REST is our suggestion for synchronous communication, and messaging with RabbitMQ is our suggestion for asynchronous communication.

Appendix: Hexagonal Architecture with PHP

Here is where you'll find the original article written by Carlos and published by php[architect] in June 2014.

Code and Examples

The authors have created an organization at GitHub called Domain-Driven Design in PHP, which is where all the code examples from this book, additional snippets, and some complete sample projects are available. For example, you can find Last Wishes, a simple Domain-Driven Design-style application showing different examples explained in this book. Additionally, you'll find our CQRS Blog, along with Gamify, a Bounded Context that adds gamification capabilities to Last Wishes.

Finally, if you find any issue or fix or have a suggestion or comment while reading this book, you can create an issue in the DDD in PHP Book Issues repository. We fix them as they come in. If you're interested, we also urge you to watch our projects and provide feedback.

Getting Started with Domain-Driven Design

So what is all the fuss about? If you've already read books on this topic by Vaughn Vernon and Eric Evans, you're probably familiar with what we're about to say, as we borrow heavily from their definitions and explanations. Domain-Driven Design (DDD), is an approach that helps us succeed in understanding and building software model designs. It provides us with strategic and tactical modeling tools to aid designing high-quality software that meets our business goals.

The main goal of this book is to show you PHP code examples of the Domain-Driven Design tactical patterns. If you want to learn more about the strategic patterns and the main Domain-Driven Design, you should read Domain Driven Design Distilled by Vaughn Vernon or Domain-Driven Design Reference: Definitions and Pattern Summaries by Eric Evans.

More importantly, Domain-Driven Design is not about technology. Instead, it's about developing knowledge around business and using technology to provide value. Only once you're capable of understanding the business your company works within will you be able to participate in the software model discovery process to produce a Ubiquitous Language.

Why Domain-Driven Design Matters

Software is not just about code. If you think about it, code is rarely the end goal of our profession. Code is just the medium to solve business problems. So why does it have to talk a different language? Domain-Driven Design emphasizes making sure businesses and software speak the same language. Once broken the barrier, there is no need for translations or tedious syncing, information doesn't get lost. Everyone contributes to discovering the Business Domain, not just coders. The resulting software is the only truth for the common language.

Domain-Driven Design it also provides a framework for strategic and tactical design — strategic to pinpoint the most important areas to develop based on business value, and tactical to build a working Domain Model of battle-tested building blocks and patterns.

The Three Pillars of Domain-Driven Design

Domain-Driven Design is an approach for delivering software, and it's focused on three pillars:

Ubiquitous Language

: Domain Experts and software developers work together to build a common language for the business areas being developed. There's no

us versus them

; it's always

us

. Developing software is a business investment and not just a cost. The effort involved in building the Ubiquitous Language helps spread deep Domain insight among all team members.

Strategic Design

: Domain-Driven Design addresses the strategy behind the direction of the business and not just the technical aspects. It helps define the internal relationships and early warning feedback systems. On the technical side, strategic design protects each business service by providing the motivation for how an service-oriented architecture should be achieved.

Tactical Design

: Domain-Driven Design provides the tools and the building blocks for iterative software deliverable. Tactical design tools produce software that is not only correct, but that is also testable and less error prone.

Ubiquitous Language

Along with  Chapter 12, Integrating Bounded Contexts, Ubiquitous Language is one of the main strengths of Domain-Driven Design.

In Terms of Context For now, consider that a Bounded Context is a conceptual boundary around a system. The Ubiquitous Language inside a boundary has a specific contextual meaning. Concepts outside of this context can have different meanings.

So, how to find, explore and capture this very special language, the following pointers would highlight the same:

Identify key business processes, their inputs, and their outputs

Create a glossary of terms and definitions

Capture important software concepts with some kind of documentation

Share and expand upon the collected knowledge with the rest of the team (Developers and Domain Experts)

Since Domain-Driven Design was born, new techniques for improving the process of building the Ubiquitous Language have emerged. The most important one, which is used regularly now, is Event Storming.

Event Storming

Alberto Brandolini explains Event Storming and its advantages in a blog post, and he does it far more succinctly than we could.Event Storming is a workshop format for quickly exploring complex business domains:

It is

powerful

: It has allowed me and many practitioners to come up with a comprehensive model of a complete business flow in hours instead of weeks.

It is

engaging

: The whole idea is to bring people with the questions and people who know the answer in the same room and to build a model together.

It is

efficient

: The resulting model is perfectly aligned with a Domain-Driven Design implementation style (particularly fitting an Event Sourcing approach), and allows for a quick determination of Context and Aggregate boundaries.

It is

easy

: The notation is ultra-simple. No complex UML that might cut off participants from the heart of the discussion.

It is

fun

: I always had a great time leading the workshops, people are energized and deliver more than they expected. The right questions arise, and the atmosphere is the right one.

If you want to know more about Event Storming, check out Brandolini's book, Introducing EventStorming.

Considering Domain-Driven Design

Domain-Driven Design is not a silver bullet; as with everything in software, it depends on the context. As a rule of thumb, use it to simplify your Domain, but never to add more complexity.

If your application is data-centric and your use cases mainly manipulate rows in a database and perform CRUD operations — that is, Create, Read, Update, and Delete — you don't need Domain-Driven Design. Instead, the only thing your company needs is a fancy face in front of your database.

If your application has less than 30 use cases, it might be simpler to use a framework like Symfony or Laravel to handle your business logic.

However, if your application has more than 30 use cases, your system may be moving toward the dreaded Big Ball of Mud. If you know for sure your system will grow in complexity, you should consider using Domain-Driven Design to fight that complexity.

If you know your application is going to grow and is likely to change often, Domain-Driven Design will definitely help in managing the complexity and refactoring your model over time.

If you don't understand the Domain you're working on because it's new and nobody has invested in a solution before, this might mean it's complex enough for you to start applying Domain-Driven Design. In this case, you'll need to work closely with Domain Experts to get the models right.

The Tricky Parts

Applying Domain-Driven Design is not easy. It requires time and effort to get around the Business Domain, terminology, research, and collaboration with Domain Experts rather than coding jargon. You'll need to have the commitment of Domain Experts for getting involved in the process too. This will requires an open and healthy continuous conversation to model their spoken language into software. On top of that, we'll have to make an effort to avoid thinking technically, to think seriously about the behavior of objects and the Ubiquitous Language first.

Strategical Overview

In order to provide a general overview of the strategical side of Domain-Driven Design, we'll use an approach from Jimmy Nilsson's book, Applying Domain-Driven Design and Patterns. Consider two different spaces: the problem space and the solution space.

In the problem space, Domain-Driven Design uses Domains and Subdomains to group and organize what companies want to solve. In the case of an Online Travel Agency (OTA), the problem is about dealing with things like flight tickets and booking hotels. Such a Domain can be organized into different Subdomains such as Pricing, Inventory, User Management, and so on.

In the solution space, Domain-Driven Design provides two patterns: Bounded Contexts and Context Maps. The goal is to define how to provide an implementation to all the identified Subdomains by defining their interactions and the details of those interactions. Continuing with the OTA example, each of the Subdomains will be solved with a Bounded Context implementation — for example, consider a custom Web Application developed by a team for the Pricing Management Subdomain, and an off-the-shelf solution for the User Management Subdomain. The Context Map will show how each Bounded Context is related to the rest. Inside the Context Map, we can see what type of relation two Bounded Contexts have (example: customer-supplier, partners). The ideal approach is to have each Subdomain implemented by one Bounded Context, but that's not always possible. In terms of implementation, when following Domain-Driven Design, you'll end up with distributed architectures. As you may already know, distributed architectures are more complex than monolithic ones, so why is this approach interesting, especially for big and complex companies? Is it really worth it? Well, it is.

Distributed architectures are proven to increase overall company productivity because they define boundaries for your product that can be developed by focused teams.

If your Domain — the problem you need to solve  — is not complex, applying the strategical part of Domain-Driven Design can add unnecessary overhead and slow down your development speed.

If you want to know more about the strategical part of Domain-Driven Design, you should take a look at the first three chapters of Vaughn Vernon's book, Implementing Domain-Driven Design, or the book Domain-Driven Design: Tackling Complexity in the Heart of Software by Eric Evans, both of which specifically focus on this aspect.

Related Movements: Microservices and Self-Contained Systems

There are other movements promoting architectures that follow the same principles Domain-Driven Design is promoting. Microservices and Self-Contained Systems are good examples of this. James Lewis and Martin Fowler define Microservices in the Microservices Resource Guide:

The Microservice architectural style is an approach to developing a single application as a suite of small services, each running in its own process and communicating with lightweight mechanisms, often an HTTP resource API. These services are built around business capabilities and are also independently deployable using fully automated machinery. There is a bare minimum of centralized management of these services, which may be written in different programming languages and also use different data storage technologies.

If you want to know more about Microservices, their guide is a good place to start.How is this related to Domain-Driven Design? As explained in Sam Newman's book, Building Microservices, Microservices are implementations of Domain-Driven Design Bounded Contexts.

In addition to Microservices, another related movement is Self-Contained Systems (SCS). According to the Self-Contained Systems website:

The Self-contained System approach is an architecture that focuses on a separation of the functionality into many independent systems, making the complete logical system a collaboration of many smaller software systems. This avoids the problem of large monoliths that grow constantly and eventually become unmaintainable. Over the past few years, we have seen its benefits in many mid-sized and large-scale projects. The idea is to break a large system apart into several smaller self-contained system, or SCSs, that follow certain rules.

The website also spells out seven characteristics of SCS:

Each SCS is an autonomous web application. For the SCS's domain all data, the logic to process that data and all code to render the web interface is contained within the SCS. An SCS can fulfill its primary use cases on its own, without having to rely on other systems being available.

Each SCS is owned by one team. This does not necessarily mean that only one team might change the code, but the owning team has the final say on what goes into the code base, for example by merging pull-requests.

Communication with other SCSs or 3rd party systems is asynchronous wherever possible. Specifically, other SCSs or external systems should not be accessed synchronously within the SCS's own request/response cycle. This decouples the systems, reduces the effects of failure, and thus supports autonomy. The goal is decoupling concerning time: An SCS should work even if other SCSs are temporarily offline. This can be achieved even if the communication on the technical level is synchronous, example by replicating data or buffering requests.

An SCS can have an optional service API. Because the SCS has its own web UI it can interact with the user — without going through a UI service. However, an API for mobile clients or for other SCSs might still be useful.

Each SCS must include data and logic. To really implement any meaningful features both are needed. An SCS should implement features by itself and must therefore include both.

An SCS should make its features usable to end-users by its own UI. Therefore the SCS should have no shared UI with other SCSs. SCSs might still have links to each other. However, asynchronous integration means that the SCS should still work even if the UI of another SCS is not available. To avoid tight coupling an SCS should share no business code with other SCSs. It might be fine to create a pull-request for an SCS or use common libraries, example: database drivers or oAuth clients.

Exercise Discuss the pros and cons of such distributed architectures with your workmates. Think about using different languages, deployment processes, infrastructure responsibilities, and so on.

Wrap-Up

During this chapter you've learned:

Domain-Driven Design is not about technology; it's actually about providing value in the field you're working in by focusing on the model. Everyone takes part in the process of discovering the Domain, and developers and Domain Experts team up to build the knowledge base by sharing the same language, the Ubiquitous Language.

Domain-Driven Design provides tactical and strategic modeling tools to design high-quality software. Strategic design targets the business direction, helps in defining the internal relationships, and technically protects each business service by defining strong boundaries. Tactical design provides useful building blocks for iterative design.

Domain-Driven Design only makes sense in certain contexts. It's not a silver bullet for every problem in software, so whether or not you use it highly depends on the amount of complexity you're dealing with.

Domain-Driven Design is a long-term investment; it requires active effort. Domain Experts will be required to collaborate closely with developers, and developers will have to think in terms of the business. In the end, the business customer is the one who has to be pleased.