Mars Rover, Introduction 15/06/2016
Welcome to this Mars Rover series where we're going to practice the followings:
- Monolithic Repositories (MonoRepo)
- Command / Query Responsibility Segregation (CQRS)
- Event Sourcing (ES)
- Test Driven Development (TDD)
In this introductory article, we're simply going to describe our Mars Rover specifications.
Note: This programming exercise originally comes from Dallas Hack Club, which is now unfortunately down.
This Mars Rover kata has been adapted for the needs of this series.
But first, let's have a quick reminder on what the practices mentioned above are.
Monolithic Repositories
A MonoRepo is a single versioning repository containing many packages that would otherwise be versioned in their own repositories.
With it, everything can be found in one place, which makes it easy to:
- navigate
- manage dependencies
- set up
- run tests
However it also brings the following disadvantages:
- no hard separation between packages (thigh coupling is possible)
- limited regarding scaling (disk space, bandwidth)
- no finely grain permission management (a user has access to everything or nothing)
MonoRepos make sense for projects that would be packaged / released together (although it makes it possible to package / release them independently).
Note: Here are some references about MonoRepos:
Command / Query Responsibility Segregation
CQRS is about separating "write" logic from "read" logic, and it can be applied on many levels, for example:
- have a read-only microservice and a separate write microservice
- have endpoints / tasks that are either write or read only
- separate your models in two (again, read-only and write-only)
It's important to note that CQRS can also be applied partially in the same project: use it only when it makes sense.
Note: Here are some references about CQRS:
Event Sourcing
With ES, every significant action is recorded as an "event". Keeping track of those events provides the following advantages:
- replay them to recreate the state of an application at a given time (undo, redo, synchronization)
- analyse how the latest state came to be (compare two versions or find who did what and when)
Just like with CQRS, it's important to note that ES can also be applied partially inside a project : use it only when it makes sense.
ES is often associated to CQRS, but they can be used separately.
Note: Here are some references about ES:
Test Driven Development
TDD can be summed up in the following steps when developing:
- create a test
- then write just enough code to make the test pass (quick and dirty, or "make it work")
- then refactor the code (clean, or "make it right")
Writing the test before the code forces us to think about how we'd like the future code to be used. It's like writing specifications, but with 3 purposes: design, documentation and automated regression checking.
This discipline makes it easy to have a high code coverage (although rigour still needs to be applied: we need to test all the happy paths and all the unhappy ones).
Note: Here are some references about TDD:
Specifications
The purpose of this series is to create the software of a Mars Rover, according to the following specifications.
Mars Rovers need first to be landed at a given position. A position is composed
of coordinates (x
and y
, which are both integers) and an orientation
(a string being one of north
, east
, west
or south
).
It is then possible to drive them, using instructions such as move_forward
(keeps orientation, but moves along the x
or y
axis) or
turn_left
/ turn_right
(keeps the same coordinates, but changes the
orientation).
From time to time, they'll be requested to give their current location
(again, x
and y
coordinates and the orientation).
For example, a rover can be landed at 23
, 42
, north
and then can be
instructed to move forward twice, then to turn left, then to move forward once.
When requested to, it should provide this location: 22
, 44
, west
.
Identifying use cases
From the above specifications, we can identify at least three use cases:
- Landing a Rover on Mars
- Driving the rover
- Requesting its location
What's next
In the next article we'll initialize the project by creating the MonoRepo and
its first package: navigation
.
Note We'll be using:
- PHP 7
- Composer
- git
- phpspec and its SpecGen extension