嵌入式码头无过滤器名为交叉原素

发布于 2025-01-21 16:30:14 字数 4688 浏览 1 评论 0原文

我正在尝试在嵌入式码头服务器中实现CORS。除了这个例外,我现在感到迷失了。

java.lang.IllegalStateException: No filter named cross-origin
    at org.eclipse.jetty.servlet.ServletHandler.updateMappings(ServletHandler.java:1260)
    at org.eclipse.jetty.servlet.ServletHandler.doStart(ServletHandler.java:179)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:114)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.server.handler.ScopedHandler.doStart(ScopedHandler.java:112)
    at org.eclipse.jetty.server.session.SessionHandler.doStart(SessionHandler.java:486)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:114)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.server.handler.ScopedHandler.doStart(ScopedHandler.java:112)
    at org.eclipse.jetty.server.handler.ContextHandler.startContext(ContextHandler.java:955)
    at org.eclipse.jetty.servlet.ServletContextHandler.startContext(ServletContextHandler.java:388)
    at org.eclipse.jetty.server.handler.ContextHandler.doStart(ContextHandler.java:896)
    at org.eclipse.jetty.servlet.ServletContextHandler.doStart(ServletContextHandler.java:306)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:121)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.server.Server.start(Server.java:469)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:114)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.server.Server.doStart(Server.java:414)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.projectsanatan.restsanatan.RestSanatan.start(RestSanatan.java:38)
    at org.projectsanatan.restsanatan.Main.main(Main.java:16)

我的代码是,


    private void initServlets() {
        ServletContextHandler servletContextHandler = new ServletContextHandler(ServletContextHandler.SESSIONS);

        servletContextHandler.setContextPath("/");
        
        ResourceConfig resourceCfg = new ResourceConfig();
        resourceCfg.packages(BookResource.class.getPackage().getName(), "/*");
        
        ServletContainer servletContainer = new ServletContainer(resourceCfg);
        
        ServletHolder servletHolder = new ServletHolder(servletContainer);
        servletContextHandler.addServlet(servletHolder, "/api/*");
//        servletContextHandler.addFilter(null, KEY, null)
        
        FilterHolder corsFilter = new FilterHolder();
        corsFilter.setInitParameter("allowedOrigins", "https://example.com");
        corsFilter.setInitParameter("allowedMethods", "POST,GET,OPTIONS,PUT,DELETE,HEAD");
        corsFilter.setInitParameter("allowedHeaders", "X-PINGOTHER, Origin, X-Requested-With, Content-Type, Accept");
        corsFilter.setInitParameter("preflightMaxAge", "728000");
        corsFilter.setInitParameter("allowCredentials", "true");
        corsFilter.setInitParameter("chainPreflight", "false");
        
        CrossOriginFilter cors = new CrossOriginFilter();
        
        corsFilter.setFilter(cors);
        
        FilterMapping corsFilterMap = new FilterMapping();
        corsFilterMap.setFilterName("cross-origin");
        corsFilterMap.setPathSpec("/*");
        corsFilterMap.setDispatcherTypes(EnumSet.of(DispatcherType.INCLUDE, DispatcherType.REQUEST));
        
        servletContextHandler.getServletHandler().addFilter(corsFilter, corsFilterMap);
        
        this.handlerList.addHandler(servletContextHandler);
        
        this.setHandler(this.handlerList);
    }

我对码头和servlet东西的经验不太经验,所以我很困惑,帮助您将不胜感激!

I am trying to implement cors in a embedded jetty server. I feel lost right now with this exception.

java.lang.IllegalStateException: No filter named cross-origin
    at org.eclipse.jetty.servlet.ServletHandler.updateMappings(ServletHandler.java:1260)
    at org.eclipse.jetty.servlet.ServletHandler.doStart(ServletHandler.java:179)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:114)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.server.handler.ScopedHandler.doStart(ScopedHandler.java:112)
    at org.eclipse.jetty.server.session.SessionHandler.doStart(SessionHandler.java:486)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:114)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.server.handler.ScopedHandler.doStart(ScopedHandler.java:112)
    at org.eclipse.jetty.server.handler.ContextHandler.startContext(ContextHandler.java:955)
    at org.eclipse.jetty.servlet.ServletContextHandler.startContext(ServletContextHandler.java:388)
    at org.eclipse.jetty.server.handler.ContextHandler.doStart(ContextHandler.java:896)
    at org.eclipse.jetty.servlet.ServletContextHandler.doStart(ServletContextHandler.java:306)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:121)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.start(ContainerLifeCycle.java:171)
    at org.eclipse.jetty.server.Server.start(Server.java:469)
    at org.eclipse.jetty.util.component.ContainerLifeCycle.doStart(ContainerLifeCycle.java:114)
    at org.eclipse.jetty.server.handler.AbstractHandler.doStart(AbstractHandler.java:89)
    at org.eclipse.jetty.server.Server.doStart(Server.java:414)
    at org.eclipse.jetty.util.component.AbstractLifeCycle.start(AbstractLifeCycle.java:93)
    at org.projectsanatan.restsanatan.RestSanatan.start(RestSanatan.java:38)
    at org.projectsanatan.restsanatan.Main.main(Main.java:16)

