I'm trying to write a utility class that will execute defined static methods to try and cut down on the boiler code and increase readability.
My idea stems from my current project of rewriting our aspx web services to a WCF service where all methods have a uniform boiler code pattern excluding the service request. The static methods don't currently exist on our existing objects as most of the logic lives within the web service method itself but should be easily transferable.
An example of what I have so far is below.
[DataContract]
public CustomObject CreateItem(int id, string name)
{
return ExecuteMethod<CustomObject>(CustomObject.CreateItem, id, name);
}
protected static T ExecuteMethod<T>(Delegate methodToExecute, params object[] parameters)
{
// Do some basic logging
// Authenticate user
try
{
if (methodToExecute == null)
{
throw new Exception();
}
if (methodToExecute.Method.ReturnType != typeof(T))
{
throw new Exception();
}
if (methodToExecute.Method.GetParameters().Length != parameters.Length)
{
throw new Exception();
}
return (T)methodToExecute.Method.Invoke(methodToExecute, parameters);
}
catch
{
throw new SoapException("There was an error", SoapException.ClientFaultCode);
}
}
public class CustomObject
{
[DataMemeber]
public int Id { get; set; }
[DataMember]
pubic string Name { get; set; }
internal static Delegate CreateItem = new Func<int, string, CustomObject>(
(id, name) =>
{
return new CustomObject() { Id = 1, Name = name };
}
);
}
My example above should illustrate what I'm trying to achieve. However, where I feel this approach is failing so far is that the parameters passed to the generic method are not typed and could result in runtime errors (both for return type and parameter types)
I have added some basic checks such as checking the return type of the methodInfo is of the same type as T and that the number of parameters of the method is equal to the number of parameters passed in but it doesn't feel 'safe'.
Am I on the right track or should I look into an alternative solution?
This is just a prototype at the moment as I'm just starting to think about the re-design.
It looks to me as if the only benefit of calling it through your method is to translate any exception into a SoapException. You can do that more easily like this:
protected static T ExecuteMethod<T>(Func<T> function)
{
try
{
return function();
}
catch
{
throw new SoapException("There was an error",
SoapException.ClientFaultCode);
}
}
Then the calling code would look like this:
public CustomObject CreateItem(int id, string name)
{
return ExecuteMethod(() => CustomObject.CreateItem(id, name));
}
(I hope in the real code you've got some logging for the exception case, btw.)