2017-02-08 21 views
0

Я разрабатываю приложение JavaEE, которое (пытается ...) использует функции безопасности ejb. Я работаю с WildFly 10.1. Я создал домен безопасности Jdbc и настроил вход на основе формы. Доступ к веб-методам и URL-адресам и правильность входа в систему (предотвращает доступ к неавторизованным и разрешает доступ после входа в систему).JAX-RS + EJB, SecurityContext внутри ejb имеет значение null, на WildFly 10.1

У меня есть набор бобов, который реализует интерфейс REST (Jax-RS), и у меня есть набор элементов ejb без статусов, который реализует бизнес-логику моего приложения.

Они являются пропущены из JBOSS-web.xml и web.xml:

<jboss-web> 
    <security-domain>myDomain</security-domain> 
</jboss-web> 

web.xml:

<security-constraint> 
    <web-resource-collection> 
     <url-pattern>/api/*</url-pattern> 
    </web-resource-collection> 
    <auth-constraint> 
     <role-name>administrator</role-name> 
     <role-name>operator</role-name> 
     <role-name>user</role-name> 
    </auth-constraint> 
</security-constraint> 
<login-config><!-- 3 --> 
    <auth-method>FORM</auth-method> 
    <realm-name>myRealm</realm-name> 
    <form-login-config> 
    <form-login-page>/public/login.html</form-login-page> 
    <form-error-page>/public/error.html</form-error-page> 
    </form-login-config> 
</login-config> 

Далее следует примерам кода, реализующих интерфейс покоя и java beans, я удалил код болельщика и обфускал имена, связанные с «используемым случаем». Пример один Jax-RS боба:

@Stateless 
@Path("api/my") 
public class myFacadeREST { 
    @EJB 
    myFacade myFacade; 

    @Context //injected response proxy supporting multiple threads 
    private HttpServletResponse response; 

    @POST 
    @Consumes({MediaType.APPLICATION_JSON}) 
    public void create(DataStuff entity) { 
     myFacade.create(entity); 
    } 

    @GET 
    @Path("{id}") 
    @Produces({MediaType.APPLICATION_JSON}) 
    public DataStuff find(@PathParam("id") String id) { 
     return myFacade.find(id); 
    } 
} 

И сниппет нагнетаемой EJB, где мне нужно программно получить доступ к контексту безопасности и основной информации:

@DeclareRoles({"administrator","operator","user"}) 
@PermitAll 
@Stateless 
public class myFacade { 

    @PersistenceContext(unitName = "myPersistencePU") 
    private EntityManager em; 

    @Context SecurityContext securityContext; 
    @Resource SecurityContext sc; //I have tried both :-(

    public DataStuff find(Object id) { 
     //Here I get a NullPointerException, tried both sc and securitycontext 
     String username = securityContext.getUserPrincipal().getName(); 
     if(username.equals("gino"){ 
      return null; 
     } 
     return getEntityManager().find(entityClass, id); 
    } 
} 

Я попытался с и без @DeclareRoles, @PermitAll, но переменные securityContext и sc всегда имеют значение null. Возможно, я что-то пропустил, но я понял, что информация о безопасности волшебным образом перемещается по боковым вызовам.

Вопросы

  • Как размножать контекст безопасности из класса JAX-RS к EJB фасоли?
  • Является ли информация о безопасности управляемой автоматическим образом, как я ожидал? или ..
  • Нужно ли мне улучшить или добавить другие файлы конфигурации jboss - ?. xml? или ..
  • Могу ли я что-то изменить в вызывающих компонентах Jax-RS, чтобы распространять информацию о безопасности вызываемым компонентам? или ..
  • Или я что-то не так?

Спасибо заранее уважением

+0

Этот вопрос является источником решения ниже, я добавил несколько полезных деталей (не хватает в источнике), надеюсь, полезно. –

+1

Чтобы ответить на ваши первые две точки, контейнер отвечает за * распространение * контекста безопасности, вам обычно не нужно беспокоиться об этом. –

ответ

0

Я нашел ответ, вопрос уже задавали here

SecurityContext только для боба JAX-RS, вам нужно вводить объект EJBContext InPlace из SecurityContext один в другие java-компоненты. Вы также можете использовать объект SessionContext, но интерфейс EJBContext похож на SecurityContext. Ниже приведена рабочая версия:

@DeclareRoles({"administrator","operator","user"}) 
@PermitAll 
@Stateless 
public class myFacade { 

    @PersistenceContext(unitName = "myPersistencePU") 
    private EntityManager em; 

    @Resource EJBContext securityContext; 

    public DataStuff find(Object id) { 
     //Now the securityContext is != null :-D 
     String username = securityContext.getCallerPrincipal().getName(); 
     if(username.equals("gino"){ 
      return null; 
     } 
     return getEntityManager().find(entityClass, id); 
    } 
}