为什么在Mac上,curl使用HTTP/1.1而不是HTTP/2?

4
根据这个链接 https://curl.haxx.se/docs/http2.html
自7.47.0版本以来,curl工具默认启用HTTPS连接的HTTP/2协议。
通过homebrew安装最新版本并检查:
curl --version
curl 7.54.1 (x86_64-apple-darwin15.6.0) libcurl/7.54.1 SecureTransport zlib/1.2.5

但当我在启用HTTP2的URL上运行curl时(例如使用https://tools.keycdn.com/http2-test进行测试),出现以下情况:

curl -I http://www.google.co.uk 
HTTP/1.1 200 OK

并且

curl --http2 -v http://www.google.co.uk
curl: (1) Unsupported protocol

你知道为什么它使用的是HTTP/1.1而不是HTTP/2吗?

2个回答

8
您可以构建curl以使用许多不同的TLS/SSL库之一,每个库都具有略微不同的功能集,并提供略微不同的条件,使curl能够正常工作。
在您的问题中显示的curl列出了SecureTransport作为其构建使用的TLS库,即macOS本机TLS库。
Secure Transport根本无法提供curl协商HTTP/2 over TLS所需的手段 - 或者至少它还没有,因为我被告知最新版本现在支持ALPN,所以未来的curl版本应该能够通过Secure Transport进行HTTP/2 over TLS。
除了适当的TLS协商外,curl还需要使用古老的nghttp2库来处理HTTP/2,因此这是curl能够处理HTTP/2所需的第二个依赖项。如果nghttp2存在,则即使TLS库无法正确协商ALPN,curl也可以在纯文本HTTP上使用HTTP/2。
修复方法?
较新的macOS版本附带了内置libreSSL和HTTP/2支持的curl。
如果您选择改用其他TLS库(例如OpenSSL、GnuTLS或NSS)重新构建curl,则它已经可以通过HTTPS很好地处理HTTP/2。

请注意,在SecureTransport中启用HTTP/2协商的函数是SSLSetALPNProtocols。它可在iOS 11+和macOS 10.13+上使用。 - Guillaume Algis
3
同时,苹果已经更换并现在发运的curl已经构建为使用libressl... - Daniel Stenberg
1
哦,不知道那个。那真是令人惊讶。 - Guillaume Algis

3
使用OpenSSL来安装支持HTTP2的更新版本curl是如何在MacOS Sierra上进行的。
1. 重新安装curl并添加OpenSSL与nghttp2组件:
``` brew reinstall curl --with-openssl --with-nghttp2 ```
2. 强制链接新版本的curl:
``` brew link curl --force ```
3. 重启终端
4. 输入 `curl -V` 命令,确认是否成功安装了新版curl,并返回以下信息:
``` curl 7.54.1 (x86_64-apple-darwin16.6.0) libcurl/7.54.1 OpenSSL/1.0.2l zlib/1.2.8 nghttp2/1.24.0 Release-Date: 2017-06-14 Protocols: dict file ftp ftps gopher http https imap imaps ldap ldaps pop3 pop3s rtsp smb smbs smtp smtps telnet tftp Features: IPv6 Largefile NTLM NTLM_WB SSL libz TLS-SRP HTTP2 UnixSockets HTTPS-proxy ```
需要注意,MacOS系统的小版本更新可能会覆盖现有的curl版本。如果这种情况发生,请重新运行 `brew link curl --force` 命令,并重启终端以切换到homebrew的支持HTTP2的新版本。

1
附注:macOS High Sierra自带curl 7.54.0,并且内置了对HTTP2的支持。 - Chris

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接