PHP 7.1:HTTP/2 没有 cURL
PHP 7.1: no cURL with HTTP/2
我的问题不是查明服务器是否支持 HTTP/2(他们都支持),而是如何确保 PHP 使用 HTTP/2 CentOS 中最新 PHP 版本的正确 cURL 设置(从 Remi 的存储库构建)。我自己的回答解决了一些与此有关的奇怪之处。
我已经设置我的 CentOS 7 服务器以支持 HTTP/2 借助这个很好的指南:Setting up HTTP/2 on your web server
所以我得到了最新版本,编译并安装了它们,一切正常。页面以 HTTP/2 headers 提供,完全按照它们应有的方式提供。
现在我想在我的 PHP 脚本中使用 HTTP/2 功能。主要是通过 HTTP/2 方式进行 cURL 调用。我发现我需要升级 libcurl
并使用特定的 HTTP/2 支持来构建和编译它。经历了一些挫折,我成功了。
所以 curl -V
告诉我:
curl 7.55.0-DEV (x86_64-unknown-linux-gnu) libcurl/7.55.0-DEV OpenSSL/1.1.0f zlib/1.2.7 nghttp2/1.23.1
Release-Date: [unreleased]
Protocols: dict file ftp ftps gopher http https imap imaps pop3 pop3s rtsp smb smbs smtp smtps telnet tftp
Features: IPv6 Largefile NTLM NTLM_WB SSL libz TLS-SRP HTTP2 UnixSockets HTTPS-proxy
太棒了!
和phpinfo()
结合新安装的OpenSSL给我相同的版本(7.55.0-DEV
),即:
OpenSSL 1.1.0f 25 May 2017
还有 Apache,顺便说一句:
Server version: Apache/2.4.26 (Unix)
Server built: Jul 7 2017 09:47:22
但是,当我使用 cURL 调用编写一个简单的 PHP 脚本并将 CURLOPT_HTTP_VERSION
选项设置为 CURL_HTTP_VERSION_2_0
时,如本例所述:,它告诉我服务器没有 HTTP/2 支持...
怎么会这样?
我注意到的一件事是 phpinfo()
中关于 OpenSSL 模块的部分仍然提到了我的旧 OpenSSL 版本(OpenSSL 1.0.1e-fips),尽管 OpenSSL-version 提到了 cURL 模块声明 OpenSSL 1.1.0f.
我已经从 Remi 的存储库安装了 PHP 7.1(目前版本为 7.1.7),它是否是针对旧的 OpenSSL 版本构建的,所以它不能与我的新版本一起使用?我还阅读了 PHP 7 中的支持,因为 HTTP/2 不是很明显,但我想这应该不是问题,对吗?
或者 OpenSSL 不是问题所在,我应该看看其他地方,也许从带有一些预期标志的源代码编译 PHP?
我存储库中的包是针对标准基本存储库构建的,因此 OpenSSL 1.0.1e 和 Curl 7.29.0(使用 NSS)。
所以你必须重建所有使用这些库的东西来利用新功能(包括PHP)
经过一些摆弄,我似乎 可以 通过 PHP cURL 调用 Remi 的 PHP 包和一个 HTTP/2 得到一个响应新建 cURL/OpenSSL.
我正在使用这段代码进行测试(摘自):
if (curl_version()["features"] & CURL_VERSION_HTTP2 !== 0) {
$url = "https://www.google.com/";
$ch = curl_init();
curl_setopt_array($ch, [
CURLOPT_URL =>$url,
CURLOPT_HEADER =>true,
CURLOPT_NOBODY =>true,
CURLOPT_RETURNTRANSFER =>true,
CURLOPT_HTTP_VERSION =>CURL_HTTP_VERSION_2_0,
]);
$response = curl_exec($ch);
if ($response !== false && strpos($response, "HTTP/2.0") === 0) {
echo "HTTP/2 support!";
} elseif ($response !== false) {
echo "No HTTP/2 support on server.";
} else {
echo curl_error($ch);
}
curl_close($ch);
} else {
echo "No HTTP/2 support on client.";
}
所需的调整是:
CURLOPT_HTTP_VERSION => 3
...和:
if ($response !== false && strpos($response, "HTTP/2") === 0)
因此,我在 cURL 选项中使用了 3
,而不是 CURL_HTTP_VERSION_2_0
作为 HTTP 版本,这应该意味着相同,但显然 PHP 在使用 CURL_HTTP_VERSION_2_0
.
查看这给出的原始响应,我注意到 Google 正在发回 HTTP/2
而不是 HTTP/2.0
。
希望对大家有所帮助!
我的问题不是查明服务器是否支持 HTTP/2(他们都支持),而是如何确保 PHP 使用 HTTP/2 CentOS 中最新 PHP 版本的正确 cURL 设置(从 Remi 的存储库构建)。我自己的回答解决了一些与此有关的奇怪之处。
我已经设置我的 CentOS 7 服务器以支持 HTTP/2 借助这个很好的指南:Setting up HTTP/2 on your web server
所以我得到了最新版本,编译并安装了它们,一切正常。页面以 HTTP/2 headers 提供,完全按照它们应有的方式提供。
现在我想在我的 PHP 脚本中使用 HTTP/2 功能。主要是通过 HTTP/2 方式进行 cURL 调用。我发现我需要升级 libcurl
并使用特定的 HTTP/2 支持来构建和编译它。经历了一些挫折,我成功了。
所以 curl -V
告诉我:
curl 7.55.0-DEV (x86_64-unknown-linux-gnu) libcurl/7.55.0-DEV OpenSSL/1.1.0f zlib/1.2.7 nghttp2/1.23.1
Release-Date: [unreleased]
Protocols: dict file ftp ftps gopher http https imap imaps pop3 pop3s rtsp smb smbs smtp smtps telnet tftp
Features: IPv6 Largefile NTLM NTLM_WB SSL libz TLS-SRP HTTP2 UnixSockets HTTPS-proxy
太棒了!
和phpinfo()
结合新安装的OpenSSL给我相同的版本(7.55.0-DEV
),即:
OpenSSL 1.1.0f 25 May 2017
还有 Apache,顺便说一句:
Server version: Apache/2.4.26 (Unix)
Server built: Jul 7 2017 09:47:22
但是,当我使用 cURL 调用编写一个简单的 PHP 脚本并将 CURLOPT_HTTP_VERSION
选项设置为 CURL_HTTP_VERSION_2_0
时,如本例所述:
怎么会这样?
我注意到的一件事是 phpinfo()
中关于 OpenSSL 模块的部分仍然提到了我的旧 OpenSSL 版本(OpenSSL 1.0.1e-fips),尽管 OpenSSL-version 提到了 cURL 模块声明 OpenSSL 1.1.0f.
我已经从 Remi 的存储库安装了 PHP 7.1(目前版本为 7.1.7),它是否是针对旧的 OpenSSL 版本构建的,所以它不能与我的新版本一起使用?我还阅读了 PHP 7 中的支持,因为 HTTP/2 不是很明显,但我想这应该不是问题,对吗?
或者 OpenSSL 不是问题所在,我应该看看其他地方,也许从带有一些预期标志的源代码编译 PHP?
我存储库中的包是针对标准基本存储库构建的,因此 OpenSSL 1.0.1e 和 Curl 7.29.0(使用 NSS)。
所以你必须重建所有使用这些库的东西来利用新功能(包括PHP)
经过一些摆弄,我似乎 可以 通过 PHP cURL 调用 Remi 的 PHP 包和一个 HTTP/2 得到一个响应新建 cURL/OpenSSL.
我正在使用这段代码进行测试(摘自
if (curl_version()["features"] & CURL_VERSION_HTTP2 !== 0) {
$url = "https://www.google.com/";
$ch = curl_init();
curl_setopt_array($ch, [
CURLOPT_URL =>$url,
CURLOPT_HEADER =>true,
CURLOPT_NOBODY =>true,
CURLOPT_RETURNTRANSFER =>true,
CURLOPT_HTTP_VERSION =>CURL_HTTP_VERSION_2_0,
]);
$response = curl_exec($ch);
if ($response !== false && strpos($response, "HTTP/2.0") === 0) {
echo "HTTP/2 support!";
} elseif ($response !== false) {
echo "No HTTP/2 support on server.";
} else {
echo curl_error($ch);
}
curl_close($ch);
} else {
echo "No HTTP/2 support on client.";
}
所需的调整是:
CURLOPT_HTTP_VERSION => 3
...和:
if ($response !== false && strpos($response, "HTTP/2") === 0)
因此,我在 cURL 选项中使用了 3
,而不是 CURL_HTTP_VERSION_2_0
作为 HTTP 版本,这应该意味着相同,但显然 PHP 在使用 CURL_HTTP_VERSION_2_0
.
查看这给出的原始响应,我注意到 Google 正在发回 HTTP/2
而不是 HTTP/2.0
。
希望对大家有所帮助!