我使用自编脚本通过PHP向APNS发送推送通知。为了能够处理错误,我使用推送通知的扩展格式,并希望从流中获取结果:
// $apns = a stream_socket_client connection
$apnsMessage = pack('CNNnH*', 1, $i, $pnDetails['expiration_time'], 32, $pnDetails['token']);
$apnsMessage .= pack('n', strlen($pnDetails['payload']));
$apnsMessage .= $pnDetails['payload'];
fwrite($apns, $apnsMessage);
// Check for errors
$errorResponse = @fread($apns, 6)
if ($errorResponse != FALSE) {
$unpackedError = unpack('Ccommand/CstatusCode/Nidentifier', $errorResponse);
}
我在apns-php项目中看到了一个非常类似的做法,但是,在我的情况下,脚本总是在fread行无限期地等待,因为它试图读取不存在的数据(如果有的话,Apple只会发送响应)一个错误)。我一直在寻找方法来判断是否有任何新数据要从TCP流中读取,但是,我找不到任何可用于HTTP调用的流回调方法也不适用于“原始”TCP连接。
如何转换我的脚本以确保它只在实际存在要读取的数据时调用fread? apns-php项目是如何解决这个问题的(我可以说它们只是在调用fread)?
答案 0 :(得分:1)
想出来,最后的提示来自欧文。诀窍是使用stream_set_blocking停用阻塞,现在我只需要等待一段时间才能使用fread获取结果,以确保Apple有足够的时间来响应。
答案 1 :(得分:0)
您是否正在连接到正确的主持人ssl://feedback.push.apple.com:2196
?
他们使用以下调用来连接和读取数据:
stream_context_create
- > stream_socket_client
- > stream_set_blocking
(0) - > stream_set_write_buffer
(0) - > while (!feof($socket)) {}
- > fread
(8192) - > stream_select
(有超时)