Friday, February 12, 2010

Data Access Layer in C# using Repository and Data Mapper – Part 4


The customer repository inherits the base repository and uses the data mapper instance for object creation. All the CRUD procedures defined in the first post of this series are called in this class. The query for accessing and persisting data in the relational model is formed in the Customer repository.
protected override BaseMapper<Customer, long> Mapper
{
    get
    {
        if (___Mapper == default(CustomerMapper)) ___Mapper = new CustomerMapper("CustomerIntId");
        return ___Mapper;
    }
}

public Customer GetById(long id)
{
    DbCommand command = ___Database.GetStoredProcCommand("usp_GetCustomerById");
    ___Database.AddInParameter(command, "CustomerIntId", DbType.Int64, id);
    return FindOne(command);
}

public void Insert(Customer entity)
{
    DbCommand command = ___Database.GetStoredProcCommand("usp_InsertCustomer");
    ___Database.AddInParameter(command, "FirstName", DbType.String, entity.FirstName);
    ___Database.AddInParameter(command, "LastName", DbType.String, entity.LastName);
    ___Database.AddInParameter(command, "Address", DbType.String, entity.Address);

    ___Database.AddOutParameter(command, "CustomerIntId", DbType.Int64, 8);

    ___Database.ExecuteNonQuery(command);

    Int64 customerIntId = (Int64)(___Database.GetParameterValue(command, "CustomerIntId"));
    entity.Id = customerIntId;
}

public void Remove(long id)
{
    DbCommand command = ___Database.GetStoredProcCommand("usp_DeleteCustomerById");
    ___Database.AddInParameter(command, "CustomerIntId", DbType.Int64, id);

    ___Database.ExecuteNonQuery(command);
}
I have uploaded the source code for the customer repository here.
[TestMethod]
public void can_insert_customers_into_db()
{
    ICustomerRepository repository = new CustomerRepository();
    var customerToInsert = new Customer { FirstName = "Prajeesh", LastName = "Prathap", Address = "BTM 2nd Stage, Bangalore" };
    repository.Insert(customerToInsert);

    var customer = repository.GetById(customerToInsert.Id);
    Assert.IsNotNull(customer);
    Assert.AreEqual<string>(customer.FirstName, "Prajeesh");

    repository.Remove(customer.Id);
}
Our final implementation looks like.

3 comments:

Anonymous said...

Good articles. Fortunately Microsoft has provided us with the Entity Framework. We use it extensively at our workplace and it is great timesaver since it builds all the necessary classes and plumbing like your Repository and Data Mapper.

amexn said...

Please Share the code

Gied said...

Entity Framework is nowhere flexible enough to fit all requirements. Custom framework is still the way to go if you want to make sure you can continue using the pattern without adding numerous "exceptions" because something doesn't fit. Great job!