Dependency Injection, Interfaces, and Mocking: our new shop standard?


Ok, raise your hand RIGHT NOW if you said “Oh my” after “Dependency Injection, Interfaces, and Mocking”.   If you didn’t, drop what you’re doing and go rent “The Wizard of Oz” because you’re really missing a monumentally important American cultural reference.

I don’t recommend the adoption of new shop standards very often for my team.  Yes, I like us to be nimble and up to speed as much as possible, but I’m not really a bleeding edge kind of guy.   I like standards that solve REAL problems.

Real Problem #1:

How do you write a unit test for a unit that depends on other units that you don’t have yet?

Real Problem #2:

How do you send your application to a super smart friend (who will be able to fix your 2 month old bug in 2 seconds) when the application depends on internal resources such as a database?

Real Problem #3:

What if you’re coding the Service tier, and some other guy is developing the persistence tier and he keeps changing his implementation in a way that causes you to have to change your implementation?

“Ok, David, here’s the new class and here’s how you instantiate it.”

“Great, thanks, Joe.  I just finished  building, testing, and deploying my application.  I’d just LOVE to do it again.”

Ok, so these are real problems that my real team of RAJPs have struggled with over the last year.  If you are not a RAJP (say, a JG (Java Guru) or a JPE (Java Programmer Extraordinaire)) you probably have a super duper array of frameworks and techniques to solve this problem that I will not figure out how to use until my RAJP solution is no longer working for me.

Solution

Step 1: Write all of your DAO classes to an Interface.

Writing to an Interface is the design foundation for all things loosely-coupled.

fig194

PickleDAO Interface

Step 2: Implement a Mock and a fully Implemented version of all your  DAO classes (to an Interface of course).  If you have any other DAO alternatives (a web service, a local cache for offline use, or whatever) be sure to implement the same interface.

You probably want to start with the Mock implementation first.  This will get you up and going quicker.

fig203

Mock Implementation of the PickleDAO

Notice the use of test data in my mock.

When you finally get around to fleshing out your DAO then you’ll start with something more like this.

fig211

Actual Implementation of PickleDAO

Step 3: Inject DAO instances into your Service object based on specific deployment needs.

There are a lot of different ways to accomplish Dependency Injection.  We’re using Spring.

I specify which implementation of PickleDAO to use at runtime in a Spring Configuration file.  For this deployment, I’m instantiating PickleDAOMock

fig241

Spring Configuration file to injection the PickleDAO instance

All that remains is a simple injection…I promise it won’t hurt!

fig253

PickleService with DAO injection

Now, I can just hear some of the guys on my team whining about how many more source files are required to accomplish this design.  Here’s what it looks like:

Package Tree for my bogus Persistence Layer

Package Tree for my bogus Persistence Layer

But come on, guys!  This is how we make our living…writing code!

Summary

If you design your persistence layer with this pattern,  you will provide optimum flexibility with loose coupling.   This solves all three of the problems that I described above.

Problem #1: When testing units that depend on a DAO that you haven’t fleshed out yet, switch the configuration to inject the Mock DAO.

NOTE:  The Spring folks recommend directly instantiating your Mock objects in your unit test rather than injecting.  I’m not yet experienced enough with unit testing to argue for or against this, so I’ll just leave at that.

Problem #2: Before you send your code off to your super smart friend, reconfigure your Spring config to instantiate a Mock or some other kind of instance that won’t require that resource.

Problem #3: The persistence guy can switch DAO implementations to his heart’s content without the Service guy ever noticing.   Worst case scenario is that the Service guy has to change his Spring config.

Perhaps one day, I’ll get tired of writing my own mocking and will use JMock or something slick like that.   If I do, I’ll be sure to tell you about it.  Until then, I’ll stick with my Regular Average Java Programmer approach.

Advertisements

One thought on “Dependency Injection, Interfaces, and Mocking: our new shop standard?

  1. Pingback: Dependency Injection in JSF « Hobione’s Weblog

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s