Question of the Week - Validation Code Reuse

Last Friday while out on the ARCast Down Under Tour in Perth Australia someone came up to me with a question about sharing code between the client and server side in an SOA. I have to admit that after 2 weeks on the road with constant presentations I wasn't thinking too clearly and I couldn't remember how to do this. I knew I had done something like this before so here I am 5 miles above the Indian Ocean on my way to Kuala Lumpur and I decided to take this challenge on. Here goes.

 

Question: How can I share validation logic between server side code and client side code in my SOA?

 

Answer:

First off let’s begin with some basics of validation in SOA. The most basic rule of all is that you should validate the content of messages. Never trust client side validation code only because anybody can create an XML message and send it to you. But suppose that you do control the client and the server and you want to share validation code across both of them. The question is how?

 

For this example let’s use my favorite object; the customer object. When you consider this problem it may help to break it down into two parts. Objects can have both behavior and state. In the case of validation you have a behavior that wants to act on the state.

 

Because you want to share behavior between client and server what you need is a behavior that can act on the state of two different types which happen to share the same state. What are the options here?

 

The best way to get this done is by creating a validator that validates objects which implement the appropriate interface.

 

Here is the simple interface for customer data

public interface ICustomerDataContract

{

    string Name

    {

        get;

        set;

    }

}

 

Now we need a simple validator

public class CustomerDataValidator

{

    static public bool Validate(ICustomerDataContract customer)

    {

        return !string.IsNullOrEmpty(customer.Name);

    }

}

Next a class that implements the interface

public class CustomerDataContract : ICustomerDataContract

{

    private string _name;

    public string Name

    {

        get{return _name;}

        set{_name = value;}

    }

}

Now we can validate on the server side like so

[WebMethod]

public bool ValidateCustomer(CustomerDataContract customer)

{

    return CustomerDataValidator.Validate(customer);

}

 

Great but what about the client side you say? No worries mate! Create a Winforms app and add a web reference to our service. This will generate a proxy with a client side version of our CustomerDataContract type. The question is, how do we add the interface to that type?

 

Simple... .NET 2.0 declares the generated types as partial classes which allows us to easily add to them without having to modify the generated files (don't you just love partial classes!)

 

namespace WindowsApplication1.localhost

{

    // This will add the interface to the generated proxy

    public partial class CustomerDataContract : ICustomerDataContract

    {

    }

}

 

The proxy class already implements the interface so we are good to go. Now we can simply add a reference to our validator as a file or in a separate assembly and call away. This allows me to validate on the client and again on the server with the same code.

 

private void button2_Click(object sender, EventArgs e)

{

    CustomerDataContract MyCustomer = new CustomerDataContract();

    MyCustomer.Name = "Ron";

    // Validate on the client side

    MessageBox.Show(CustomerDataValidator.Validate(MyCustomer).ToString());

    // Call the service and show it's result

    localhost.Service svc = new localhost.Service();

    MessageBox.Show(svc.ValidateCustomer(MyCustomer).ToString());

}

 

Wohoo! I knew there was a way to get this done!

 

That was fun – what's next? Who has a question for me? This is a fun way to blog.