注意事项: 1.建议和feedback服务器建立长连接,连接过于频繁有可能被当做攻击(简简单单的做一些测试时没有关系的); 2.获取的token是在上次你给你的应用发推送失败时加feedback服务的,里面会返回失败的具体时间 3.返回的数据由三部分组成,请看下面的图 结
注意事项:
1.建议和feedback服务器建立长连接,连接过于频繁有可能被当做攻击(简简单单的做一些测试时没有关系的);
2.获取的token是在上次你给你的应用发推送失败时加feedback服务的,里面会返回失败的具体时间
3.返回的数据由三部分组成,请看下面的图
结构中包含三个部分,第一部分是一个上次发推送失败的时间戳,第二个部分是device_token的长度,第三部分就是失效的device_token
立即学习“PHP免费学习笔记(深入)”;
下面是我的代码:
<?php
/**
* @desc 连接苹果的推送服务器
* @return bool|resource
*/
function connect_feedback(){
$passphrase = 'cheshi123';
$cert_file = 'cheshi_productionck.pem';//推送的证书地址,环境不要错了
$feedback_server = 'ssl://feedback.push.apple.com:2196';//feedback服务器地址
//沙盒环境地址是 ssl://feedback.sandbox.push.apple.com:2196
$ctx = stream_context_create();
stream_context_set_option($ctx, 'ssl', 'local_cert', $cert_file);
stream_context_set_option($ctx, 'ssl', 'passphrase', $passphrase);
$fp = stream_socket_client($feedback_server, $error, $errorString, 60, STREAM_CLIENT_CONNECT, $ctx);
if(!$fp){
print "Failed to connect feedback server: $error $errorString\n";
return false;
}else{
print "Connection to feedback server OK\n";
}
return $fp;
}
/**
* @desc 连接本地的redis,用来存储获取到的token,也可以用其他方式存储
* @param $redis_server
*
* @return bool|Redis
*/
function connect_redis($redis_server){
$param = parse_url($redis_server);
$redis = new Redis();
if($redis->connect($param['host'],$param['port'])){
print "connect redis OK";
}else{
print "failed to connect redis server";
return false;
}
return $redis;
}
/**
* @desc 执行推送操作的主要代码
*/
function feedback(){
$count1 = 0;
$run_times = 0;
$redis_server = "tcp://localhost:6379";
$iostokenremoved= 'iostokenremoved';
$iostokenremoved_num = 'iostokenremoved_num';
$fp = connect_feedback();
$redis = connect_redis($redis_server);
//苹果建议provider和feedback服务维持一个长连接,如果频繁的建立连接可能会被当做攻击处理
$devcon ='';
while($run_times<2000){
$run_times++;
//socket连接检测
if($devcon ===FALSE){
print date('Ymd His').'|feedback server disconnected';
@fclose($fp);
unset($fp);
$fp = connect_feedback();
}
//redis连接检测
if(!is_resource($redis) OR !$redis->ping()==='+PONG'){
print date('Ymd His').'|redis server disconnected';
@$redis->close();
unset($redis);
$redis = connect_redis($redis_server);
}
//每次读取38个字段,这是保存的一个完整token 信息的长度
while ($devcon = fread($fp, 38)){
$count1 ++ ;
$arr = unpack("H*", $devcon);//解包传过来的二进制数据
$rawhex = trim(implode("", $arr));
$feedbackTime = hexdec(substr($rawhex, 0, 8));
$feedbackDate = date('Y-m-d H:i:s', $feedbackTime);
$feedbackDeviceToken = substr($rawhex, 12, 64);
//记录被删除的token
$redis->hSet($iostokenremoved,$feedbackDeviceToken,$feedbackDate);
//记录每天的卸载数量
$redis->hIncrBy($iostokenremoved_num,date('Y-m-d',$feedbackTime),1);
}
echo 'FeedBack:'. $count1 . PHP_EOL;
usleep(10000000);//sleep 10秒
}
$redis->close();
fclose($fp);
}
//可以通过命令行来执行这个脚本 php -f feedback.php feedback
if(isset($argc[1]) && function_exists($argv[1])){
$argv[1]();
}else{
die('invalid input');
}
C++高性能并发应用_C++如何开发性能关键应用
Java AI集成Deep Java Library_Java怎么集成AI模型部署
Golang后端API开发_Golang如何高效开发后端和API
Python异步并发改进_Python异步编程有哪些新改进
C++系统编程内存管理_C++系统编程怎么与Rust竞争内存安全
Java GraalVM原生镜像构建_Java怎么用GraalVM构建高效原生镜像
Python FastAPI异步API开发_Python怎么用FastAPI构建异步API
C++现代C++20/23/26特性_现代C++有哪些新标准特性如modules和coroutines
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号