Thursday, October 14, 2010

A Pinch of Functional in my C# - An Everyday Example

I'm working on a codebase that, like many other code bases,  has a number of data access objects(DAOs) that all inherit a common superclass. The other day I got tired of looking this pattern of code repeated a lot in the DAOs:
    1        public MyDTO GetMyDTO(...)
    2         {
    3             DataContext DB = NewDBContext;
    4             try
    5             {
    6                 DB.Connection.Open();
    7                 //Fetch something from the DB and return it
    8             }
    9             finally
   10             {
   11                 if (DB.Connection.State == ConnectionState.Open)
   12                     DB.Connection.Close();
   13             }
   14         }

I wanted the creation of the DBContext and the handling of the connection to be factored into somewhere reusable. So I applied the functional "suround with" pattern and introduced this method in the superclass:
    1        protected TReturn UsingDBConnection<TReturn>(Func<DataContext, TReturn> func)
    2         {
    3             DataContext DB = NewDBContext;
    4             try
    5             {
    6                 DB.Connection.Open();
    7                 return func(DB);
    8             }
    9             finally
   10             {
   11                 if (DB.Connection.State == ConnectionState.Open)
   12                     DB.Connection.Close();
   13             }
   14         }
and the DAO code then turns into this:
    1        public MyDTO GetMyDTO(...)
    2         {
    3             return UsingDBConnection(DB =>
    4             {
    7                 //Fetch something from the DB and return it
    7             });
    8         }

C# has supported this for years now, so why am I posting it? -Because I wish I saw more of this type of code. To me it's easy to read and I get to reuse the common part.


4 comments:

  1. Hi Christian.

    I agree completely. In this case, getting rid of the explicit opening and closing of resources and the error handling makes the code much nicer and more focused.

    An idea might be creating an overloaded method, thereby enabling both the original style of code and this other more "functional" style. As an example, in Ruby, it is quite common to have different behaviour depending on whether or not you supply a block of code. See IO::open for a classic example: http://ruby-doc.org/core/classes/IO.html#M002239.

    ReplyDelete
  2. @stissing: Thanks for the tip. That would make a lot of sense here, and maybe even help in moving existing code incrementally towards this slightly more functional style.

    ReplyDelete
  3. I use the surround with pattern to encapsulate calling wcf services and handling exceptions awhile back. Didn't think to talk about it. I think that's the problem, more devs talking about stuff like this, and being able to find this info easily. I just found this post, and I was looking for something else!

    ReplyDelete
  4. As such this is an simple example but for those who are familiar with this, for beginners this will be something new to learn from it. You can even deal with this using ObjectContext as it is almost similar to DbContext.

    ReplyDelete