Puma 可以从变量读取 TLS 证书吗?

发布于 2025-01-09 04:41:31 字数 1832 浏览 0 评论 0原文

我们有一个在 Windows 中运行的使用 Puma 的 Rails 应用程序。到目前为止,我们已经将 SSL/TLS 证书存储在文件系统上,这似乎是一般标准,以及 Puma 的设计是在启动时获取该数据。

我们希望只在磁盘上保留一个加密的 PKCS#12 文件 (.12),该文件保存所有证书数据(一个或多个证书和私钥),在 puma 启动期间将特定证书提取到变量中,然后将其直接输入到 Puma ssl_bind 命令中。

因此,我试图弄清楚 Puma 是否可以接受保存证书数据的变量,而不是提供指向纯文本文件的预期 cert_path 和 key_path。

我尝试了几种不同的替换方法带有变量的文件路径,但到目前为止我只收到错误(例如见下文)。我已经从文件系统中输出了相同的证书密钥,它们对我来说看起来相同。我读过其他一些相关的 SO 线程,这些线程建议我可能需要添加换行符或以其他方式稍微操作变量中的数据,但到目前为止,这种思路让我感到困惑,我不确定它是否真的适合我的场景。我认为这归结为 ssl_bind 期望文件路径,并且可能在幕后运行“文件打开”逻辑。是不是根本不支持直接拿?

这是今天有效的示例:

# tls.key and tls.crt are already sitting on filesystem

ssl_bind '0.0.0.0', '443', {
key: 'certs/tls.key',
cert: 'certs/tls.crt', 
no_tlsv1: true,
no_tlsv1_1: true,
verify_mode: 'none'
}

这是我们想要做的示例

require 'openssl'

# get p12 password out of secrets at runtime
p12_password = Rails.application.credentials.p12[:password].to_s

# open encrypted p12 file 
p12 = OpenSSL::PKCS12.new(File.binread('certs/tls.p12'), p12_password)

# pull out certificate and key from p12
leafkey = p12.key.to_pem
leafcertificate = p12.certificate.to_pem       

ssl_bind '0.0.0.0', '443', {
    key: leafkey,
    cert: leafcertificate,
    no_tlsv1: true,
    no_tlsv1_1: true,
    verify_mode: 'none'
    }

我们从上面收到的错误是:

C:/Ruby27-x64/lib/ruby/gems/2.7.0/gems/puma-4.3.8/lib/puma/minissl.rb:209:in `key=': No such key file '-----BEGIN EC PRIVATE KEY-----MDECAQEEIBccaYhSLodf 4TRzzWkOE5rr8t Ul0oQHcjYmmoiuvloAoGCCqGSM4jdu73-----END EC PRIVATE KEY-----' (ArgumentError)

这是有效的 EC 密钥数据,但 Puma/ssl_bind 看起来很困惑(毫不奇怪),它不是磁盘上包含此数据的文件的预期路径。 我们可以通过这种方式欺骗 Puma 直接接受它吗?

感谢您阅读并花时间表达您的任何想法!

We have a Rails app running in Windows that uses Puma. So far we've stored our SSL/TLS certificates on the filesystem, which seems to be the standard in general, and the way Puma is designed to take in that data when starting up.

We would like to instead keep only an encrypted PKCS#12 file (.12) on disk, that holds all certificate data (one or more certificates and the private key), pulls out the specific certs during puma start up into variables, and then feeds that directly into the Puma ssl_bind command.

So I'm trying to figure out if Puma can accept variables that hold certificate data, as opposed to providing the expected cert_path and key_path that point at plaintext files.

I've tried a few different ways of replacing the file paths with variables, but I only get errors so far (see below for example). I've output the cert key along side the same from the file system, and they look identical to me. I've read other somewhat related SO threads that suggest maybe I need to add newlines or otherwise slightly manipulate the data in my variables, but that line of thinking has confused me so far and I'm not sure if it really pertains to my scenario. I think it comes down to ssl_bind expecting a file path, and likely running "file open" logic under the hood. Does it simply not support taking it directly?

Here is an example of what works today:

# tls.key and tls.crt are already sitting on filesystem

ssl_bind '0.0.0.0', '443', {
key: 'certs/tls.key',
cert: 'certs/tls.crt', 
no_tlsv1: true,
no_tlsv1_1: true,
verify_mode: 'none'
}

Here is an example of what we want to do

require 'openssl'

# get p12 password out of secrets at runtime
p12_password = Rails.application.credentials.p12[:password].to_s

# open encrypted p12 file 
p12 = OpenSSL::PKCS12.new(File.binread('certs/tls.p12'), p12_password)

# pull out certificate and key from p12
leafkey = p12.key.to_pem
leafcertificate = p12.certificate.to_pem       

ssl_bind '0.0.0.0', '443', {
    key: leafkey,
    cert: leafcertificate,
    no_tlsv1: true,
    no_tlsv1_1: true,
    verify_mode: 'none'
    }

The error we receive from the above is:

C:/Ruby27-x64/lib/ruby/gems/2.7.0/gems/puma-4.3.8/lib/puma/minissl.rb:209:in `key=': No such key file '-----BEGIN EC PRIVATE KEY-----MDECAQEEIBccaYhSLodf 4TRzzWkOE5rr8t Ul0oQHcjYmmoiuvloAoGCCqGSM4jdu73-----END EC PRIVATE KEY-----' (ArgumentError)

This is the valid EC key data, but Puma/ssl_bind appears confused (not surprisingly) that it's not the expected path to a file on disk that contains this data. Can we trick Puma into accepting it directly this way?

Thank you for reading and taking the time to express any thoughts you may have!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

娇纵 2025-01-16 04:41:31

此要求是作为增强功能添加到 此 PR

到目前为止,我似乎能够将 Puma 从 4.3.8 直接更新到 5.6.2,没有任何麻烦。我们确实需要将 2 个选项更新为 *_pem 版本,即

cert 变为 cert_pem< /em> 和
key 变成 key_pem

有了这个,它就可以工作了。

使用 puma 5.6.2 运行的示例:

require 'openssl'

# using cleartext password for testing/simplicity
p12 = OpenSSL::PKCS12.new(File.binread('certs/tls.p12'), "1234")

leafcertificate = p12.certificate.to_pem
leafkey = p12.key.to_pem

ssl_bind '0.0.0.0', '443', {
    cert_pem: leafcertificate,
    key_pem:  leafkey,
    no_tlsv1: true,
    no_tlsv1_1: true
    }

个人经验教训:我应该优先深入研究 Puma 存储库:拉取请求、问题等。

This requirement was added as a enhancement in this PR

So far it looks like I was able to update Puma from 4.3.8 directly to 5.6.2 without any fuss. We did need to update 2 options to the *_pem versions, i.e.,

cert becomes cert_pem and
key becomes key_pem

With this in place, it JUST WORKED.

Example running with puma 5.6.2:

require 'openssl'

# using cleartext password for testing/simplicity
p12 = OpenSSL::PKCS12.new(File.binread('certs/tls.p12'), "1234")

leafcertificate = p12.certificate.to_pem
leafkey = p12.key.to_pem

ssl_bind '0.0.0.0', '443', {
    cert_pem: leafcertificate,
    key_pem:  leafkey,
    no_tlsv1: true,
    no_tlsv1_1: true
    }

Personal lessons learned: I should have prioritized digging into the Puma repo: pull requests, issues, etc.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文