<!DOCTYPE html>
<html>
<meta charset="UTF-8">
<script src="./../dist/pako.js"></script>
<script>
const obj = [
{ foo: 'bar', baz: 'baz' },
{ abra: 1, cadabra: 22222222222222222 }
]
let result = pako.gzip(encodeURIComponent(JSON.stringify(obj)), { to: "string" });
function send(result) {
var xhr = new XMLHttpRequest;
xhr.open('POST', 'http://www.yd.com/open/test', true);
xhr.send(result);
}
send(result);
</script>
</html>
<body>
Sending objects to server, run server code to see result.
</body>
php接收端
laravel8框架 php8
$in = file_get_contents("php://input");
p($in);
$res = json_decode(urldecode(gzdecode($in)), true);
p($res);
可以正常接受解壓數(shù)據(jù)
但是在webman socket數(shù)據(jù)就會出問題
gzdecode 出現(xiàn)data error
/*
* {
createTime: 命令發(fā)送時間
data:{} 修改的命令
id: "7a" websocket的id
returnMessage: "success"
status: "0" 0告訴前端需要根據(jù)data的命令修改 1無意義
type: 0:連接成功,1:發(fā)送給當前連接的用戶,2:發(fā)送信息給其他用戶,3:發(fā)送選區(qū)位置信息,999:用戶連接斷開
username: 用戶名
}
* ?m?A? EO?^¨??′r?.*?a¥?ú??qá????g??R ?è?8c._uá*??efy Taafví?@+[?&??#?àA@*^ò.ü<?òD?t?2?W????tT· ÷?a?×kDZ??? ?5Tk(K?O?a8?′?hC·R bl±?Y? u?W
*/
public function onMessage(TcpConnection $connection, $data)
{
$key = $this->getUid($connection->getLocalIp(), $connection->getLocalPort(), $connection->worker->workerId, $connection->worker->id, $connection->id);
$return = [];
$return['createTime'] = time();
$return['data'] = null;
$return['returnMessage'] = 'success';
$return['status'] = '1';
$return['type'] = 0;
$return['id'] = $key;
$return['username'] = $key;
if ($data == 'rub') {
//心跳不回復(fù)
} else {
$in = json_decode(urldecode(gzdecode($data)), true);
// $this->broadcast($key, $data);
// $connection->send(json_encode($return));
// $connection->send($data);
}
}
數(shù)據(jù)格式是 pako加密的
let result = pako.gzip(encodeURIComponent(JSON.stringify(obj)), { to: "string" });
接受到的數(shù)據(jù)格式
目前懷疑是 回調(diào)的onMessage $data數(shù)據(jù)返回有問題導(dǎo)致無法正解析
2022年9月21日09:52:36
終于解決了webman對接問題
因為現(xiàn)在php8 default_charset = "UTF-8" PHP的默認處理字符集是utf-8
但是gzip的默認字符集是 ISO-8859-1, gzdecode函數(shù)處理也需要 ISO-8859-1字符集
參考了java版本的代碼發(fā)現(xiàn)他也是轉(zhuǎn)還了字符集
public static String uncompress(String str) throws IOException {
if (str == null || str.length() == 0) {
return str;
}
ByteArrayOutputStream out = new ByteArrayOutputStream();
ByteArrayInputStream in = new ByteArrayInputStream(str.getBytes("ISO-8859-1"));
GZIPInputStream gunzip = new GZIPInputStream(in);
byte[] buffer = new byte[256];
int n;
while ((n = gunzip.read(buffer)) >= 0) {
out.write(buffer, 0, n);
}
// toString()使用平臺默認編碼,也可以顯式的指定如toString("GBK")
return out.toString();
}
str.getBytes("ISO-8859-1"),我就嘗試轉(zhuǎn)換了一下
$content = mb_convert_encoding($data, 'ISO-8859-1', 'utf-8');
var_dump(json_decode(urldecode(gzdecode($content)), true));
然后就解析成功了,現(xiàn)在php對接Luckysheet也可以了
我覺得可能是你前端代碼問題,你沒發(fā)websocket前端代碼,所以問你前端代碼在哪?結(jié)果你還是沒貼...
我測試沒問題
process/Ws.php
<?php
namespace process;
class Ws
{
public function onMessage($con, $data)
{
var_export(json_decode(urldecode(gzdecode($data)), true));
}
}
config/process.php
<?php
return [
'ws' => [
'handler' => \process\Ws::class,
'listen' => 'websocket://0.0.0.0:1234'
]
];
前端代碼
const obj = [
{ foo: 'bar', baz: 'baz' },
{ abra: 1, cadabra: 22222222222222222 }
]
let result = pako.gzip(encodeURIComponent(JSON.stringify(obj)), { to: "string" });
ws = new WebSocket('ws://127.0.0.1:1234');
ws.onopen = function(){
ws.send(result);
}
打印結(jié)果