IllegalArgumentException: не найден обработчик для ключа 'javax.security.auth.Subject.container' - PullRequest
0 голосов
/ 05 декабря 2018

Я в основном придерживаюсь этого урока: https://www.ibm.com/developerworks/java/library/j-javaee8-security-api-4/index.html?ca=drs-

Моя среда разработки: TomEE 8.0 M1 Plume

pom.xml

    <dependency>
        <groupId>org.glassfish.soteria</groupId>
        <artifactId>javax.security.enterprise</artifactId>
        <version>1.0</version>
    </dependency>
    <dependency>
        <groupId>javax</groupId>
        <artifactId>javaee-api</artifactId>
        <version>8.0</version>
        <scope>provided</scope>
    </dependency>

ApplicationConfig:

@CustomFormAuthenticationMechanismDefinition(
        loginToContinue = @LoginToContinue(
                loginPage = "/login.xhtml",
                errorPage = "/login.xhtml?error",
                useForwardToLogin = true
        )
)

@ApplicationScoped
@Named
public class ApplicationConfig {
}

TestServlet:

@WebServlet("/test")
public class TestServlet extends HttpServlet {

    @Inject
    SecurityContext securityContext;

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        securityContext.isCallerInRole("admin");
    }
}

Перейти к http://localhost:8080/test, Я получаю это исключение:

    05-Dec-2018 16:38:39.132 SEVERE [http-nio-8080-exec-219] org.apache.catalina.core.StandardWrapperValve.invoke Servlet.service() for servlet [servlet.TestServlet] in context with path [] threw exception
 java.lang.IllegalArgumentException: No handler can be found for the key 'javax.security.auth.Subject.container'
    at javax.security.jacc.PolicyContext.getContext(PolicyContext.java:91)
    at org.glassfish.soteria.authorization.JACC$2.run(JACC.java:175)
    at java.security.AccessController.doPrivileged(Native Method)
    at org.glassfish.soteria.authorization.JACC.getFromContext(JACC.java:173)
    at org.glassfish.soteria.authorization.JACC.getSubject(JACC.java:73)
    at org.glassfish.soteria.authorization.JACC.isCallerInRole(JACC.java:78)
    at org.glassfish.soteria.authorization.spi.impl.ReflectionAndJaccCallerDetailsResolver.isCallerInRole(ReflectionAndJaccCallerDetailsResolver.java:82)
    at org.glassfish.soteria.SecurityContextImpl.isCallerInRole(SecurityContextImpl.java:89)
    at servlet.TestServlet.doGet(TestServlet.java:20)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:634)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:741)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:231)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:53)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.openejb.server.httpd.EEFilter.doFilter(EEFilter.java:65)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:199)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:96)
    at org.apache.tomee.catalina.OpenEJBValve.invoke(OpenEJBValve.java:44)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:607)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:139)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:92)
    at org.apache.tomee.catalina.OpenEJBSecurityListener$RequestCapturer.invoke(OpenEJBSecurityListener.java:97)
    at org.apache.catalina.valves.AbstractAccessLogValve.invoke(AbstractAccessLogValve.java:668)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:74)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:343)
    at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:408)
    at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:66)
    at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:770)
    at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1415)
    at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
    at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
    at java.lang.Thread.run(Thread.java:745)

Я из Spring и Spring Security, но новичок вCDI и EJB.

Подскажите, пожалуйста, как настроить это handler или я что-то упустил?

Спасибо!

1 Ответ

0 голосов
/ 30 декабря 2018

Ошибка вызвана тем, что TomEE не полностью реализует JACC, от которого зависит SPI авторизации по умолчанию («ReflectionAndJaccCallerDetailsResolver») Soteria.

Обратите внимание, что TomEE фактически поддерживает JACC, но не полностью.

Здесь есть несколько вариантов (от простых до более сложных):

  1. Очевидное;дождитесь финальной версии TomEE 8, которая должна так или иначе заставить эту работу работать (используя собственную реализацию EE Security или иным образом)То же самое, что реализация по умолчанию теперь использует JACC для.
  2. Внесите вклад в TomEE и внедрите недостающие биты в их реализацию JACC (или внесите вклад в Tomcat с реализацией только через Интернет).Для этого уже есть JIRA, см. TOMEE-1912

Я планировал предоставить пример для 2. и сделать SPI более очевидным в Soteria 1.1, но, к сожалению,еще не дошел до этого.

...