# Reduce boilerplate with RepositoryPattern

I'm refactoring a WPF application that uses Repository pattern to access the web services, I've got a tons of repository wrote as

public class DiagnosticsRepository : DefaultRepositoryBase, IDiagnosticsRepository
{
{
var client = GetServiceStackClient();

var request = new MasterDiagnosticTypesRequest
{
};

return client.PostAsync(request);
}

{
var client = GetServiceStackClient();

var request = new MasterDiagnosticRequest()
{ MasterType = type };

return client.PostAsync(request);
}

{
var client = GetServiceStackClient();

var request = new DiagnosticoDataRequest()

{
StoredProcedureName = storedProcedure,
Data = DateTime.Today
};

return client.PostAsync(request);
}
}


How can I review it so that I can avoid the repetition? the only part that changes is the request

• I assume you meant 'refactoring' instead of 'reviewing'? – Pieter Witvoet Aug 4 '17 at 10:18
• you're right, fixing title – advapi Aug 4 '17 at 10:19
• I think you need first refactor PostAsync. As I can see from your code this method can return many different types. I suggest to generalize return type of this method with kind of IPostResponse. As for parameter of the method I would define it as IPostRequest. And all request types should implement this interface. After these changes refactoring of repositories will be trivial. – Maxim Aug 4 '17 at 10:27
• PostAsync is from ServiceStack – advapi Aug 4 '17 at 10:28
• I am not sure but it seems that you can specify type of the response via generic type parameter of the method like PostAsync<IPostResponse>. I didn't work with ServiceStack but it looks configurable. – Maxim Aug 4 '17 at 10:36

If you must keep the code the same way, I can think of only reducing the repeated

var client = GetServiceStackClient();
return client.PostAsync(request);


by doing something like this:

public class DiagnosticsRepository : DefaultRepositoryBase, IDiagnosticsRepository
{
{
var request = new MasterDiagnosticRequest()
{
MasterType = type
};

return Refactor<IList<MasterDiagnostic>, MasterDiagnosticRequest>.Get(request);
}

{
var request = new DiagnosticoDataRequest()
{
StoredProcedureName = storedProcedure,
Data = DateTime.Today
};

return Refactor<DiagnosticoDataResponse, DiagnosticoDataRequest>.Get(request);
}

// get rid of the repetition...
private class Refactor<TRespone, TRequest>
{
{
var client = GetServiceStackClient();
return client.PostAsync(request);
}
}
}


Frankly, I don't think you should have all these various methods and signatures at all. You could reduce the repository to just the methods that are usually found in a repository (ex: Add, Update, GetById, Delete, Etc...

Which would mean your repository would potentially just look like this instead:

public class DiagnosticsRepository<T> : IDiagnosticsRepository
{
public static Task<T> Get(object request = default(object))
{
var client = GetServiceStackClient();
return client.PostAsync(request);
}
}


-The below is unconfirmed for your particular library, but based on my quick read of the documentation, this should work-
With the above minimized repository, if you like, you could go even further and swap your requests to anoymous types to reduce the amount of classes you are generating -- which is not uncommon especially for JSON requests. For example:

string storedProcedure = "...";
object request = new { StoredProcedureName = storedProcedure, Data = DateTime.Today };
var response = DiagnosticsRepository<DiagnosticoDataResponse>.Get(request);

• I've not got spurce here... btw i was thinking of a Func<TResponse> in the base class...your approach of a static method is the same? Unfortunately I don't have CRUD operation... and access is 90% via StoredProcedures – advapi Aug 4 '17 at 20:11
• I don't think you will make your code any easier to understand by adding more layers into your classes. I'd take a look at how to pass the generic types into .PostAsync<T>()and refactor based on that rather than using all these helper methods like XyzRequest() – Svek Aug 4 '17 at 20:16
• xyzRequest are POCO used by ServiceStack to perform calls – advapi Aug 4 '17 at 20:18
• @advapi - I'm certain it can be refactored... Have you tried sending an anonymous type on the request? Ex: new { Prop = val } instead of new XyzRequest { Prop = val }? -- If I am right, we just saved you from at least double the classes you're writing. – Svek Aug 4 '17 at 20:29
• no Ive not... the advantage of this is that I've the POCO on the server side – advapi Aug 4 '17 at 20:31