从安全源获取请求主机名?

时间:2017-08-21 22:01:05

标签: java jsp tomcat

我在网站上进行安全检查,我们有一些代码可以执行以下操作:

<link rel="stylesheet" href="<%=request.getScheme()%>://<%=request.getServerName() %>:<%=request.getServerPort()%><%= request.getContextPath() %>/css/<fmt:bundle basename="version"><fmt:message key="build.date"/><fmt:message key="js.path.separator"/></fmt:bundle>${relativePath}" media="all" type="text/css" />

根本原因是构建一个包含构建版本的CSS路径,以强制浏览器加载最新的CSS文件并避免缓存问题。

不幸的是,构造的第一部分使用request.getServerName()来构造URL。事实证明,这引用了来自传入请求的HOST头。这是一个安全漏洞,因为标头可能被欺骗,导致生成的链接引用另一个站点而不是本地站点。

有更安全的方法吗?我曾想过在应用程序上下文中添加一个值,但想知道是否有更好的方法来执行此操作。

1 个答案:

答案 0 :(得分:2)

您不应该使用scheme,serverName或serverPort来构建您的URL,因为这些都默认为相对于当前请求。

如果您的网页位于https://example.com:8081/project/pages/things.html,那么您的示例/project/css/<version><build-date>.css中的链接就会解析为https://example.com:8081/project/css/<version><build-date>.css,因此您可以将这些部分保留下来

<link rel="stylesheet" href="<%= request.getContextPath()
     %>/css/<fmt:bundle basename="version">
            <fmt:message key="build.date"/>
            <fmt:message key="js.path.separator"/>
            </fmt:bundle>${relativePath}" media="all" type="text/css" />