Reputation: 2242
We have a Service that exposes all of the data the client uses, all of the object have the interface IAuthorized
.
the data that gets out to the client needs to be filtered based on the user credentials.
the flow is like that the client call the service -> the service calls the SomeManager class that gets the data from the database ...
here comes the AuthorizationManager to filter the data ...
public class SomeManager
{
public object[] Foo()
{
var data = Repository.GetData();
return autorizationManager.Filter(data);
}
public object[] Foo_Else()
{
var data = Repository.GetOtherData();
return autorizationManager.Filter(data);
}
}
as you can see each method needs to be filtered ,
so what i ask you is : can we build a base class that filter each method with some attribute the output data ? is it smart ? should we leave it like that ? simply wach method we shell call the autorization ?
can you think of a better way ?
some thing like that :
public class EngineManager :BaseFilterAutho
{
[AuthorizationCollection]
public object[] Foo()
{
var data = Dao.GetData();
return data; //get filtered
}
[SingleCollection]
public object Foo_Else()
{
var data = Dao.GetOtherData().First();
return data //get filtered
}
}
Upvotes: 2
Views: 2035
Reputation: 4954
I have worked on a project where the data was filtered by the authorization of the user. The method used was similar to your "AuthorizationManager" method. That required a lot of filtering code to be written, but it works OK and is simple to understand.
There are other methods, your idea is certainly possible to implement. What you are referring to is using Aspect Oriented Programming, AOP. That is a common way in the Java world and is also possible in .Net. PostSharp is one 3rd party library that makes this possible. I have never used PostSharp in a working project myself, but I'm currently playing with it to learn AOP myself.
Below is an example of an aspect, implemented with PostSharp, that would alter the return value of a method to filter the data returned. This is a dummy aspect where I'm playing with a PostSharp demo, filtering the returned data to only return those Contacts that contain the letter "S".
As you can see, this aspect requires the return value to be IQueryable. I suspect you will always need to have some basic knowledge of the datatype of your return values, e.g. if you are working with IQueryable, ICollection, arrays or something else.
[Serializable]
public class CollectionFilterAspect : OnMethodBoundaryAspect
{
public override void OnExit(MethodExecutionArgs args)
{
base.OnExit(args);
IQueryable<Contact> retVal = (IQueryable<Contact>)args.ReturnValue;
args.ReturnValue = from r in retVal where r.LastName.Contains("S") select r;
}
}
To use this aspect, you can use your suggested syntax, putting an attribute on the method to indicate that it should be filtered.
[CollectionFilterAspect]
public IQueryable<Contact> GetByName(string value)
While this short demo illustrates that this is certainly possible, it may or may not be a good idea. I have no experience using this in real world software, so I can't help you there.
Upvotes: 1