Scala in practice: Composing Traits – Lego style

As a kid, i loved to play with Lego bricks, especially to build freaky spacecrafts.

spacecraftAt that time it was easy to let my phantasy go (where noone has gone before) and build completely new models simply by composing some standard bricks. Those bricks weren’t too specialized, meaning that there weren’t too many constraints on how to combine them. On the other side you always had to compose a new spacecraft from the very ground up as there weren’t some more higher organized units like engines or control cabins.

Nowadays, you’ll find such units. There are engines, control cabins or a whole commando bridge, Wings, Field Generators and so on – a whole set of higher organized units whithin a single domain. On the other side, you can’t combine every unit with an arbitrary other unit within that domain since there are some ‘constraints’  that will prohibit some unsound combinations.

Now you may ask how that cute childhood story relates to Scala?
You may have seen already some similarities to the field of software development where you also want to compose some higher organized building blocks within a certain domain, enforcing that they are only combined in a proper way. It turns out, that Scala’s concept of traits provide some mechanisms of ‘mixin’ them together while enforcing the compliance of some constraints. This may sound too abstract at that point, but hold on – we’ll build some spacecrafts in the above mentioned way and things will get clearer.

Look, it’s a spacecraft

Let’s start with a hull for our spacecraft. To keep things simple and to focus on the core idea of constrained
composition, the spacecraft’s hull will only provide one abstract method engange to start the craft:

abstract class Spacecraft{

    def engage
}

As you can see, method engage and therefore the whole class is abstract, so you can’t instantiate a pure hull
of a spacecaft. So whenever we want to build a full fledged craft, we may have to ‘add’ (or mix in) a component
that knows how to engage that craft.

Captains place

Typically, a spacecraft possess a kind of ‘control center’ which is normally well suited for initiating the
start of a craft, hence should provide an implementation for method engage. There may be different kinds of
control centers that could be used for building your own, customized spacecraft – e.g. a whole commando bridge for
those big deep space crafts or a small control cabin for those little crafts mainly maneuvering near the orbit.

 trait CommandoBridge{

def engage { for( _ <- 1 to 3 ){ speedUp } }

    def speedUp
}

Now we see what it means to engage (a Spacecraft) if composing a commando Bridge to the hull. We simply speed up that craft 3 times.
But hold on – although we know what it means to engage that craft, speeding up that craft is not in the responsibility of the commando bridge, since speedUp is left abstract (speeding down is omitted since it follows the same mechanism – you get the idea).

Re-calibrating all Dilithium crystals

So the spacecraft seems to be incomplete without a unit to speed it up – let’s call such a unit ‘engine’.  Again, there may be different kinds of engines we could select from to assemble our craft.
Let’s say there is a Pulse-Engine that directly supports the command of speeding up:

trait PulseEngine{

    val maxPulse: Int

    var currentPulse = 0;

    def speedUp { if( currentPulse < maxPulse ) currentPulse += 1  }
}

As you can see, a PulseEngine is able to speed up until a maximum pulse rate. In order to ‘produce’ different pulse engines (supporting different maximum pulse rates for different types of crafts), the field is again left abstract.
Now we could create our first spacecraft, using a commando bridge and a pulse engine (let’s say that’s all you need for building a full fledged spacecraft).

class StarCruiser extends Spacecraft with CommandoBridge with PulseEngine{

    val maxPulse = 200
}

As you can see, we’ve created a new (Sub-)Type of a spacecraft and mixed in both Traits, obtaining a commando bridge (that knows how to engage the whole craft) and an engine (that knows how to get the craft into speed when engaging the craft).
The only thing left is to define the maximum pulse rate our StarCruiser is able to achieve.

Wiring

In the above case, all units fitted together smoothly. For example, a pulse engine provided exactly the ‘interface’ (speedUp) that was needed by a commando bridge, so you could compose both without additional work. Let’s take a look at another control center, that we could apply to our craft, that may offer an incompatible ‘interface’ :

trait ControlCabin{

    def engage = increaseSpeed

    def increaseSpeed
}

This time we need to do some additional wiring, if we want to compose a new type of craft using a control cabin and a pulse engine, since both units don’t fit together directly (the dependency needed by ControlCabin (increaseSpeed) isn’t directly fulfilled by PulseEngine)

class Shuttle extends Spacecraft with ControlCabin with PulseEngine{

    val maxPulse = 10

    def increaseSpeed = speedUp
}

As you can see, we have to wire together the control cabin with the pulse engine in order to let them cooperate.
In the same way, we could think of another kind of engine which offers a completely different ‘interface’:

trait WarpEngine extends Engine{

    val maxWarp: Int

    var currentWarp = 0;

    def toWarp( x: Int ) { if( x < maxWarp ) currentWarp = x }
}

Again, we need to wire together the concrete control center with the WarpEngine, depending on their incompatible ‘interfaces’.

Let’s compose a craft, using a commando bridge and a warp engine.
Firstly, we are forced to define a maximum warp level, since it’s an abstract field of WarpEngine. Secondly we have to wire together the commando bridge with the warp engine, that is to ‘route’ the commando bridge’s method speedUp to the warp engines ‘interface’ toWarp with an appropriate implementation:

class Explorer extends Spacecraft with CommandoBridge with WarpEngine{

    val maxWarp = 10

    def speedUp = toWarp( currentWarp + 1 )
}

Alternatively, we could also use a simple control cabin for another type of spacecraft. Again we have to link the contol cabins commands (increaseSpeed) to the warp engines ‘interface’:

object Defiant extends Spacecraft with ControlCabin with WarpEngine{

