Monthly Archives: August 2009

Advertising on this blog

If you are an Adblock Plus user like me it is very likely that you have not noticed that i added Google Ads to this blog a month or two ago. Given that the total earnings are less than 5$ i have decided to remove them.

Extension methods to improve readability

A common reason to take advantage of extension methods is to enhance readability (think fluent interfaces). My team uses the specification pattern regularly and in case a requirement says something like “if the player has reached level 10 a message should be displayed” they would implement it as:

if (new HasReachedLevel(10).IsSatisfiedBy(player))
{
 view.DisplayMessage("Congratulations! You have reached level 10.");
}

Pretty good but did you notice that they changed the order of player and level in their (code) story? With the aid of an extension method we can express this requirement as:

if (player.Satisfies(new HasReachedLevel(10)))
{
 view.DisplayMessage("Congratulations! You have reached level 10.");
}

Here is the extension method that allows you to express the requirement in this way:

public static bool Satisfies<t>(this T candidate, ISpecification<t> specification)
{
 return specification.IsSatisfiedBy(candidate);
}

About the implementation of a fluent interface

Now that i have defined my API for initialization it is time to implement it. Inspired by the Moq.Language and Moq.Language.Flow namespaces in Moq i have decided to define my interfaces in a separate namespace: Infrastructure.StateMachineLanguage.

Ever since i have read Clean code i feel the need to write classes that do one thing (and one thing only) so i came up with the following classes:

  • something to store commands per state, CommandsForState
  • something to store actions per command, ActionsForCommand

For the implementation of the IChooseCommandAndAction interface i have decided to create a class that falls back on my classes that handle IChooseCommand and IChooseAction already:

public class CommandAndActionForState<tstate, TCommand> : IChooseCommandAndAction<tstate, TCommand>
{
 private readonly CommandsForState<tstate, TCommand> commandsForState;
 private readonly ActionsForCommand<tstate, TCommand> actionsForCommand;

 public CommandAndActionForState(CommandsForState<tstate, TCommand> commands, ActionsForCommand<tstate, TCommand> actions)
 {
  commandsForState = commands;
  actionsForCommand = actions;
 }

 public IChooseAction<tstate, TCommand> On(TCommand command)
 {
  return commandsForState.On(command);
 }

 public IChooseCommandAndAction<tstate, TCommand> Do(Action action)
 {
  return actionsForCommand.Do(action);
 }
}


screenshot of files in statemachine solution.

As you can see, complex problems can have simple solutions. Feel free to download the complete solution: StateMachine.zip.

About the design of a fluent interface

Now that i have presented a simple ControlStateMachine i can raise the bar a little. A statemachine that handles commands. Here is how a developer should be able to initialize this machine:

sut.WhenIn(States.Loading)
 .On(Commands.Next)
  .Do(() => Console.WriteLine("got next command while loading..."))
  .Do(() => Console.WriteLine("doing it again..."))
 .On(Commands.Previous)
  .Do(() => Console.WriteLine("got previous command while loading..."));

sut.WhenIn(States.Ready)
 .On(Commands.Previous)
  .Do(() => Console.WriteLine("got previous command while ready..."));

So how should we define our methods to accomplish this initialization style? Let’s begin with identifying the methods we need.

  • WhenIn(TSTate state)
  • On(TCommand command)
  • Do(Action action)

Next thing to do is analyze in which sequence these methods can be called:

From -> To WhenIn On Do
WhenIn X
On X
Do X X

Ok, now that we have clarified the requirements a little we can start working on a solution. Let’s start with defining an interface for each of the methods:

interface IChooseState<tstate, TCommand> { Q1 WhenIn(TState state); }
interface IChooseCommand<tstate, TCommand> { Q2 On(TCommand command); }
interface IChooseAction<tstate, TCommand> { Q3 Do(Action action); }

From WhenIn we need to be able to call On. Thus Q1 = IChooseCommand<TState, TCommand>. Q2 is also easily solved because from On we only have to be able to call Do, thus Q2 = IChooseAction<TState, TCommand>.

From Do we should be able to call both On and Do. We can do that by defining another interface which has both methods:

interface IChooseCommandAndAction<tstate, TCommand> : IChooseCommand<tstate, TCommand>, IChooseAction<tstate, TCommand> { }

Now that we have found answers for Q1, Q2 and Q3 we can define the API for initializing our StateMachine as following:

IChooseCommand<tstate, TCommand> WhenIn(TState state);
IChooseAction<tstate, TCommand> On(TCommand command);
IChooseCommandAndAction<tstate, TCommand> Do(Action action);

