Thursday, March 25, 2010

A Pattern to Reduce Erlang Complexity

Presented here is a recipe for reducing the complexity of a common programming pattern that is likely to appear in Erlang source code.  The solution pattern presented here is similar to the functional programming idiom known as "The Error Monad" whereby a series of function calls may or may not return an error.

Example Problem

withdraw_money(AccountNumber, Password, Amount) ->
  case account:find(AccountNumber) of
{ok, Account} ->
     case security:check_password(Password, Account) of
ok ->
        case dispenser:available_cash() < Amount of
true ->
           case account:withdraw(Amount) of
ok ->
              case dispenser:spit_out_cash(Amount) of
ok ->
                 ok;
DispenserError ->
                 DispenserError
              end;
WithdrawalError ->
              WithdrawalError
           end;
false ->
           {error, atm_is_empty}
        end;
SecurityError ->
        SecurityError
     end;
AccountError ->
     AccountError
  end.

Example Solution


-include("idiom-try-check-catch.hrl").


withdraw_money(AccountNumber, Password, Amount) ->
  try
{ok, Account} = check(account, find, AccountNumber),
check(security, check_password, Password, Account),
case check(dispenser, available_cash) < Amount of
     true ->
check(account, withdraw, Amount),
check(dispenser, spit_out_cash, Amount);
     false ->
{error, atm_is_empty}
end
  catch
throw:Reason ->
     {error, Reason}
  end.



Guts




-type reason() :: any().
-type error() :: {error, reason()}.
-type might_return_an_error() :: error() | any().

-spec f(Arg1, Arg2) -> error().


Saturday, February 27, 2010

What I'd like to see in Erlang


Erlang is a great distributed concurrent programming ecosystem that has annoyances.  This is my top "pid peeve" list.  ("pid peeve" = "erlang pet peeve")

1. Improved Record Syntax  (dead horse beaten to death, but still!)

Advantages:  It is easy to search code for use cases.
Disadvantages:  Most of the typical idioms that fit on one line in other programming languages requires a great deal of typing in Erlang.

There is also a problem with the record_info psuedo-function in that I cannot use it at runtime.  Converting to a property list requires a bit of a hassle.

2. Better Documentation Framework

Three main problems:

- There are a lot of rarely used libraries that seem to be highlighted at the expense of what would otherwise have been useful real-estate.
- The organization is like a stack of mystery meat navigation.  Compare the picture of the menu at right with the concept defined here.
- The docs are left over from the days when people cared about cover pages and actually used tables of content.

Although this has been solved wonderfully with clever stuff like http://erldocs.com/R13B04 one would expect the main distribution to present a most useful delivery.

(On the other hand we want the people behind Erlang building great concurrent libraries and not so much great viz.)