    val maxWarp = 20 // claimed by WarpEngine

    def increaseSpeed = toWarp( 10 ) // claimed by ControlCabin
}

Restricted Access

Until now, we only applied a control center or engines to spacecrafts. But nothing would restrict us to use those units in other domains so far. Say we want to build a certain airplane and apply a warp engine.

class Jet extends Airplane with WarpEngine{

    val maxWarp = 5
}

It’s propably not the best idea to equip a Jet with a warp engine, since this seems to be a bit oversized for an airplane. We need a way to restrict the usage of warp engines – they should be only applied to spacecrafts. Fortunately we can express this kind of constraint, using Scala’s self type annotation. Included within a trait, it’s like saying ‘this trait is only allowed to be mixed into a type of x‘ (in our case ‘Spacecraft‘):

trait WarpEngine extends Engine{

    this: Spacecraft =>
    ...
}

As you can see, we used the WarpEngines self type to restrict its appliance only to spacecrafts. In all other cases, Scala’s compiler will complain about an unsound mixin.

What makes a spacecraft a spacecaft ?

With selftypes, we now have an instrument to restrict the usage of a trait to be mixed in only to a certain Type.
On the other side, we aren’t forced to use a control center or an engine at all if creating a new spacecraft, since we could provide an implementation of the spacecrafts abstract methods directly within a subtype. That may be fine in some cases, but what if we want to state that a spacecraft has to be composed of at least a certain type of control center and a certain type of engine? Again, we can use the service of the self type annotation, this time applied to our abstract class spacecraft, stating that a spacecraft should at least be compound of a control center and an engine:

abstract class Spacecraft{

    this: ControlCenter with Engine =>
    ...
}

The only thing left is to provide an appropriate type ControlCenter resp. Engine and the correct classification of those concrete units (e.g. ‘CommandoBridge is a ControlCenter‘)

 trait ControlCenter

 trait CommandoBridge extends ControlCenter{ ... }

 trait ControlCabin extends ControlCenter{ ... }

 trait Engine

 trait PulseEngine extends Engine{ ... }

 trait WarpEngine extends Engine{ ... }

Summary

Abstract methods and self type annotations are two powerful tools which help to guide or constrain the composition of traits.
You may use abstract methods and abstract fields to enforce a kind of ‘wiring’ between multiple units or at least to force the definition of some concrete information.
You may use a self type annotation to restrict the appliance of a trait, so that it can only be mixed in to a certain type (or subtypes). On the other side, you’re able to enforce that a certain trait (or subtype) have to be mixed in to a certain type, again by using a self type annotation.
In all cases, the ‘composer’ of those units will be guided by the compiler – you can’t forget to give a definition for an abstract method or arrange an unsound composition, since all those ‘constraints’ are based on Scala’s statically typed Type system.

Talking about Domain Driven Design at XPUG Rhein/Main

I will talk about Domain Driven Design (DDD) at the Extreme Programming User Group Rhein/Main (in Frankfurt / Germany) on April 8, 2009.

We’ll take a closer look at the core intentions and ideas behind DDD (like grinding a Ubiquitous Language, Deep Models, Declarative Design or bounded Contexts),  surrounded by some real world examples.

Come along and feel welcome if you want to know more on what it’s all about ‘DDD’ and want to discuss about afterwards.

Just give me a note at mario.gleichmann@mg-informatik.de if you’re interested to attend and i’m up for sharing further contact / meeting infos with you (talk will be in german).

DAO – it’s not about Layering, it’s about Abstraction!

Again there were some interesting debates in the near past, which once again discussed the role of the DAO within enterprise applications, especially based on JEE and EJB 3. One main argument for the dissapearance of DAOs is the very unlikely probability to exchange or replace your once chosen persistence technology, so that you may directly rely on EJBs Entity Manager within your Business Services (since it’s in fact very unlikely that your underlying persistence technology will change). This argument is mostly accompanied with the concern, that the introduction of a DAO Layer might increase complexity and introduce some performance penalties, while direct usage of the Entity Manager let collapse two separate Layers into one. Read the rest of this entry »

Posted in design. 4 Comments »

Refining Uncle Bob’s Clean Code

I’ve just finished reading ‘Uncle Bob’s’ new book ‘Clean Code‘. I fully agree with most of the statements and it was a pleasure to read, especially because Uncle Bob and his co-authors have a talent for putting some of the most relevant values and principles of software development into so simple words (i wished they have crossed my mind within more than one discussion in the past). Read the rest of this entry »

Did you really get Behaviour Driven Development?

You maybe have noticed some new articles and product announcements recently, that turn themself in the ‘tradition’ of Behaviour Driven Development (BDD).
Most of them mainly concentrate on the introduction of a new vocabulary in order to get rid of the test centric terminology. Some of them even suggest to stick with the well known xUnit test frameworks and mainly kind of change their test method names (if only they contain the now famous word ‘should’) and think they’re done … really? Read the rest of this entry »

Test Driven Development and Design By Contract – friend or foe?

in this post i’ll try to answer a legitimate question, relating to a comment due to my last statement that interfaces are poor contracts: why do we need contracts (in the sense of invariants, pre- and postconditions) when we’ve got unit tests right at hand, that could also test the stated conditions?

in fact, it’s very tempting to see unit tests as an all-embracing instrument to check and show that a class will behave correctly, making contracts kind of unnecessary.
i’ll try to show you that unit tests (as an instrument for test driven development) and contracts (as an instrument for Design By Contract) indeed share the same goals but aren’t competing techniques, rather than methods that could complement each other. Read the rest of this entry »