Have you ever seen this development cycle?

  1. Install new build
  2. App doesn’t start, doesn’t log any error why
  3. Go back to source code and add improved logging
  4. Install new build
  5. Read logs
  6. Fix the actual problem (usually some stupid configuration thing)
  7. Repeat steps 1-6 until all bugs are gone

Was it because of your code, or someone else’s? This sort of cycle is time consuming, frustrating, stressful, and makes you look helpless (or like a cowboy) in front of project managers and support staff.

If your app can’t produce logs your infrastructure staff can understand, then your app is not even close to production-readiness. If it doesn’t log clear errors, how can anyone hope to deploy and support it?

August 20th, 2010 | No Comments Yet

On Friday I attended DDD eXchange 2010, a one-day software conference here in London on Domain Driven Design. This years conference focused on two themes — architectural innovation and process — and I saw talks by Eric Evans, Udi Dahan, Greg Young, Ian Cooper and Gojko Azdic discussing their various aspects. Here are some of my highlights.

The difference between a Domain and a Domain Model

Eric Evan led the keynote focusing on definitions of many of the original terms that get mixed from the blue DDD book. In particular, he clarified the difference between the domain and the domain model:

  • Domain — the business. How people actually do things.
  • Domain Model — a useful abstraction of the business, modelled in code.

One is fixed (only the business can change it), the other is flexible. It sounds really obvious, but often the terms are used interchangibly and things get messy. Most notably:

  • DDD systems never have a domain layer — they have a domain model. Go and rename your Domain namespace to DomainModel right now.
  • Ubiquitous language is created to describe the domain model — it is not just blindly dictated from the existing domain. Mark Gibaud summarized this succinctly in a tweet:

Both of these are things I have been vocal about in the past.

The difference between a Sub-Domain and a Bounded Context

Following on from the previous point, another tricky one — a subdomain is a sub-part of the business (e.g. in a banking domain, a subdomain might be loans), where bounded contexts are more concerned with things like linguistic boundaries. They are easiest to spot when two business experts use the same words to refer to different concepts.

Likewise, a generic subdomain is not a reusable code library/service (like Google Maps) — it is an area of the business with no special differentiation. Compare this versus the core domain, where the business derives its competitive advantage through differentiating itself from the market.

CQRS

Much of the morning was spent discussing Command Query Responsibility Segregation (CQRS), Event Sourcing, persistent view models, and all that entails. If you’ve kept up with Greg and Udi’s recent talks (here and here), you didn’t miss anything.

In a paper-based system…

Greg mentioned a useful tool he sometimes uses when identifying roles and events in a business system: imagine how the business would operate if it were completely free of computers.

How did they stay afloat sixty years ago when people went home sick? Records got lost, or contained mistakes? Are there any old employees around you can talk to who still remember? The answers to these questions may provide insight into how the domain should be modelled.

This also led into an interesting discussion about how the rise of the multi-user RDBMS has led businesses to expect their software to be 100% consistent (even though their business processes never historically were, before they got computers), and how difficult it is nowdays to convince businesses to embrace scary prospects like eventually-consistency and the possibility of stale data.

Aggregates synchronize through events, not method calls

Ian Cooper mentioned this briefly in his session on implementing DDD on a large insurance company project. Basically, an aggregate must never call a method on another aggregate — doing so would violate each of their consistency boundaries. Instead, an interaction like this should be modelled as a domain event, with a separate handler coordinating its own consistency boundary (e.g. a transaction) for the second aggregate.

Final thoughts

Overall I had a fantastic time, and I highly recommend anyone to attend next year. Props to the Skills Matter staff and Eric for running such a great event!

You can check out videos of all the sessions here.

Photo credits: Skills Matter DDD eXchange 2010 Flickr set

June 15th, 2010 | 2 Comments

Last week, I bought my first new development machine in three years, and it’s a beast.

Early on I decided I wanted a laptop over a big desktop PC. Although laptops are usually more expensive, slower, have smaller screens, and fiddly keyboards, mobility is really important for me — I am planning to be working/travelling around Europe for forseeable future, and lugging a huge desktop everywhere isn’t really feasible. I want to travel light. But also it needs to be powerful enough to run all the heavy developer tools (Visual Studio, VMWare, SQL Server, Photoshop etc) I use every day.

Laptop – i7 MacBook Pro

My last laptop was a Mac (a Powerbook G4), and I was very happy with it — it lasted for five years before I moved to London and saw me through university, two jobs, three flats, and is basically where I learnt to program. So it should not be a surprise that last week, after months of waiting, I finally spec’d out a brand new 15″ i7 MacBook Pro from the Apple online store.

