1(818)262-8552
Or Email
contact@invertedsoftware.com

Move a DataReader to an Object with reflection


By Gal Ratner

Any multi tier application has a data layer, the purpose of the data layer is to, yes, hold data and while a database design is derived from the requirements and use of your application, in many cases, the data layer's structure is designed to mimic user screens or simplify input / output data operations.
The classic example is a web service. We have a system that holds our customer's data and we wish to share it with another system using a web service.
The easy solution would be to build a data object to hold a customer's data.
The data can be stored in multiple tables, but, in the data layer we are only going to use one object.
We are going to call it Customer and create a first and last name properties.

The Customer class

public class Customer
{
  private string firstName;

  public string FirstName
  {
    get { return firstName; }
    set { firstName = value; }
  }
  private string lastName;

  public string LastName
  {
    get { return lastName; }
    set { lastName = value; }
  }
}


Our web service is designed to return a list of our customers:

[WebMethod]
public List<Customer> GetCustomerList()
{
  List<Customer> customerList = new List<Customer>();
  return customerList;
}


How shell we bring our customers from the database into a list of objects and thru the web service?
One solution will be to select the data using an SqlDataReader and then manualy fill an object. Something like this:

Customer MyCustomer = new Customer();
MyCustomer.FirstName = reader["FirstName"].ToString();


This will of course require us to code all of the fields for every object we need. Not very efficient.

Reflection can help:

Reflection is the part of .NET that can look into an object and tell us what is inside.
It also has the ability to create objects for us according to specified types. Think of Reflection as the back door to .NET.

The reflection way:

public static Object GetAs(SqlDataReader reader, Type objectToReturnType)
{
  // Create a new Object
  Object newObjectToReturn = Activator.CreateInstance(objectToReturnType);
  // Get all the properties in our Object
  PropertyInfo[] props = objectToReturnType.GetProperties();
  // For each property get the data from the reader to the object
  for (int i = 0; i < props.Length; i++)
  {
    objectToReturnType.InvokeMember(props[i].Name, BindingFlags.SetProperty, null, newObjectToReturn, new Object[] { reader[props[i].Name] });
  }
return newObjectToReturn;
}


Its pretty simple: all we have to do is match the reader columns to the object properties.
rdr["FirstName"] will fill Customer.FirstName and so on.
All we have to do now is to cast our Object back to Customer and build the list.
For this example I have used SQLHelper to create the SqlDataReader

public List<Customer> GetCustomerList()
{
  List<Customer> customerList = new List<Customer>();
  using (SqlDataReader rdr = SqlHelper.ExecuteReader(SqlHelper.mainConnectionString, CommandType.StoredProcedure, "GetCustomers"))
  {
    while (rdr.Read())
      customerList.Add((Customer)SQLReaderToObject.GetAs(rdr, typeof(Customer)));
  }
  return customerList;
}


The web service can then look like:

[WebMethod]
public List<Customer> GetCustomerList()
{
  return GetCustomerList();
}


Conclusion:

Using the above code can save you quite a lot of time when coding your data layer. Give it a try!



About Us | Contact Us | Standards of Business Conduct | Employment
InvertedSoftware.com All rights reserved