部署在代理后面时,Grails 会生成正确的链接

Grails generating proper links when deployed behind proxy

为已部署的 Grails 应用程序考虑以下设置。

到目前为止,这是一个非常标准的设置,我已经成功使用了很多次。我现在的问题是 Grails 应用程序生成的链接,尤其是那些用于重定向的链接(标准控制器重定向,它一直发生,例如在成功发布表单之后)。

到目前为止,一个配置与所有其他应用程序不同:在此 Grails 应用程序中 未配置 serverURL。该应用程序是一个多租户应用程序,其中每个租户都有自己的子域。 (因此,如果应用程序通常在 https://www.example.com, a tenant can use https://tenant.example.com 下 运行。)子域是自动设置的,即在 DNS 或 Apache 级别没有任何配置。 Grails 可以完美地做到这一点,通过在 Config.groovy 中省略 serverURL 属性:然后它通过检查客户端主机解析所有 url。

但是:在生成重定向-url 时,Grails 不知道该网站是 运行 在 https 下。所有重定向 url 都以 http 开头...我想这并不奇怪,因为在应用程序中没有配置我们使用 https:没有 serverURL 配置,从技术上讲应用程序 运行 在 Tomcat 的标准 http 端口上,因为 Apache 的 SSL 卸载和代理。

所以,最重要的是:我可以做些什么来让 Grails 生成正确的重定向?

我已尝试扩展 DefaultLinkGenerator 并覆盖 makeServerURL() 方法。像这样:

class MyLinkGenerator extends DefaultLinkGenerator {

MyLinkGenerator(String serverBaseURL, String contextPath) {
    super(serverBaseURL, contextPath)
}

MyLinkGenerator(String serverBaseURL) {
    super(serverBaseURL)
}

def grailsApplication

/**
 * @return serverURL adapted to deployed scheme
 */
String makeServerURL() {
    // get configured protocol
    def scheme = grailsApplication.config.grails.twt.baseProtocol ?: 'https://'
    println "Application running under protocol $scheme"

    // get url from super
    String surl = super.makeServerURL()
    println "> super.makeServerURL(): $surl"
    if (surl) {
        // if super url not matching scheme, change scheme
        if (scheme=='https://' && surl?.startsWith('http://')) {
            surl = scheme + surl?.substring(7)
            println "> re-written: $surl"
        }
    }

    return surl

}

}

(也许不是最漂亮的代码,但我希望它能解释我想做的事情。我在 resources.groovy 中省略了关于配置此 class 的内容。)

当运行这段代码奇怪的事情发生时:

如有任何帮助或见解,我们将不胜感激!

顺便说一句,Grails 版本是 2.1.1(运行 升级有点落后...)。

您似乎总是在与外界进行 https 通信,因此您最干净的选择是在您的 Apache 网络服务器上解决问题的源头。添加到 httpd.conf Header edit Location ^http://(.*)$ https://,你就完成了。

如果您有限制迫使您在应用程序中解决这个问题,您可以在拦截器之后重写 Grails 中的 Location header 字段。该解决方案的详细信息在 this post.

写这个问题已经过去了很多年,但问题仍然相同或至少相似;-)

以防万一有人遇到 same/similar 问题(Grails 重定向 URL 是 http 而不是 https)...我们遇到了这个问题 OpenShift 上的 Grails 3.3.9 应用程序 运行。 应用程序 运行 处于 HTTP 模式(在端口 8080 上)并且 OpenShift 负载均衡器正在执行 SSL 终止。

我们把

解决了
server:
  use-forward-headers: true

进入我们的application.yml。在那之后 Grails 完美运行并且创建的所有重定向都是正确的 https://.

提示:我们没有在我们的配置中使用grails.serverURL