Wednesday, November 19, 2008

Using NMock to Create an IDataReader for Testing Data Access Methods

If you have a simple Data Access class with a method like the one below which you need to test without depending on specific values in the database (and without embarking on a major refactoring expedition).

public decimal GetAvailableBalance(int custNumb)
decimal retVal = 0.00M; 
using (SqlConnection sqlConnection = new SqlConnection(_dbConnection))
using (SqlCommand sqlCommand = sqlConnection.CreateCommand())
sqlCommand.CommandType = CommandType.StoredProcedure;
sqlCommand.CommandText = "dbo.GetCustomerBalance";
sqlCommand.Parameters.AddWithValue("CustomerID", custNumb);
using (IDataReader dr = sqlCommand.ExecuteReader())
if (dr != null)
retVal = Convert.ToDecimal(dr["AvailableBalance"]);
return retVal; 

Replace this:

With This:
public virtual IDataReader GetReader(SqlCommand cmd)
return cmd.ExecuteReader(); 

Now create a test class that inherits from the Data Access class and override that virtual method. Like so:

public class IMTTests : TransactionStore
Mockery mocks = new Mockery(); 
IDataReader idr = null; 

public override IDataReader GetReader(SqlCommand cmd)
return idr; 

Now in your test, create your mock DataReader to assign to the private variable and set the specific expectations of your data mapping.

public void TestAvailableBalance()
idr = (IDataReader)mocks.NewMock(typeof(IDataReader));
Decimal amount = this.GetAvailableBalance(12345);
Assert.AreEqual(42.00M, amount); 

1 comment:

  1. Thanks bro.. exactly what this mock newbie was looking for!

    one question though! Why does it now work when I use Once instead of AtLeastOnce like