fob_hot_ai_mail_auto_reply.php 5.4 KB
<?php


use Model\folderSql;

require_once "../vendor/autoload.php";


/**
 * 预热自动回复
 * @author:dc
 * @time 2025/7/2 9:58
 * Class fob_ai_mail_auto_reply
 */
class fob_hot_ai_mail_auto_reply {


    public $isStop = false;


    /**
     * @var \Lib\Db
     */
    public $db;


    public $startTime = 0;

    /**
     * SyncToEsCmd constructor.
     */
    public function __construct()
    {
        $this->db = db();

        $handler = function ($signal){
            _echo('收到进程信号 '. $signal);
            // 可以处理其他程序
            $this->isStop = true;
        };
        pcntl_signal(SIGTERM, $handler); // 这个是kill
        pcntl_signal(SIGINT, $handler); // 这个是 ctrl+c

        $this->startTime = time();
    }


    /**
     * @return bool
     */
    public function isStop(): bool
    {
        // 检查是否接收到信号
        pcntl_signal_dispatch();

        // 是否超过来最大执行时间
        if(time()-43200 > $this->startTime){
            return true;
        }

        return $this->isStop;
    }

    protected $bodys = [];

    public function getDelayTime(){
        /**
         * 随机一个延时时间秒 极小的概率30-60分钟,小概率60-120分钟,中概率120-180分钟 大概率180-240分钟
         */

// 生成一个 0 到 100 之间的随机数
        $randomValue = rand(0, 100);

        // 根据随机值的范围来决定延迟时间
        if ($randomValue < 5) { // 5% 的概率
            // 随机 30-60分钟
            $rand = rand(45, 60) * 60; // 转换为秒
        } elseif ($randomValue < 15) { // 10% 的概率 (5% + 10%)
            // 随机 60-120分钟
            $rand = rand(65, 120) * 60; // 转换为秒
        } elseif ($randomValue < 45) { // 30% 的概率 (15% + 30%)
            // 随机 120-180分钟
            $rand = rand(125, 180) * 60; // 转换为秒
        } else { // 55% 的概率 (45% + 55%)
            // 随机 180-240分钟
            $rand = rand(180, 240) * 60; // 转换为秒
        }

        return time()+$rand;
    }

    public function handler(){

        $this->bodys = file_get_contents(__DIR__."/body.reply");
        $this->bodys = explode("--------------",$this->bodys);

        while (!$this->isStop()){

            $id = redis()->lPop('new_hot_mail_auto_reply_ids');
            if($id){
                // 检查是否到时间了
                list($did,$time)  = explode('.',((string) $id).'.0');
                if($time == '0'){
                    redis()->rPush('new_hot_mail_auto_reply_ids',$id.'.'.$this->getDelayTime());
                    continue;
                }
                if($time > time()){
                    redis()->rPush('new_hot_mail_auto_reply_ids',$id);
                    usleep(10000);
                    continue;
                }
                // 查询数据
                $data = $this->db->first(\Model\listsSql::first('`id` = '.$did,'`id`,`email_id`,`subject`,`is_hots`,`from`,`udate`,`uid`'));
                if($data && $data['is_hots']){
                    // 在检查下是否是 收件箱
                    if($this->db->cache(3600)->value(\Model\folderSql::has(['id'=>$data['folder_id'],'origin_folder'=>'INBOX']))){
                        _echo('处理 '.$data['id']);
                        $email = $this->db->throw()->cache(3600)->first(\Model\emailSql::first($data['email_id']));

                        // 验证是否是ai邮箱
                        if($this->db->count(sprintf("select count(*) from `hot_mail` where `email` = '%s'",$email['email']))){
                            // 标记已读
                            $mailInstance = \Lib\Imap\ImapPool::get((new \Lib\Imap\ImapConfig($email)));
                            if($mailInstance->login()){
                                $mailInstance->folder('INBOX')->msg()->uid($data['uid'])->seen();
                                $mailInstance = null;
                            }

                            // 来回超过5次就不回了
                            if(substr_count($data['subject'],"Re:") < 3){
// 有配置才回复
                                $ret = \Lib\Mail\MailFun::sendEmail([
                                    'subject'   =>  'Re:'.$data['subject'],
                                    'tos'   =>  [['email'=>$data['from'],'name'=>explode('@',$data['from'])[0]]],
                                    'body'  => $this->trimBody($data,$data['subject']),
                                    'mail-header' => [
                                        'Aicc-Hot-Mail' =>  'hot' // 预热邮件
                                    ]
                                ],$email);
                                _echo('回复成功'.$data['id']." ".$email['email'].' to '.$data['from']." ".$ret[1]);
                            }else{
                                _echo('来回超过5次就不回了 '.$data['id']);
                            }
                        }
                    }

                }

            }else{
                sleep(1);
            }
        }

    }

    public function trimBody($data,$inbox){
        // 随机body内容
        $reply = $this->bodys[array_rand($this->bodys)];

        return "<pre>------------------ 原始邮件 ------------------
发件人: {$data['from']};
发送时间: ".date("Ymd H:i",$data['udate'])."
收件人: {$data['to']};
主题: {$data['subject']}

{$inbox}</pre>".$reply;
    }




}

(new fob_ai_mail_auto_reply())->handler();

return 1;