My code is


    private void initServlets() {
        ServletContextHandler servletContextHandler = new ServletContextHandler(ServletContextHandler.SESSIONS);

        servletContextHandler.setContextPath("/");
        
        ResourceConfig resourceCfg = new ResourceConfig();
        resourceCfg.packages(BookResource.class.getPackage().getName(), "/*");
        
        ServletContainer servletContainer = new ServletContainer(resourceCfg);
        
        ServletHolder servletHolder = new ServletHolder(servletContainer);
        servletContextHandler.addServlet(servletHolder, "/api/*");
//        servletContextHandler.addFilter(null, KEY, null)
        
        FilterHolder corsFilter = new FilterHolder();
        corsFilter.setInitParameter("allowedOrigins", "https://example.com");
        corsFilter.setInitParameter("allowedMethods", "POST,GET,OPTIONS,PUT,DELETE,HEAD");
        corsFilter.setInitParameter("allowedHeaders", "X-PINGOTHER, Origin, X-Requested-With, Content-Type, Accept");
        corsFilter.setInitParameter("preflightMaxAge", "728000");
        corsFilter.setInitParameter("allowCredentials", "true");
        corsFilter.setInitParameter("chainPreflight", "false");
        
        CrossOriginFilter cors = new CrossOriginFilter();
        
        corsFilter.setFilter(cors);
        
        FilterMapping corsFilterMap = new FilterMapping();
        corsFilterMap.setFilterName("cross-origin");
        corsFilterMap.setPathSpec("/*");
        corsFilterMap.setDispatcherTypes(EnumSet.of(DispatcherType.INCLUDE, DispatcherType.REQUEST));
        
        servletContextHandler.getServletHandler().addFilter(corsFilter, corsFilterMap);
        
        this.handlerList.addHandler(servletContextHandler);
        
        this.setHandler(this.handlerList);
    }

I am not very much experienced with jetty and servlet stuff so I am confused, help would be really appreciated!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

土豪我们做朋友吧 2025-01-28 16:30:14

有一些问题。

  1. 两个servlet和过滤器的映射均由servletContexthandler完成,而不是servlethandler
  2. 如果您使用filterholder与名称映射,则必须命名filterholder
    名称的映射对于嵌入式杰出的使用过于复杂,实际上仅存在于web-inf/web.xml基于配置的>>。只需直接使用filterholder
  3. 您缺少所需的servletContexThandler basereSource声明
  4. 您缺少所需的defaultServletservletContext
  5. 您缺少defaulthandler在您的顶级处理程序树上(通常设置为最后一个条目),

正确的设置就是这样...

ServletContextHandler servletContextHandler = new ServletContextHandler(ServletContextHandler.SESSIONS);
servletContextHandler.setContextPath("/");
// Base Resource is required for your setup
servletContextHandler.setBaseResource(Resource.newResource(urlToStaticContent));

ResourceConfig resourceCfg = new ResourceConfig();
resourceCfg.packages(BookResource.class.getPackage().getName(), "/*");

ServletContainer servletContainer = new ServletContainer(resourceCfg);

ServletHolder servletHolder = new ServletHolder(servletContainer);
servletContextHandler.addServlet(servletHolder, "/api/*");

FilterHolder corsHolder = servletContextHandler.addFilter(CrossOriginFilter.class,
    "/*",
    EnumSet.of(DispatcherType.INCLUDE, DispatcherType.REQUEST));

corsHolder.setInitParameter("allowedOrigins", "https://example.com");
corsHolder.setInitParameter("allowedMethods", "POST,GET,OPTIONS,PUT,DELETE,HEAD");
corsHolder.setInitParameter("allowedHeaders", "X-PINGOTHER, Origin, X-Requested-With, Content-Type, Accept");
corsHolder.setInitParameter("preflightMaxAge", "728000");
corsHolder.setInitParameter("allowCredentials", "true");
corsHolder.setInitParameter("chainPreflight", "false");

