60*15) { //发送时间大于当前时间15分钟 continue; } else { \Log::info('========现将客服消息设置成发送状态 "sending" 用户不能操作(删除,编辑,停止) = ' . $customSendMsgsPrams['id']); $customSendMsgsPrams['status'] = 'sending'; $customSendMsgsPrams->save(); $officialAccountArray = $customSendMsgsPrams->toArray(); Redis::hset('send_batch_wechat_msg:task_id:' . $customSendMsgsPrams['id'], 'wechat_msg', json_encode($officialAccountArray)); $allStandByWechatCustomMsgsArray[] = $customSendMsgsPrams; } } for ($x = 0; $x < count($allStandByWechatCustomMsgsArray); $x++) { $customSendMsgsPrams = $allStandByWechatCustomMsgsArray[$x]; // 转化图文的链接url // $customSendMsgsPrams['content'] = self::convert_custom_content($customSendMsgsPrams['content'],$customSendMsgsPrams['id'],$customSendMsgsPrams['distribution_channel_id']); $media_id = $customSendMsgsPrams['wechat_media_id']; $appids = $customSendMsgsPrams['appid']; $batch_id = $customSendMsgsPrams['batch_id']; $task_id = $customSendMsgsPrams['id']; // 获取发送的批次信息 $batchWechatMaterial = BatchWechatMaterial::find($batch_id); $send_time= isset($batchWechatMaterial['send_time'])?$batchWechatMaterial['send_time']:date('Y-m-d H:i:s'); $is_full_send= isset($batchWechatMaterial['is_all_user'])?$batchWechatMaterial['is_all_user']:0; \Log::info('batch_wechat_msg,appids:'.$appids.' is_full_send:'.$is_full_send.' media_id:'.$media_id); $appidArray = explode(',', $appids); $usercountnum = 0; for ($j=0; $j < count($appidArray); $j++) { $skip = 0; $next_openid = ''; $loop = 0; while ( $skip <= 2500000) { $loop++; \Log::info('toCheckAndSendBatchCustomMsg_loop:'.$skip.' loop:'.$loop.' next_openid:'.$next_openid); $users = array(); // 全服务号粉丝发,要记录next_openid if($is_full_send){ // 防止异常 if($loop > 1 && empty($next_openid)){ \Log::info('send_template_appid:'.$appidArray[$j].' break,skip:'.$skip); break; } try{ $user_res = ForceSubscribeService::getFullOfficialAccountUsers($appidArray[$j],$next_openid); $users = $user_res['openids'];// TODO格式化成一样的格式 $next_openid = $user_res['next_openid']; } catch (\Exception $e) { \Log::info($e); } }else{ //5,获取所选条件下筛选出的用户 $sign_time = 'z'; $subscribe_time = isset($batchWechatMaterial['subscribe_time'])?$batchWechatMaterial['subscribe_time']:''; $sex= isset($batchWechatMaterial['sex'])?$batchWechatMaterial['sex']:''; $balance= isset($batchWechatMaterial['balance'])?$batchWechatMaterial['balance']:''; $category_id= isset($batchWechatMaterial['category_id'])?$batchWechatMaterial['category_id']:''; $order_type= isset($batchWechatMaterial['pay_type'])?$batchWechatMaterial['pay_type']:''; $sign_time= isset($batchWechatMaterial['sign_time'])?$batchWechatMaterial['sign_time']:''; $interaction_time= isset($batchWechatMaterial['interaction_time'])?$batchWechatMaterial['interaction_time']:''; $users = ForceSubscribeService::forceUserCountByBatchWechatCustomPrams($appidArray[$j],$customSendMsgsPrams['distribution_channel_id'],$subscribe_time,$sex,$balance,$category_id,$order_type,$sign_time,$interaction_time,$skip); } \Log::info('toCheckAndSendBatchCustomMsg_users_num:'.count($users)); // continue; $queue_user_one_num = 10000; $user_loop = 1; $last_openids = $openids = []; if (count($users)>0) { $usercountnum += count($users); for ($i=0; $i < count($users); $i++) { // 循环用户发送客服消息 $data = array(); if ($i == count($users)-1) { $data['type'] = 'last_task'; }else{ $data['type'] = 'one_task'; } \Log::info('i:'.$i.' $user_loop:'.$user_loop.' openid:'.$users[$i]['openid'].' type:'.$data['type']); // 一次组装10000个用户 (接口1次最多10000个,1天最多发100次) if($user_loop <= $queue_user_one_num){ $openids[] = $users[$i]['openid']; $user_loop++; // 最后1组直接执行 if($data['type'] == 'one_task'){ continue; }else{ $last_openids = $openids; } }else{ $user_loop = 1; $last_openids = $openids; } // $data['content'] = $customSendMsgsPrams['content']; $data['openids'] = $last_openids; $data['appid'] = $appidArray[$j]; $data['media_id'] = $media_id; $data['type'] = 'last_task'; // 默认发1个直接更新,防止更新失败情况 $data['task_id'] = $task_id; $data['batch_id'] = $batch_id; $data['send_time'] = $send_time; $send_data=array( 'send_time'=>$send_time, 'data' => $data ); $now_time = strtotime($send_time)-time(); $delay = $now_time < 0 ? 0:$now_time; \Log::info('SendBatchWechatMaterial:'.json_encode($last_openids).' task_id:'.$task_id); \Log::info($send_data); $job = (new SendBatchWechatMaterial($send_data))->onConnection('rabbitmq')->delay($delay)->onQueue('{send_batch_wechat_material}'); dispatch($job); $last_openids = $openids = []; } }else{ \Log::info('toCheckAndSendBatchCustomMsg_no_user:'.$customSendMsgsPrams['task_id']); break; } $skip += count($users); } } $customSendMsgsPrams['send_user_num'] = $usercountnum; // 若没有用户,则直接更新为已发送 if($usercountnum == 0){ \Log::info('has_no_batch_custom_users:'.$customSendMsgsPrams['id']); $customSendMsgsPrams['status'] = 'has_send'; } \Log::info('toCheckAndSendBatchCustomMsg_update_user_num:'.$customSendMsgsPrams['id'].' usercountnum:'.$usercountnum); $customSendMsgsPrams->save(); } }else{ \Log::info('toCheckAndSendBatchCustomMsg_no_msgs'); } } catch (\Exception $e) { \Log::info('toCheckAndSendBatchCustomMsg_ept:'.$e->getMessage()); } } /** * 转换客服消息内容 */ public static function convert_custom_content($content,$mark_str,$distribution_channel_id){ \Log::info('convert_custom_content_start:'); $_contents = json_decode($content); \Log::info('convert_custom_content_before:'); \Log::info($_contents); $new_contents = null; $origin_mark_str = $mark_str; $send_type = 'batch_custom'; // 智能推送不加前缀 if(strpos($origin_mark_str,'smart_push_') > -1){ $send_type = 'smart_push'; $origin_mark_str = str_replace('smart_push_','',$origin_mark_str); } \Log::info('origin_mark_str:'.$origin_mark_str); foreach($_contents as $key=>$_content){ // 新版要自动添加域名 $_content[2]->url = self::checkAddDomain($distribution_channel_id,$_content[2]->url); $mark_str = $origin_mark_str.'&source=wechatmsg';// source能让用户继续阅读 $_contents[$key][2]->url = self::redirect_url_add_param($_content[2]->url,$mark_str,$send_type,false); $new_contents[] = $_contents[$key]; } \Log::info('convert_custom_content_after:'); \Log::info($new_contents); $_convert_contents = json_encode($new_contents); return $_convert_contents; } /** * 跳转地址加参 * @param unknown_type $redirect_url * @param unknown_type $type * @return string */ public static function redirect_url_add_param($redirect_url,$mark_str,$type='custom',$trusteeship=false){ $pre_str = ''; if($type == 'batch_custom'){ $pre_str = 'batch_custom_'; } // 模板客服消息,单独加参 $inner_order_id = ''; if(!$trusteeship){ $inner_order_id = '&inner_order_id='.$pre_str.$mark_str; } $send_time_str = ''; // 跳转链接加参 if(strpos($redirect_url,'?') > -1){ $redirect_url .= '&fromtype='.$pre_str.$mark_str.$inner_order_id.$send_time_str; }else{ $redirect_url .= '?fromtype='.$pre_str.$mark_str.$inner_order_id.$send_time_str; } return $redirect_url; } // 新版要自动添加域名 public static function checkAddDomain($distribution_channel_id,$redirect_url){ // 非托管,如果url没有域名,则加上 if(strpos($redirect_url, 'http') !== false){ \Log::info('not_need_add_domain:'.$distribution_channel_id.' url:'.$redirect_url); }else{ \Log::info('need_add_domain_before:'.$distribution_channel_id.' url:'.$redirect_url); $redirect_url = env('PROTOCOL').'://site'.encodeDistributionChannelId($distribution_channel_id).'.'.env('CUSTOM_HOST').'.com'.$redirect_url; \Log::info('need_add_domain_after:'.$distribution_channel_id.' url:'.$redirect_url); } return $redirect_url; } }