Now tell me about your strategy for implementing a fluent interface!

Presenting ControlStateMachine

Here is a situation we are all familiar with: A form that only displays a certain set of controls depending on the mode or state of the application. Let me start with an example: At design time there are three buttons

screenshot of flowlayoutpanel with three buttons: edit, save and cancel.

The user can look at the data and decide to edit it:

screenshot of flowlayoutpanel with only one visible button: edit.

Or the user is editing the data and can decide to commit or discard her changes:

screenshot of flowlayoutpanel with two visible buttons: save and cancel.

A couple of years i ago i used to spread such display logic all over my code and it was hard to figure out which control was visible at a given point. Later on i refactored that code and encapsulated it in functions like: MakeControlsForDisplayVisible and MakeControlsForEditVisible which felt like a huge improvement. These days i have the feeling that a very simple state machine can improve the readability even better.

Ok, so how simple is simple? Currently the requirements list is pretty limited:

screenshot of unittests for controlstatemachine

Anyway, here is how i would write the code today (Yeah, for a stupid example this looks like overkill):

private void InitializeButtonLayoutPanelMachine()
{
 controlStateMachine = new ControlStateMachine<displayAndEditStates>(buttonLayoutPanel);

 controlStateMachine.WhenStateChangesTo(DisplayAndEditStates.Display)
  .TheOnlyVisibleControlsAre(buttonEdit);

 controlStateMachine.WhenStateChangesTo(DisplayAndEditStates.Edit)
  .TheOnlyVisibleControlsAre(buttonSave, buttonCancel);
}

As always, here is the source: ControlStateMachine and WhenChangingState.

Presenting ControlChanges

Because i noticed that i kept writing the same operations on control over and over again i decided to capture them in a couple of functions. I presume most of you have done this already. Here is the list of operations:

screenshot of a class diagram with the following operations: MakeVisible, MakeInvisible and TheOnlyVisibleControlsAre.

In case it is not clear what these methods should do i have defined the following specifications for them:

screenshot of requirements list for controlchanges.

Get the code here: ControlChanges and WhenExecutingControlChanges. Stay tuned for more!

Experimenting with ControlStateMachine and Fluent interfaces

A long time ago i read Build your own CAB series and recently i noticed that there is a wiki: Presentation Patterns Wiki! and it inspired me to experiment with state machines. Here are a couple of examples:

controlStateMachine = new ControlStateMachine<states>(this);

controlStateMachine.AfterEachStateChange()
 .Do(MakeRelevantButtonsVisible);

controlStateMachine.WhenStateChangesTo(States.RetrievingSubscriptionPeriod)
 .TheOnlyVisibleControlsAre(flowLayoutPanel1, datePicker1);

controlStateMachine.WhenStateChangesTo(States.RetrievingCustomerInformation)
 .MakeVisible(customerInput1)
 .Do(() => customerInput1.Dock = DockStyle.Fill);

controlStateMachine.WhenStateChangesTo(States.Ready)
 .MakeInvisible(customerInput1);

And here is another example:

wizardStateMachine = new WizardStateMachine<states>(controlStateMachine);

wizardStateMachine.InState(States.RetrievingSubscriptionPeriod)
 .OnCommand(WizardCommands.Next)
  .TransitionTo(States.RetrievingCustomerInformation);

wizardStateMachine.InState(States.RetrievingCustomerInformation)
 .OnCommand(WizardCommands.Back)
  .TransitionTo(States.RetrievingSubscriptionPeriod)
 .OnCommand(WizardCommands.Finish)
  .TransitionTo(States.Ready);

wizardStateMachine.InState(States.Ready)
 .OnCommand(WizardCommands.New)
  .Do(() => MessageBox.Show("Currently not supported"));

Stay tuned for future posts where i describe the problem space that have lead to this API.

About reading books

A while ago Gabriel wrote the following:

PS3: you can read all the books that you want, in the end to truly master .NET you need experience and more experience! Normally it would take you about 10 years of relevant experience to get to that level of expertise

I agree that expertise only comes from experience but i do believe that good books can guide you to the pit of success and help you recognize solutions that are doomed to fail.

Clean Code: A Handbook of Agile Software Craftsmanship

For my summer holidays i needed a book that was easy readable (size, weight, content) and Clean Code: A Handbook of Agile Software Craftsmanship was a perfect match for my reading sessions at the pool. Even better, i found inspiration to write cleaner (and thus better) code. This book is most certainly recommend!