本地Jetty运行App Engine Java 11 helloworld-servlet出现404错误
问题背景
运行Google的helloworld-servlet示例时,页面http://localhost:8080/hello能正常加载带样式的JSP内容,但浏览器控制台始终报GET http://localhost:8080/favicon.ico 404 (Not Found)。此前运行无异常,当前两台机器均使用JDK 17.0.10,已尝试清理本地依赖、重新构建项目、更换机器、升级Jetty版本等操作,问题仍存在。
原因分析
这个404本质是项目未提供favicon.ico文件,且当前JDK 17+Jetty的组合不再默认返回内置的favicon图标(此前旧版本环境中Jetty可能自动提供默认图标,不会触发404报错)。
解决方案
方法1:手动添加favicon.ico文件(最直接)
在helloworld-servlet/src/main/webapp目录下放置任意favicon.ico文件(可将普通图标文件重命名为该名称),然后重新执行mvn package打包项目,重启Jetty服务即可。浏览器会正常读取该图标,404报错消失。
方法2:通过web.xml配置拦截请求避免404
如果不想添加图标文件,可在helloworld-servlet/src/main/webapp/WEB-INF/web.xml中添加以下配置,让服务器对favicon请求返回空内容(204状态码):
<servlet> <servlet-name>EmptyFaviconServlet</servlet-name> <servlet-class>com.example.EmptyFaviconServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>EmptyFaviconServlet</servlet-name> <url-pattern>/favicon.ico</url-pattern> </servlet-mapping>
同时创建对应的Servlet类:
package com.example; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.io.IOException; public class EmptyFaviconServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { resp.setStatus(HttpServletResponse.SC_NO_CONTENT); } }
重新打包启动服务后,favicon请求会返回204状态码,不再出现404报错。
方法3:配置Jetty DefaultServlet处理静态资源
若使用Jetty 11,可在web.xml中配置DefaultServlet来统一处理静态资源请求(包括favicon):
<servlet> <servlet-name>default</servlet-name> <servlet-class>org.eclipse.jetty.servlet.DefaultServlet</servlet-class> <init-param> <param-name>dirAllowed</param-name> <param-value>false</param-value> </init-param> </servlet> <servlet-mapping> <servlet-name>default</servlet-name> <url-pattern>/favicon.ico</url-pattern> </servlet-mapping>
如果项目中没有favicon.ico,此配置仍会返回404,但可配合Jetty的资源配置指定一个全局默认图标路径。
补充说明
JDK升级到17后,可能改变了Jetty的类加载逻辑或默认资源处理规则,导致原本Jetty内置的默认favicon不再生效,因此出现了之前未遇到的404报错。其中方法1无需修改代码,是最便捷的解决方式。
内容的提问来源于stack exchange,提问作者timmacp

