内容
目录
常规
请先阅读常规 迁移指南页面,了解 Apache Tomcat® 版本之间迁移或升级的常见注意事项。
从 6.0.x 迁移到 7.0.x
本部分列出了 6.0.x 和 7.0.x 之间所有已知更改,这些更改可能会在升级时导致向后兼容性问题。
需要 Java 6
Apache Tomcat 7.0.x 需要 Java 6 或更高版本。Apache Tomcat 6.0.x 需要 Java 5。
Servlet 3.0 API
Apache Tomcat 7 支持 Java Servlet 3.0、JavaServer Pages 2.2、Expression Language 2.2 和 WebSocket 1.1 规范。规范版本之间的更改可以在每个规范文档的更改附录中找到。
在使用通配符导入语法的 JSP 页面中,Servlet API 中添加的新类可能与 Web 应用程序中的类发生冲突。例如,如果包 "a"
包含类 Part
,那么以下 JSP 页面将停止在 Tomcat 7 中编译
<%@page import="a.*"%>
<% Part page = new Part(); %>
发生这种情况是因为隐式导入 javax.servlet.http.*
和显式导入 a.*
将提供 Servlet 3.0 中添加的类 Part
的冲突定义。解决方案是使用显式导入 import="a.Part"
。
正则表达式
现在,所有使用正则表达式的配置选项都需要一个正则表达式(使用 java.util.regex
),而不是一个逗号分隔或分号分隔的表达式列表。
这涉及以下内容
- RemoteAddrFilter、RemoteHostFilter 过滤器 和 RemoteAddrValve、RemoteHostValve 阀 中的
allow
和deny
属性; - RemoteIpFilter、RemoteIpValve 中的
internalProxies
、trustedProxies
属性; - ReplicationValve 中的
filter
属性; - HTTP 连接器 中的
restrictedUserAgents
、noCompressionUserAgents
属性。
请注意,可以使用“|
”运算符(或)连接单独的正则表达式。在当前版本和早期 Tomcat 版本中,“|
”都可用。
部署
不再从已部署的 WAR 和目录将 XML 上下文描述符(META-INF/context.xml
文件)复制到主机的 xmlBase
。可以通过将 Host 元素的 copyXML
属性设置为 true
来启用 Tomcat 6 的默认行为。
在 7.0.12 至 7.0.47(含)版本中,无论 Host
的 unpackWARs
设置的值如何,主机 appBase
之外的 WAR 都不会解包。请注意,仅在 7.0.48 及更高版本中支持此解包。请参阅问题 51294。
管理器应用程序
Manager 应用程序已针对 Tomcat 7 及更高版本进行了重新构建,并且一些 URL 已更改。现在,用于访问 Manager 应用程序的所有 URL 都应从以下选项之一开始
- HTML GUI 的 <ContextPath>/html
- 文本界面的 <ContextPath>/text
- JMX 代理的 <ContextPath>/jmxproxy
- 状态页面的 <ContextPath>/status
请注意,文本界面的 URL 已从“<ContextPath>”更改为“<ContextPath>/text”。
使用 Manager 应用程序所需的权限已从单一 manager
权限更改为以下四个权限。您需要分配用于您希望访问的功能所需的权限。
manager-gui
- 允许访问 HTML GUI 和状态页面manager-script
- 允许访问文本界面和状态页面manager-jmx
- 允许访问 JMX 代理和状态页面manager-status
- 仅允许访问状态页面
HTML 界面受 CSRF 保护,但文本和 JMX 界面不受保护。为维护 CSRF 保护
- 拥有
manager-gui
权限的用户不应被授予manager-script
或manager-jmx
权限。 - 如果 Manager 应用程序由拥有
manager-script
或manager-jmx
权限的用户通过浏览器访问(例如,用于测试文本或 jmx 界面,因为这些界面是为工具而非人类设计的),则必须在之后关闭所有浏览器窗口以终止会话。
已从 Manager 应用程序中删除 roles 命令,因为它不适用于默认配置,并且大多数 Realms 不支持提供权限列表。
主机管理器应用程序
Host Manager 应用程序已针对 Tomcat 7 及更高版本进行了重新构建,并且一些 URL 已更改。现在,用于访问 Host Manager 应用程序的所有 URL 都应以以下选项之一开头
- HTML GUI 的 <ContextPath>/html
- 文本界面的 <ContextPath>/text
请注意,文本界面的 URL 已从“<ContextPath>”更改为“<ContextPath>/text”。
使用 Host Manager 应用程序所需的权限已从单一 admin
权限更改为以下两个权限。您需要分配用于您希望访问的功能所需的权限。
admin-gui
- 允许访问 HTML GUI 和状态页面admin-script
- 允许访问文本界面和状态页面
HTML 界面受 CSRF 保护,但文本界面不受保护。为维护 CSRF 保护
- 拥有
admin-gui
权限的用户不应被授予admin-script
权限。 - 如果 Host Manager 应用程序由拥有
admin-script
权限的用户通过浏览器访问(例如,用于测试文本界面,因为此界面是为工具而非人类设计的),则必须在之后关闭所有浏览器窗口以终止会话。
会话管理器配置
已对会话管理器进行了一些更改,以提高会话生成和销毁的性能,包括对会话 ID 生成的更改。会话 ID 生成的更改利用了 java.secure.SecureRandom
的改进,因为会话 ID 生成最初是编写的。配置更改为
- Manager 的
randomClass
属性已更改为secureRandomClass
,并且提供的类必须扩展java.secure.SecureRandom
- 已添加两个新属性
secureRandomAlgorithm
和secureRandomProvider
以启用 SecureRandom 实现的选择。 algorithm
属性已移除entropy
属性已移除
java.secure.SecureRandom
已知的一个问题是,它的初始化需要来自熵源的某些随机数据。对于某些熵源实现,可能需要一些时间来收集足够多的随机数据。如果会话 ID 生成器的初始化需要明显的时间(超过 100 毫秒),将记录一条诊断消息。例如:
DATE org.apache.catalina.util.SessionIdGenerator createSecureRandom
信息:使用 [SHA1PRNG] 创建会话 ID 生成所需的 SecureRandom 实例花费了 [406] 毫秒。
可以通过定义系统属性来更改 JRE 使用的熵源。例如:
-Djava.security.egd=file:/dev/./urandom
上述值中的 "/./" 字符用于解决 JRE 问题 #6202721。
会话 cookie 配置
随着 Servlet 3.0 规范中添加 SessionCookieConfig
,一些会话 Cookie 配置选项已被移除,以减少配置和代码复杂性。
- Connector
.emptySessionPath
:此选项已移除。可以在全局 context.xml(位于CATALINA_BASE/conf/context.xml
中)中配置 sessionCookiePath="/" 来获得等效效果。 org.apache.catalina.SESSION_COOKIE_NAME
系统属性:此属性已移除。可以在全局 context.xml(位于CATALINA_BASE/conf/context.xml
中)中配置sessionCookieName
属性来获得等效效果。org.apache.catalina.SESSION_PARAMETER_NAME
系统属性:此属性已移除。可以在全局 context.xml(位于CATALINA_BASE/conf/context.xml
中)中配置sessionCookieName
属性来获得等效效果。- Context
.disableURLRewriting
:此选项已移除。可以在 Web 应用程序或全局CATALINA_BASE/conf/web.xml
文件中配置session-config/tracking-mode
元素来获得等效效果。
Tomcat 7 中的会话和 SSO Cookie 默认情况下会发送 HttpOnly 标志,以指示浏览器阻止 JavaScript 访问这些 Cookie。这被认为更安全,但它会阻止 JavaScript 访问 Cookie 的值。此功能可以通过 Context 元素上的 useHttpOnly
属性进行控制。(此功能也在最新版本的 Tomcat 6.0 中实现,但默认情况下处于关闭状态。可以通过在 Web 应用程序或全局 CATALINA_BASE/conf/context.xml
文件中的 Context 元素上设置 useHttpOnly="true"
来启用它)。
Cookie
默认情况下,Tomcat 不再接受不符合规范的仅名称 Cookie。但是,已添加了一个新的系统属性 org.apache.tomcat.util.http.ServerCookie.ALLOW_NAME_ONLY
,可用于接受仅名称 Cookie。
如果 Cookie 值或路径包含必须引用(根据 RFC2109 规范)的字符,则在将 Cookie 发送给客户端之前,Cookie 将自动从“版本 0”Cookie 转换为“版本 1”Cookie,并且这些值将被双引号包围。需要引用的字符由几个 系统属性 控制,例如 org.apache.tomcat.util.http.ServerCookie.FWD_SLASH_IS_SEPARATOR
。已知 Internet Explorer 在处理“版本 1”Cookie 时存在问题。(错误 57872)。
请求属性
用于访问 SSL 会话 ID 的自定义请求属性 javax.servlet.request.ssl_session
已弃用,取而代之的是 Servlet 规范中定义的新标准请求属性 javax.servlet.request.ssl_session_id
。对自定义属性的支持将在 Tomcat 8 中移除。
Comet
为了使 Comet 在安全管理器下运行时正常工作,Comet 类已从 org.apache.catalina
包移至 org.apache.catalina.comet
包。使用 Comet 的代码需要更新并重新编译以反映新的包名称。
XML 验证
XML 验证的配置已简化。xmlValidation
和 xmlNamespaceAware
属性已从 Host 元素中移除。这些属性以及 tldValidation
和 tldNamespaceAware
现在按 Context 元素设置。默认值(每个属性为 false
)未更改。但是,根据 Servlet 规范的要求,如果 org.apache.catalina.STRICT_SERVLET_COMPLIANCE
系统属性设置为 true
,则 XML 验证和命名空间感知将默认启用。
系统属性
已修改 org.apache.catalina.STRICT_SERVLET_COMPLIANCE
系统属性以对其效果提供更大的控制。现在,每个行为更改都由一个专用的系统属性控制。默认行为保持不变。org.apache.catalina.STRICT_SERVLET_COMPLIANCE
系统属性现在控制是否对其他系统属性使用符合规范的默认值。即使 org.apache.catalina.STRICT_SERVLET_COMPLIANCE
为 true
,设置单个系统属性也将始终优先。
已删除 org.apache.coyote.MAX_TRAILER_SIZE
,并由 Connector 的 maxTrailerSize 属性取代。
conf/web.xml 文件的处理
欢迎文件处理
已更改欢迎文件处理以遵循 Servlet 3.0 规范中的说明。如果您的欢迎文件列表包含由 servlet(例如 *.jsp)处理的文件,您可能会观察到行为的变化。请参阅 Context 上的 resourceOnlyServlets
选项。
注释扫描
Servlet 3.0 规范要求的注释扫描可能会影响 Web 应用程序的启动时间,并增加加载扫描类的内存需求。请注意,根据 Servlet EG 的说明,即使使用 Servlet 2.4 和更早版本的规范的应用程序也会被扫描。请参阅问题 53619 和用户邮件列表上的相关讨论。
有几种方法可以解决此问题。推荐的方法是将不需要注释扫描的应用程序标记为这样的应用程序。可以在应用程序的 WEB-INF/web.xml
中通过以下步骤完成
-
更新
web-app
元素以指示 Web 应用程序正在使用规范版本 3.0。可以从默认的conf/web.xml
文件中复制version
、xsi:schemaLocation
、xmlns
和xmlns:xsi
属性的值。 -
将
metadata-complete="true"
属性添加到web-app
元素。 -
添加一个空的
<absolute-ordering />
元素。
从 Servlet 2.5 规范开始支持 metadata-complete
属性。absolute-ordering
元素需要 Servlet 3.0。
第二种方法是配置 JarScanner 组件以根据 JAR 文件的名称忽略某些 JAR 文件。这通常在 conf/catalina.properties
文件中配置。有关 系统属性一章中 jarsToSkip
属性的文档,请参阅配置参考的详细信息。从 Tomcat 7.0.30 开始,可以分别配置为 Servlet 3.0 扫描(扫描注释和 Web 应用程序片段)、TLD 扫描(标签库)或两者跳过哪些 JAR。Tomcat 的更高版本可能会提供更好的方法来控制此功能。
TLD 处理
TLD 处理已经有了许多改进。除了进行一些内部重构以提高一致性和减少重复之外,还有一些功能改进。这些是
- 标签文件中的 EL 处理现在与为标签文件声明的 JSP 版本一致。
- 现在强制执行 JSP 规范的 JSP.7.3.1 部分的要求,并且不允许将 TLD 文件放置在
WEB-INF/lib
或WEB-INF/classes
中。
内部 API
虽然 Tomcat 7 内部 API 与 Tomcat 6 广泛兼容,但在细节级别上已经发生了许多更改,并且它们不是二进制兼容的。与 Tomcat 内部交互的自定义组件的开发人员应查看相关 API 的 JavaDoc。
特别要注意的是
- 所有组件都扩展的 Lifecycle 接口的标准实现。
- 使用泛型。
- 使用上下文名称而不是上下文路径作为主机中上下文的唯一标识符。
JSP 编译器
控制一项性能优化功能的 JspServlet
初始化参数已从 genStrAsCharArray 重命名为 genStringAsCharArray,现在与 Apache Ant 的 Jasper 任务中相关属性的名称一致。
升级 7.0.x
Tomcat 7.0.x 值得注意的更改
Tomcat 开发人员的目标是让每个修补程序版本与之前的版本完全向后兼容。有时,为了修复错误,需要打破向后兼容性。在大多数情况下,这些更改将不会被注意到。本节列出了不完全向后兼容并且在升级时可能导致中断的更改。
- 从 7.0.51 开始,Web 应用程序类加载器现在比系统类加载器加载类具有更高的优先级。
从 7.0.63 开始,连接器上
maxPostSize
属性的值 0 的含义已更改为表示零限制,而不是无限制,以使其与maxSavePostSize
保持一致并更直观。从 7.0.100 开始,AJP 连接器的默认侦听地址已更改为环回地址,而不是所有地址。
参考:AJP 连接器。
从 7.0.100 开始,AJP 连接器的 requiredSecret 属性已弃用,并被 secret 属性取代。
参考:AJP 连接器。
从 7.0.100 开始,secretRequired 属性已添加到 AJP 连接器。如果设置为默认值
true
,则 AJP 连接器在未指定 secret 时不会启动。参考:AJP 连接器。
从 7.0.100 开始,allowedRequestAttributesPattern 属性已添加到 AJP 连接器。具有无法识别的属性的请求现在将被 403 阻止。
参考:AJP 连接器。
Tomcat 7.0.x 配置文件差异
在将 Apache Tomcat 实例从一个 Tomcat 7 版本升级到另一个版本时,尤其是在为 $CATALINA_HOME 和 $CATALINA_BASE 使用单独位置时,必须确保配置中任何更改文件(例如新属性和默认值更改)都已作为升级的一部分应用。为了帮助识别这些更改,可以使用以下表单查看 Tomcat 7 不同版本中配置文件之间的差异。
从下面的框中选择一个配置文件、旧版本和新版本,然后单击“查看差异”以查看差异。差异将显示在一个新选项卡/窗口中。
注意:如果没有差异,您将看到一个错误页面。
您还可以在工作副本中使用类似于以下内容的 Git 命令
git diff 7.0.0 7.0.80 -- conf/