Why a Mac, when I’m primarily a .NET developer? Really, it comes down to these simple reasons:

  1. In my opinion, MacBook Pros are, and always have been the best looking laptops on the market.
  2. They are fast (although still only dual-core).
  3. The build quality of Apple laptops is very high, and it will probably last a long time.
  4. It can happily run Windows.

Going with a MacBook Pro was pretty much a no brainer as far as I’m concerned. But that’s not the end of the story — there’s a lot more to see under the hood.

Solid State Disk (SSD) – 200GB OCZ Vertex LE

It’s long been known that SSDs are fantastic for developers — their ultra-low seek times and small read/write latency can make them several times faster at compiling code than their spinning counterparts. Not to mention it’ll make your PC boot in about ten seconds.

Now SSDs have been available with Macs for some time, but the Toshiba drives used aren’t known for their performance. For a long time I was planning to get an Intel X-25M instead — the long-standing value/performance king of the SSD market. That is, until I saw the absurdly-fast OCZ Vertex 2 Pro.

This thing eats all other SSDs alive. But sadly you will never be able to buy one, because a few months after this review, the entire Vertex 2 Pro product line was cancelled. It seems the cost of the super fast enterprise-grade Sandforce SF-1500 controller was not feasible for OCZ’s desired price range, so they canned it.

However, a small number (only 5,000 units) of SF-1500-based drives were made available to customers as the OCZ Vertex Limited Edition (LE), probably from some early shipment. And according to Anand’s benchmarks, they are actually even faster than the Vertex 2 Pro. So naturally, I had to get one.

The difference is astounding. Here’s a comparison of my XBench results, before and after the upgrade (Seagate Momentus 7200RPM vs OCZ Vertex LE, click for full results):

As you can see, random small (4K) reads and writes is where it really shines — no more waiting for spinning magnetic platters for me!

Memory – 8GB Apple

Historically, Apple’s RAM upgrades have always been notoriously expensive — it’s almost always cheaper to buy/install it yourself. Strangely at the moment, however, Apple’s prices aren’t too bad, so I decided to configure it with 8GB installed — partly for convenience, and partly to ensure my RAM sticks are matched (same specs/manufacturer).

Screen – 15″ Hi Res, Glossy LCD

I have to admit this decision was based entirely on aesthetics — the matte screen is easier to read, particularly in bright sunlight, but that silver bezel is so 2004 :)

The hi res screen is glorious too, but you will want to increase your font size a bit when coding (I always use 14 pt).

Operating System – dual boot Mac OS X/Windows 7 Professional

Although I love Mac OS X, .NET is my game, so I’ll probably be spending most of my time in Windows. This is my first Intel Mac (hey, it’s been a while…) so I’m quite new to the whole Bootcamp/Parallels/VMWare thing, but at this stage VMWare Fusion looks pretty good – being able to run my Bootcamp partition as a VM under Mac OS X seems like a nice solution.

Moshi Palmguard

I got a Moshi Palmguard because of my last Mac – a G4 Powerbook which suffered from ugly aluminum corrosion and pitting on the palm rests. Apparently aluminium pitting is still a problem for Macs today, so I wanted something to help protect it.

My Moshi Palmguard looks fantastic, and was dead easy to stick on — I found it easiest to align it with the cut-out at the bottom of the the track pad (where you open the lid). Just make sure there isn’t any dust or crumbs on the palm rests before sticking it on — you can’t reapply it once it’s attached. Also, I didn’t bother with the trackpad guard — the trackpad on a MacBook Pro is plastic, not metal, so it won’t corrode, and my Powerbook’s still looked fine after five years, so I didn’t see much point.

So that’s it — my proud new developer machine!

Final specs:

  • 15″ MacBook Pro
  • MBP 15″ HR Glossy WS Display (upgraded from standard res)
  • Intel Core i7 M620 dual core 2.66GHz CPU
  • 8GB 1066MHz DDR3 RAM (upgraded from 4GB)
  • 200GB OCZ Vertex LE SSD SF-1500 (upgraded from 500GB 7200RPM Seagate Momentus)
  • SuperDrive 8X DVDRW/CDRW
May 29th, 2010 | 4 Comments

Lately, I’ve seen a disturbing misconception about DDD crop up a couple of times in online and offline discussions. Here it is:

Ubiquitous language is sourced exclusively from the business. The developer side has no input, and must adopt whatever vocabulary they are given.

