문제

I have an Java EE 7 Web application with a security manager that enable users to authenticate with 'Roles'. Throughout the application there are services whose implementation depends on the users 'Role'.

Originally I had an interface that was implemented by a single class and inside each method in that class I determined what 'Role' the subject had and used a switch to execute the respective code.

To improve on this I have now created several interface implementation classes and have decorated each with a respective @Qualifier, each one being destined to be mapped to a specific 'Role'.

Just for the sake of simplicity lets say that the qualifiers are @Administrator and @User and I have 30 classes throughout the application that require this 'Role' based implementation. In each case I always want 'Administrators' to use the @Administrator decorated implementation and 'Users' to use the @User decorated implementation.

I don't wan't to write 30 producer factory classes as that seems inefficient (and wrong!). What I would like to achieve is a single factory that always selects the respective qualifier irrespective of the type.

Here is a very simplified version of the code for clarity.

The interfaces:

public interface MyInterface {
...
}

public interface MyInterface2 {
...
}

The original approach was with a switch (simplified to if else here)

public class AdministratorMyInterface implements MyInterface {

    if (role.equals("Administrator")) {
       ... execute administrator version ...
    } else {
       ... execute user version ...
    }

}

public class AdministratorMyInterface2 implements MyInterface2 {

    if (role.equals("Administrator")) {
       ... execute administrator version ...
    } else {
       ... execute user version ...
    }

}

The new goal is to have separate implementation. One to be used with Administrators.

@Administrator
public class AdministratorMyInterface implements MyInterface {

... implementations specific to administrators ...

}

@Administrator
public class AdministratorMyInterface2 implements MyInterface2 {

... implementations specific to administrators ...

}

Some interface implementation to be used by users with User role:

@User
public class UserMyInterface implements MyInterface {

... implementations specific to users ...

}

@User
public class UserMyInterface2 implements MyInterface2 {

... implementations specific to users ...

}

I now need a way so that if an Administrator executes the code they always implement the implementation decorated with @Administrator.

Is this possible? Is there a better approach to this?

도움이 되었습니까?

해결책

You can write a producer for MyInterface that gets Instance injected and then select()s the appropriate implementation.

Have a look at this excellent example: http://www.byteslounge.com/tutorials/java-ee-cdi-programmatic-dependency-disabiguation-example-injection-point-inspection

  @Produces
  public MyInterface createService(
    @Any Instance<MyInterface> instance, InjectionPoint ip){
    // you will need to determine if @Admin or @User should be used ... I dont know your user handling, so this is custom coding.
    return instance.select(annotation).get();
  }
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top