Hyperf 是一个高性能、高灵活性的渐进式 PHP 协程框架,内置协程服务器及大量常用的组件,性能较传统基于
PHP-FPM
的框架有质的提升,提供超高性能的同时,也保持着极其灵活的可扩展性,标准组件均基于PSR 标准实现,基于强大的依赖注入设计,保证了绝大部分组件或类都是可替换
与可复用
的。(简短介绍来源于:https://hyperf.wiki/3.1/#/)
问题一:需要接收其他客户端发送的二进制数据(GZIP压缩的数据)
在初期我以为是只要在NGINX端开启支持GZIP即可,后面发现NGINX的GZIP开关并不会影响其他客户端发送来的请求数据。框架默认只支持json格式,后面通过查看Issues发现有别人踩过类似的坑(需求)#5488。
<?php
declare(strict_types=1);
/**
* This file is part of Hyperf.
*
* @link https://www.hyperf.io
* @document https://hyperf.wiki
* @contact group@hyperf.io
* @license https://github.com/hyperf/hyperf/blob/master/LICENSE
*/
namespace HyperfHttpMessageServer;
use HyperfHttpMessageExceptionBadRequestHttpException;
use HyperfHttpMessageServerRequestParser;
use HyperfHttpMessageStreamSwooleStream;
use HyperfHttpMessageUploadUploadedFile;
use HyperfHttpMessageUriUri;
use HyperfUtilsApplicationContext;
use PsrHttpMessageRequestInterface;
use PsrHttpMessageServerRequestInterface;
use PsrHttpMessageUploadedFileInterface;
class Request extends HyperfHttpMessageBaseRequest implements ServerRequestInterface
{
// ...省略多余代码 只展示关键改动代码
protected static function normalizeParsedBody(array $data = [], ?RequestInterface $request = null)
{
if (! $request) {
return $data;
}
$rawContentType = $request->getHeaderLine('content-type');
if (($pos = strpos($rawContentType, ';')) !== false) {
// e.g. text/html; charset=UTF-8
$contentType = strtolower(substr($rawContentType, 0, $pos));
} else {
$contentType = strtolower($rawContentType);
}
try {
$parser = static::getParser();
// 此处新增对Gzip的请求头处理
$content = (string) $request->getBody();
if (strpos($request->getHeaderLine('content-encoding'), 'gzip') !== false && substr($content, 0, 2) == "x1fx8b") {// str_contains($request->getHeaderLine('content-encoding'), 'gzip')
// 如果有gzip请求头,对请求content进行gz解压(为求稳 同时判断前面的字节是否为二进制)
$content = gzdecode("$content");
}
if ($parser->has($contentType) && $content) {
$data = $parser->parse($content, $contentType);
}
} catch (InvalidArgumentException $exception) {
throw new BadRequestHttpException($exception->getMessage());
}
return $data;
}
}
以上代码块是我基于自己开发环境中实际改动调整的地方;由于生产环境是2.2版本,遂自行进行一定改动。
总结
通过本次解决问题,复习及学习了几个PHP
函数
strpos()
(PHP 4, PHP 5, PHP 7, PHP 8)
substr()
(PHP 4, PHP 5, PHP 7, PHP 8)
str_contains()
(PHP 8)
gzuncompress()
(PHP 4 >= 4.0.1, PHP 5, PHP 7, PHP 8)
gzdecode()
(PHP 5 >= 5.4.0, PHP 7, PHP 8)
我正在参与2023腾讯技术创作特训营第四期有奖征文,快来和我瓜分大奖!