// Default Servlet is Required
ServletHolder defaultHolder = new ServletHolder("default", DefaultServlet.class);
servletContextHandler.addServlet(defaultHolder, "/"); // default url-pattern

HandlerList handlerList = new HandlerList();
handlerList.addHandler(servletContextHandler);
// Default Handler is for requests that don't match a context above
// Such as requests that don't have a path that start with "/"
// It is safe to leave active, even in production, and will help with troubleshooting issues
handlerList.addHandler(new DefaultHandler());

server.setHandler(handlerList);

crossoriginfilter的过滤器映射已指定dispatchertype of <代码> include 和请求,这是一个非常奇怪的设置。

进行CORS include(或forward)dispatch非常尴尬,跳过它。

但是您没有指定async,这实际上是非常普遍的。

我会以这种方式更改映射...

FilterHolder corsHolder = servletContextHandler.addFilter(CrossOriginFilter.class,
    "/*",
    EnumSet.of(DispatcherType.REQUEST, DispatcherType.ASYNC));

要牢记使用crossoriginfilter的事情。

  1. 它只会根据您的配置产生HTTP响应标头。
  2. 它不会“防止”或“失败”任何与您的配置不符的请求。
  3. 没有Origin请求标头的请求不会触发CrossoriginFilter

There's a few issues.

  1. Mapping of both Servlets and Filters is done by the ServletContextHandler, not the ServletHandler.
  2. If you use a FilterHolder + Mapping with name, then you have to name your FilterHolder.
    Mapping with name is overly complicated for embedded-jetty use, it really only exists for WEB-INF/web.xml based configuration. Just use the FilterHolder directly.
  3. You are missing the required ServletContextHandler BaseResource declaration
  4. You are missing the required DefaultServlet on your ServletContext
  5. You are missing the DefaultHandler on your top level handler tree (usually set as last entry)

A correct setup would be like this ...

ServletContextHandler servletContextHandler = new ServletContextHandler(ServletContextHandler.SESSIONS);
servletContextHandler.setContextPath("/");
// Base Resource is required for your setup
servletContextHandler.setBaseResource(Resource.newResource(urlToStaticContent));

ResourceConfig resourceCfg = new ResourceConfig();
resourceCfg.packages(BookResource.class.getPackage().getName(), "/*");

ServletContainer servletContainer = new ServletContainer(resourceCfg);

ServletHolder servletHolder = new ServletHolder(servletContainer);
servletContextHandler.addServlet(servletHolder, "/api/*");

FilterHolder corsHolder = servletContextHandler.addFilter(CrossOriginFilter.class,
    "/*",
    EnumSet.of(DispatcherType.INCLUDE, DispatcherType.REQUEST));

corsHolder.setInitParameter("allowedOrigins", "https://example.com");
corsHolder.setInitParameter("allowedMethods", "POST,GET,OPTIONS,PUT,DELETE,HEAD");
corsHolder.setInitParameter("allowedHeaders", "X-PINGOTHER, Origin, X-Requested-With, Content-Type, Accept");
corsHolder.setInitParameter("preflightMaxAge", "728000");
corsHolder.setInitParameter("allowCredentials", "true");
corsHolder.setInitParameter("chainPreflight", "false");

// Default Servlet is Required
ServletHolder defaultHolder = new ServletHolder("default", DefaultServlet.class);
servletContextHandler.addServlet(defaultHolder, "/"); // default url-pattern

HandlerList handlerList = new HandlerList();
handlerList.addHandler(servletContextHandler);
// Default Handler is for requests that don't match a context above
// Such as requests that don't have a path that start with "/"
// It is safe to leave active, even in production, and will help with troubleshooting issues
handlerList.addHandler(new DefaultHandler());

server.setHandler(handlerList);

The Filter mapping of your CrossOriginFilter has specified the DispatcherType set of INCLUDE and REQUEST, that's a really odd setup.

Doing CORS from an INCLUDE (or FORWARD) dispatch is super awkward, skip it.

But you didn't specify ASYNC, which is actually super common.

I would change the mapping this way ...

FilterHolder corsHolder = servletContextHandler.addFilter(CrossOriginFilter.class,
    "/*",
    EnumSet.of(DispatcherType.REQUEST, DispatcherType.ASYNC));

Things to keep in mind for using CrossOriginFilter.

  1. It will only produce HTTP Response headers based on your configuration.
  2. It does not "prevent" or "fail" any request that doesn't match your configuration.
  3. Requests without a Origin request header will not trigger the CrossOriginFilter.
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文