客戶端php 截選如下
$r='';
do {
$r.=fread($fp, 1024);
$s=stream_get_meta_data($fp);
} while ($s);
接收有時(shí)候不足 8192 有時(shí)到了8192 沒(méi)了,大家有遇到這個(gè)問(wèn)題嗎?
tcp是流式的,數(shù)據(jù)是分批發(fā)過(guò)來(lái)的,發(fā)過(guò)來(lái)的數(shù)據(jù)會(huì)暫存在系統(tǒng)socket緩沖區(qū),$s只是代表緩沖區(qū)是否有未讀數(shù)據(jù),不代表整個(gè)數(shù)據(jù)包是否傳遞完畢。所以你上面的代碼是有問(wèn)題的。
穩(wěn)妥的方法是根據(jù)通訊協(xié)議來(lái)分包,例如數(shù)據(jù)發(fā)過(guò)來(lái)的前幾個(gè)字節(jié)是數(shù)據(jù)包的長(zhǎng)度len,得到長(zhǎng)度后while循環(huán)直到讀取len長(zhǎng)度的數(shù)據(jù)后跳出while循環(huán),這樣才是完整的數(shù)據(jù)。
類似
$len = 0;
$buf = '';
while(1) {
$buf .= fread($fp, 1024);
// 還不知道數(shù)據(jù)長(zhǎng)度,計(jì)算這個(gè)包的數(shù)據(jù)長(zhǎng)度
if (!$len) {
// your_func_of_get_len里還要判斷下目前收到的數(shù)據(jù)長(zhǎng)度是否足夠計(jì)算出整個(gè)包的長(zhǎng)度
$len = your_func_of_get_len($buf);
}
// 判斷數(shù)據(jù)是否全部得到,得到就跳出
if (strlen($buf) >= $len) {
// 實(shí)際上最好要截取下,因?yàn)閠cp流式的,可能是多個(gè)包粘在一起。如果是多個(gè)包粘在一起,還要記得保存下個(gè)包的部分?jǐn)?shù)據(jù),避免數(shù)據(jù)丟失,這里省略了
$buf = substr($buf, 0, $len);
break;
}
}