<?php
/**
 * Corp.php
 *
 * @Author: Ghaoo
 * @Date  2020/7/27 0027
 */

namespace Weasy\Core;

use addons\qyexternal\model\Corp as Qywx;
use addons\qyexternal\model\FollowUser;
use addons\qyexternal\model\UserBehavior;
use think\Request;
use Weasy\External\Api\CorpAPI;
use Weasy\External\Callback\WXBizMsgCrypt;
use Weasy\External\Utils\Utils;

class Corp
{
    public $corp;

    /**
     * 创建Corp实例.
     * @param int $id
     * @param string $corp_id
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\ModelNotFoundException
     * @throws \think\exception\DbException
     */
    public function __construct($id, $corp_id = "")
    {
        if ($id > 0) {
            $qywx = Qywx::where("id", $id)->find();
        } else {
            $qywx = Qywx::where("corp_id", $corp_id)->find();
        }

        if (!$qywx) {
            throw new \Exception("企业微信实例未找到,ID: $id, CorpId: $corp_id");
        }

        $this->corp = $qywx;
    }

    public function sync($type = "")
    {
        $sync = new Sync($this->corp);

        switch ($type) {
            case "sync_follow_user_list":
                $sync->FollowUserList();
                break;
            case "sync_contacts_list":
                //$sync->ContactsList();
                break;
            case "sync_group_chat_list":
                $sync->GroupChatList();
                break;
            case "sync_user_behavior_data":
                $this->syncUserBehaviorData($sync);
                break;
            default:
                $sync->FollowUserList();
                //$sync->ContactsList();
                $sync->GroupChatList();
                $this->syncUserBehaviorData($sync);
        }

        return true;
    }

    public function getGroupMembers($chat_id)
    {
        $api = new CorpAPI($this->corp->corp_id, $this->corp->external_secret);

        $groupMembers = $api->ExternalContactGroupChatGet($chat_id);

        return $groupMembers["member_list"];
    }

    protected function syncUserBehaviorData(Sync $sync)
    {
        $days = 30;
        $follow = FollowUser::where("corp_id", $this->corp->corp_id)->select();
        $lastData = UserBehavior::where("corp_id", $this->corp->corp_id)->order("date", "desc")->find();
        // 存在同步数据
        if ($lastData) {
            $start = $lastData->date;
            $end = strtotime(date("Y-m-d", strtotime("-1 day"))); // 企业微信数据统计只统计到前一天
            $days = intval(ceil(($end - $start)/84600));
            // 是否超过30天
            if ($days <= 30) {
                // 是否需要同步
                if ($start < $end) {
                    foreach ($follow as $user) {
                        $sync->UserBehaviorData($user->userid, $start, $end);
                    }
                }
                return;
            }
        }

        $start_time = strtotime(date("Y-m-d", strtotime("-$days day")));
        $end_time = strtotime(date("Y-m-d", strtotime("-1 day")));
        foreach ($follow as $user) {
            $sync->UserBehaviorData($user->userid, $start_time, $end_time);
        }
    }

    public function go(Request $request)
    {
        if ($request->isGet() && isset($_GET["echostr"])) {
            $echoStr = $this->verifyUrl();
            if (!$echoStr) {
                throw new \Exception("验证失败");
            }

            echo $echoStr;
            exit();
        }

        if ($request->isPost()) {

            if (!isset($_GET["msg_signature"]) || !isset($_GET["timestamp"]) || !isset($_GET["nonce"])) {
                return false;
            }
            $sReqMsgSig = $_GET["msg_signature"];
            $sReqTimeStamp = $_GET["timestamp"];
            $sReqNonce = $_GET["nonce"];

            $sReqData = $request->getContent();

            $sMsg = "";  // 解析之后的明文
            $wxcpt = new WXBizMsgCrypt($this->corp->token, $this->corp->key, $this->corp->corp_id);
            $errCode = $wxcpt->DecryptMsg($sReqMsgSig, $sReqTimeStamp, $sReqNonce, $sReqData, $sMsg);
            if ($errCode == 0) {
                $msg = Utils::Xml2Array($sMsg);

                if (isset($msg["MsgType"]) && $msg["MsgType"] == "event") {
                    new Payload($msg);
                }

            } else {
                return new \Exception("解析消息失败");
            }
        }
    }

    protected function verifyUrl() {
        if (!isset($_GET["msg_signature"]) || !isset($_GET["timestamp"]) || !isset($_GET["nonce"]) || !isset($_GET["echostr"])) {
            return false;
        }
        $sVerifyMsgSig = $_GET["msg_signature"];
        $sVerifyTimeStamp = $_GET["timestamp"];
        $sVerifyNonce = $_GET["nonce"];
        $sVerifyEchoStr = $_GET["echostr"];

        $sEchoStr = "";
        $wxcpt = new WXBizMsgCrypt($this->corp->token, $this->corp->key, $this->corp->corp_id);
        $errCode = $wxcpt->VerifyURL($sVerifyMsgSig, $sVerifyTimeStamp, $sVerifyNonce, $sVerifyEchoStr, $sEchoStr);
        if ($errCode == 0) {
            return $sEchoStr;
        } else {
            return false;
        }
    }
}