force_ssl 在 Rails 中做了啥?

Posted

技术标签:

【中文标题】force_ssl 在 Rails 中做了啥?【英文标题】:What does force_ssl do in Rails?force_ssl 在 Rails 中做了什么? 【发布时间】:2013-03-18 13:57:27 【问题描述】:

在之前的question 中,我发现我应该设置 nginx ssl 终止并且不让 Rails 处理加密数据。

那为什么会存在下面呢?

config.force_ssl = true

我看到这个在生产配置文件中被注释掉了。但是,如果期望 nginx 将处理所有 ssl 内容,以便我的 rails 应用程序不处理加密数据,那么 config.force_ssl = true 会做什么?

如果我知道我将一直使用 nginx,是否应该在生产环境中将其注释掉?

【问题讨论】:

【参考方案1】:

它强制与服务器的所有通信都被加密并使用 SSL,即通过 HTTPS。

当您将它包含在控制器中时,该控制器将只接受 HTTPS 请求。

有用的链接:

    http://api.rubyonrails.org/classes/ActionController/ForceSSL/ClassMethods.html http://rubydoc.info/docs/rails/ActionController/ForceSSL http://railscasts.com/episodes/270-authentication-in-rails-3-1?view=comments

【讨论】:

【参考方案2】:

设置config.force_ssl 包括ActionDispatch::SSLActionDispatch::SSL 文档描述的功能如下(为清楚起见添加了重点):

请参阅包含 here 和 ActionDispatch::SSL here 的文档。

文档

此中间件在config.force_ssl = true 时被添加到堆栈中,并传递config.ssl_options 中设置的选项。它执行三项工作来强制执行安全的 HTTP 请求:

    TLS 重定向:将 http:// 请求永久重定向到 https:// 具有相同的 URL 主机、路径等。默认启用。设置config.ssl_options 修改目标 URL (例如redirect: host: "secure.widgets.com", port: 8080 ),或设置 redirect: false 禁用此功能。

    安全 cookie:在 cookie 上设置 secure 标志以告诉浏览器它们 不得与 http:// 请求一起发送。默认启用。放 config.ssl_optionssecure_cookies: false 禁用此功能。

    HTTP 严格传输安全 (HSTS):告诉浏览器记住 此站点为 TLS-only 并自动重定向非 TLS 请求。 默认启用。将config.ssl_options 配置为hsts: false 以禁用。 设置config.ssl_optionshsts: … 来配置HSTS:

    expires:这些设置会持续多久,以秒为单位。默认为 180.days(推荐)。获得浏览器资格所需的最低要求 预加载列表是18.weekssubdomains:设置为true 告诉浏览器应用这些设置 到所有子域。这可以保护您的 cookie 不被 子域上的易受攻击的站点。默认为truepreload: 宣传本站可能被浏览器收录 预加载的 HSTS 列表。 HSTS 会在每次访问时保护您的网站除了 第一次访问,因为它还没有看到您的 HSTS 标头。关闭这个 差距,浏览器供应商包括一个内置的支持 HSTS 的站点列表。 转到https://hstspreload.appspot.com 提交您的网站以供收录。 要关闭 HSTS,省略标头是不够的。浏览器会记住原始的 HSTS 指令,直到它过期。相反,使用标头告诉浏览器立即使 HSTS 过期。设置hsts: falsehsts: expires: 0 的快捷方式。

请求可以通过exclude 选择退出重定向:

config.ssl_options =  redirect:  exclude: -> request  request.path =~ /healthcheck/   

【讨论】:

"请求可以通过exclude 选择退出重定向" - 警告:此功能最近才在 Rails 5 中添加,因此不适用于 Rails 4.2 或更低版本的用户跨度> 我相信 exclude 全局选项在 Rails 5 之前很长一段时间就可用了,所以它的语法略有不同:config.ssl_options = exclude: proc |env| env['PATH_INFO'].start_with?('/healthcheck/') — serverfault.com/a/517401【参考方案3】:

它不会只是强制您的浏览器将 HTTP 重定向到 HTTPS。它还将您的 cookie 设置为标记为“安全”,并启用HSTS,其中每一个都是非常好的防止 SSL 剥离的保护措施。

尽管 HTTPS 可以保护您在“https://example.com/yourapp”上的应用免受 MITM 攻击,但如果有人在您的客户端和您的服务器之间闯入,他们很容易让您访问“http://example.com/yourapp”。如果没有上述保护措施,您的浏览器会很乐意将会话 cookie 发送给执行 MITM 的人。

【讨论】:

force_ssl 的来源不包含此选项启用 HSTS 的指示 @agios 这是一个单独的每个控制器 force_ssl 属性。 force_ssl 配置变量,用于安装Rack::SSL 中间件,其中does enable HSTS by default。 @agios 你找错地方了:github.com/rails/rails/blob/… 听起来config.force_ssl = true应该是默认的,为什么rails团队将其注释为默认?【参考方案4】:

此设置通过将 HTTP 请求重定向到相应的 HTTPS 来强制使用 HTTPS。所以访问http://domain.com/path的浏览器会被重定向到https://domain.com/path

将设置注释掉将允许两种协议。

您仍然需要配置您的网络服务器来处理 HTTPS 请求。

【讨论】:

但是如果你在 nginx 级别启用 HTTPS(通过redirect 301 https:... 将所有内容重定向到 HTTPS),就不会所有事情都通过 https,因此config.force_ssl = true 并没有真正做任何事情(因为什么都没有将永远是http)?还是这里有更深层次的安全原因? @TristanTao 是的,那也可以。但即便如此,我也会启用config.force_ssl,以防有人从网络服务器的配置中删除重定向。 小心点,config.force_ssl 与控制器中的 force_ssl 在保护 cookie 免受会话劫持方面略有不同:eq8.eu/blogs/… 另请注意,同时拥有config.force_ssladd_header Strict-Transport-Security max-age=...; 将产生2 个Strict-Transport-Security 标头

以上是关于force_ssl 在 Rails 中做了啥?的主要内容,如果未能解决你的问题,请参考以下文章

nextState 在 shouldComponentUpdate 中做了啥?

BuildContext 在 Flutter 中做了啥?

retranslateUi 在 PyQT 中做了啥

elementFormDefault 在 XSD 中做了啥?

InputStream.available() 在 Java 中做了啥?

=== 在 PHP 中做了啥