Slide 1

Slide 1 text

No content

Slide 2

Slide 2 text

TDD, DDD & Teamwork @jlammerts @pelshoff

Slide 3

Slide 3 text

Part I: TDD

Slide 4

Slide 4 text

What is a test?

Slide 5

Slide 5 text

Something shouldn’t happen ● Expect exception ● Do the thing

Slide 6

Slide 6 text

final class PresentationTest extends TestCase { /** * @test */ public function presentationsShouldHaveTitles(): void { $this->expectException(InvalidPresentation::class); new Presentation('', '', ''); } }

Slide 7

Slide 7 text

Something should happen ● Do the thing ● Expect result

Slide 8

Slide 8 text

final class PresentationTest extends TestCase { /** * @test */ public function presentationsShouldAllowNewSubtitles(): void { $actual = new Presentation('With', 'a', 'title'); $expectation = new Presentation('With', 'another', 'title'); $actual->changeSubtitleTo('another'); $this->assertEquals($expectation, $actual); } }

Slide 9

Slide 9 text

What is a good test?

Slide 10

Slide 10 text

A good test... ● Arrange ● Act ● Assert

Slide 11

Slide 11 text

A good test... ● Setup ● Expect ● Execute ● Verify

Slide 12

Slide 12 text

A good test... ● Setup ● Expect ● Perform ● Assert

Slide 13

Slide 13 text

A good test... ● Given ● When ● Then

Slide 14

Slide 14 text

What is TDD?

Slide 15

Slide 15 text

“Test-Driven Development (TDD) is a technique for building software that guides software development by writing tests.” - Martin Fowler

Slide 16

Slide 16 text

Three steps of TDD ● Red ● Green ● Refactor

Slide 17

Slide 17 text

What is the difference between test-first & TDD?

Slide 18

Slide 18 text

Recap ● Given, When, Then ● Red, Green, Refactor ● Client-first

Slide 19

Slide 19 text

Good luck and have fun!

Slide 20

Slide 20 text

Part II: Teamwork

Slide 21

Slide 21 text

The Attitude Model

Slide 22

Slide 22 text

Divergent

Slide 23

Slide 23 text

Convergent

Slide 24

Slide 24 text

Divergent Tend to be… ● Open ● Optimistic and curious ● Quick, sloppy and careless

Slide 25

Slide 25 text

Convergent Tend to be... ● Closed ● Pessimistic and inquisitive ● Paced, diligent and careful

Slide 26

Slide 26 text

The Double Design Diamond

Slide 27

Slide 27 text

No content

Slide 28

Slide 28 text

Good luck and have fun!

Slide 29

Slide 29 text

Part III: DDD

Slide 30

Slide 30 text

Value objects

Slide 31

Slide 31 text

final class Name { private $lastName; private $firstName; private $insertion; public function __construct(string $lastName, string $firstName, string $insertion) { $this->lastName = $lastName; $this->firstName = $firstName; $this->insertion = $insertion; $this->nameMustHaveLastName(); } private function nameMustHaveLastName(): void { if (!$this->lastName) { throw InvalidName::becauseLastNameIsMissing(); } } public function getLastName(): string { /**/ } public function getFirstName(): string { /**/ } public function getInsertion(): string { /**/ } }

Slide 32

Slide 32 text

final class EmailAddress { private $emailAddress; public function __construct(string $emailAddress) { $this->emailAddress = $emailAddress; $this->emailAddressMustBeAnActualEmailAddress(); } private function emailAddressMustBeAnActualEmailAddress(): void { if (!filter_var($this->emailAddress, FILTER_VALIDATE_EMAIL)) { throw InvalidEmailAddress::becauseThisIsNotAnEmailAddress(); } } public function asString(): string { return $this->emailAddress; } }

Slide 33

Slide 33 text

Value objects ● Express a value ● Define allowed values ● Are immutable ● Are easy to test

Slide 34

Slide 34 text

Entities

Slide 35

Slide 35 text

final class Attendee { private $id; private $name; private $emailAddress; public function __construct(Uuid $id, Name $name, EmailAddress $emailAddress) { $this->id = $id; $this->name = $name; $this->emailAddress = $emailAddress; } public function getId(): Uuid { /**/ } public function getName(): Name { /**/ } public function setName(Name $name): Attendee { /**/ } public function getEmailAddress(): EmailAddress { /**/ } public function setEmailAddress(EmailAddress $emailAddress): Attendee { $this->emailAddress = $emailAddress; return $this; } }

Slide 36

Slide 36 text

Entities ● Have identity ● Are more than their attributes ● Evolve over time ● Are slightly harder to test

Slide 37

Slide 37 text

Services

Slide 38

Slide 38 text

final class Registration { private $repository; public function __construct(AttendeeRepository $repository) { $this->repository = $repository; } public function registerNew(Attendee $attendee): void { $this->emailAddressMustBeUnique($attendee->getEmailAddress()); $this->repository->add($attendee); } private function emailAddressMustBeUnique(EmailAddress $emailAddress): void { try { $this->repository->findByEmailAddress($emailAddress); } catch (AttendeeNotFound $e) { return; } throw RegistrationFailed::becauseEmailAddressIsNotUnique(); } }

Slide 39

Slide 39 text

Services ● Have no identity or attributes (Are not a “thing”) ● Tackle cross-concern operations ● Are harder to test

Slide 40

Slide 40 text

Context Technische bouwblokken Quiz Case study I Case study II

Slide 41

Slide 41 text

class Address

Slide 42

Slide 42 text

class BicycleService

Slide 43

Slide 43 text

class StreetAddress

Slide 44

Slide 44 text

class Investment

Slide 45

Slide 45 text

Good luck and have fun!

Slide 46

Slide 46 text

The end! @jlammerts @pelshoff https://joind.in/event/php-yorkshire-2019/tdd-ddd--teamwork