This is only true in situations where your project team is a Conformist to some upstream model. For example, if you’re developing an XML library, it’s probably best to stick to standard terms like Element and Attribute, than start inventing your own names for things.

In all other situations, however, you have more say. For example, if you’re developing a standalone business app from scratch, and a domain expert suggests a name for something that you think doesn’t quite fit, suggest a better one. Refining the ubiquitous language into a suitable abstraction is a team effort involving both developers and domain experts, and more often than not it flows back into the business as staff start to use the system. So it had better make sense!

April 18th, 2010 | 1 Comment

If you’re a new developer, one term you’ll hear used a lot is state. I remember I struggled with the idea at first, so I thought I’d write a brief introduction to the concept of state, and how it is applied to a few design and testing principles.

What is state?

Let’s use me as an example. Here are three facts that describe my current state:

  • My name is Richard.
  • I’m 23 years old.
  • I just ate some of my flatmate’s pancakes for lunch (wohoo!).
  • I’m in a pretty good mood.

In code, you might represent this as:

public class Person
{
    public string Name;
    public int Age;
    public Activity CurrentActivity;
    public bool IsHungry;
    public MoodType Mood;
}

These fields comprise my state. Some are unlikely to change (my name, for instance) while others are much more volatile (I will be hungry again in a few hours).

So you can see state changes over time. For example, my state right now is totally different than my state after 40 hours of nonstop travel from London from New Zealand — I arrived tired, and pretty frazzled. Both these states are different again than when I’m asleep.

State can be recorded, persisted (e.g. saved to a Person table in a RDBMS) and tracked over time. Usually, though, we’re only interested in the current state.

So state is just data, right?

Well… yes and no. When persisted, state becomes data, and in an object, state represents the data portion. Remember object-oriented programming combines behaviour (methods) with data (state).

But at a higher level, state represents the overall picture of an object right now, how it will behave, and what range of actions are available. A good example of this is the State Pattern from the GoF book. In their example, a TCP network connection has different states: established, closed, or listening for an incoming connection. These states are each encapsulated into an object, assigned to a field and the TCPConnection delegates behaviour to the current state:

So you can see in examples like this, state is more than just data — it affects behaviour too.

Unit testing state vs unit testing behaviour

This is something you might hear in the context of TDD and BDD. In short, testing on state means looking at an object’s visible state after something happened, and checking that all the values are correct.

bankingService.Transfer(chequeAccount, savingsAccount, 100.0);

// State-based assertions
Assert.AreEqual(0.0, cheque.Balance);
Assert.AreEqual(100.0, savings.Balance);

In comparison, testing on behaviour means using mocks to verify the expected methods are called.

bankingService.Transfer(chequeAccount, savingsAccount, 100.0);

// Behaviour-based assertions
chequeAccount.AssertWasCalled(account => account.Withdraw(100.0));
savingsAccount.AssertWasCalled(account => account.Deposit(100.0));

Generally behaviour-based testing is preferred, because:

  1. Focusing on behavioural seams (methods on interfaces) results in looser coupling, because the internal implementation of objects should change more often than the interfaces between them.
  2. The internal state of an object is private, and you shouldn’t be looking at it anyway — the basis of the Tell Don’t Ask principle.

Stateless services

An object’s state effects its behaviour. For example, when I eat, I feel full. If I eat too much, I feel sick — I can’t continue eating over and over.

Services, on the other hand, should be stateless. Imagine a dice-based random number generator. Every dice roll is a clean start — it should not retain any memory between rolls. To simplify usage and scale better, all service calls should be like this.

Another simpler example of unwanted state is services with methods like Initialize(), Start(), Connect(), Open() etc that must be called before other methods. Users of this service need to take responsibility for calling it and thus managing the lifecycle of the service — an unreasonable burden that introduces unnecessary coupling.

Explicit state transitions

One newer technique in domain-driven design is recognizing important state transitions, and making them explicit through the use of events. A simple example of this could be when your bank account balance goes below zero, its state becomes overdrawn:

public class Account
{
    public void Withdraw(Decimal amount)
    {
        balance -= amount;
        if (balance < 0)
            DomainEvents.Raise(new AccountBecameOverdrawn(this));
    }
}

This is an important state change — part of the business’s ubiquitous language that might have further implications down the line e.g. incurring overdraft fees. Udi Dahan writes a lot on this topic — it is a big help in decoupling your domain model, and is is the basis for event-sourcing CQRS.

So hopefully that starts to gives you an idea of what state is all about — more than just data!

March 29th, 2010 | 1 Comment