企业微信 之快捷回复项目

开发文档:https://open.work.weixin.qq.com/api/doc/90000/90135/90664

一、效果图

 

 二、开发流程

1、创建应用

 

 2、配置应用

 

 三、简单代码

1、授权登录

 2、回调

 helper.php

/**
 * GET 请求
 * @param string $url
 */
function http_get($url){
    $oCurl = curl_init();
    if(stripos($url,"https://")!==FALSE){
        curl_setopt($oCurl, CURLOPT_SSL_VERIFYPEER, FALSE);
        curl_setopt($oCurl, CURLOPT_SSL_VERIFYHOST, FALSE);
        curl_setopt($oCurl, CURLOPT_SSLVERSION, 1); //CURL_SSLVERSION_TLSv1
    }
    curl_setopt($oCurl, CURLOPT_URL, $url);
    curl_setopt($oCurl, CURLOPT_RETURNTRANSFER, 1 );
    curl_setopt($oCurl, CURLOPT_VERBOSE, 1);
    curl_setopt($oCurl, CURLOPT_HEADER, 1);

    // $sContent = curl_exec($oCurl);
    // $aStatus = curl_getinfo($oCurl);
    $sContent = execCURL($oCurl);
    curl_close($oCurl);

    return $sContent;
}
/**
 * POST 请求
 * @param string $url
 * @param array $param
 * @param boolean $post_file 是否文件上传
 * @return string content
 */
function http_post($url,$param,$post_file=false){
    $oCurl = curl_init();

    if(stripos($url,"https://")!==FALSE){
        curl_setopt($oCurl, CURLOPT_SSL_VERIFYPEER, FALSE);
        curl_setopt($oCurl, CURLOPT_SSL_VERIFYHOST, false);
        curl_setopt($oCurl, CURLOPT_SSLVERSION, 1); //CURL_SSLVERSION_TLSv1
    }
    if(PHP_VERSION_ID >= 50500 && class_exists('CURLFile')){
        $is_curlFile = true;
    }else {
        $is_curlFile = false;
        if (defined('CURLOPT_SAFE_UPLOAD')) {
            curl_setopt($oCurl, CURLOPT_SAFE_UPLOAD, false);
        }
    }
    
    if($post_file) {
        if($is_curlFile) {
            foreach ($param as $key => $val) {                     
                if(isset($val["tmp_name"])){
                    $param[$key] = new CURLFile(realpath($val["tmp_name"]),$val["type"],$val["name"]);
                }else if(substr($val, 0, 1) == '@'){
                    $param[$key] = new CURLFile(realpath(substr($val,1)));                
                }                           
            }
        }                
        $strPOST = $param;
    }else{
        $strPOST = json_encode($param);
    } 
    
    curl_setopt($oCurl, CURLOPT_URL, $url);
    curl_setopt($oCurl, CURLOPT_RETURNTRANSFER, 1 );
    curl_setopt($oCurl, CURLOPT_POST,true);
    curl_setopt($oCurl, CURLOPT_POSTFIELDS,$strPOST);
    curl_setopt($oCurl, CURLOPT_VERBOSE, 1);
    curl_setopt($oCurl, CURLOPT_HEADER, 1);

    // $sContent = curl_exec($oCurl);
    // $aStatus  = curl_getinfo($oCurl);

    $sContent = execCURL($oCurl);
    curl_close($oCurl);

    return $sContent;
}

/**
 * 执行CURL请求,并封装返回对象
 */
function execCURL($ch){
    $response = curl_exec($ch);
    $error    = curl_error($ch);
    $result   = array( 'header' => '', 
                     'content' => '', 
                     'curl_error' => '', 
                     'http_code' => '',
                     'last_url' => '');
    
    if ($error != ""){
        $result['curl_error'] = $error;
        return $result;
    }

    $header_size = curl_getinfo($ch,CURLINFO_HEADER_SIZE);
    $result['header'] = str_replace(array("
", "
", "
"), "<br/>", substr($response, 0, $header_size));
    $result['content'] = substr( $response, $header_size );
    $result['http_code'] = curl_getinfo($ch,CURLINFO_HTTP_CODE);
    $result['last_url'] = curl_getinfo($ch,CURLINFO_EFFECTIVE_URL);
    $result["base_resp"] = array();
    $result["base_resp"]["ret"] = $result['http_code'] == 200 ? 0 : $result['http_code'];
    $result["base_resp"]["err_msg"] = $result['http_code'] == 200 ? "ok" : $result["curl_error"];

    return $result;
}

//给URL地址追加参数
function appendParamter($url,$key,$value){  
    return strrpos($url,"?",0) > -1 ? "$url&$key=$value" : "$url?$key=$value";
}

//生成指定长度的随机字符串
function createNonceStr($length = 16) {
  $chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
  $str = "";
  for ($i = 0; $i < $length; $i++) {
    $str .= substr($chars, mt_rand(0, strlen($chars) - 1), 1);
  }
  return $str;
}

//读取本地文件
function get_php_file($filename) {
    if(file_exists($filename)){
        return trim(substr(file_get_contents($filename), 15));
    }else{
        return '{"expire_time":0}';
    }    
}
//写入本地文件
function set_php_file($filename, $content) {
    $fp = fopen($filename, "w");
    fwrite($fp, "<?php exit();?>" . $content);
    fclose($fp);
}

//加载本地的应用配置文件
function loadConfig(){
    return json_decode(get_php_file("../config.php"));
}

//根据应用ID获取应用配置
function getConfigByAgentId($id){
    $configs = loadConfig();
    
    foreach ($configs->AppsConfig as $key => $value) {                
        if($value->AgentId == $id){
            $config = $value;
            break;
        }
    }

    return $config;
}

/**
 * 日志函数
 * @param $msg
 * @param string $filename
 */
function write_log($msg, $filename='msg')
{
    $file = fopen("./$filename.log", "a");
    $msg = "[" . date("Y-m-d H:i:s") . "] - " . $msg;
    fwrite($file, $msg . "
");
    fclose($file);
}

/**
 * 设置缓存,按需重载
 * @param string $cachename
 * @param mixed $value
 * @param int $expired
 * @return boolean
 */
function setCache($cachename, $value, $expired)
{
    //TODO: set cache implementation
    $content = var_export(array('access_token' => $value, 'expires_in' => $expired), true);
    file_put_contents($cachename.".php", "<?php return " . $content . ";");
    return false;
}

/**
 * 获取缓存,按需重载
 * @param string $cachename
 * @return mixed
 */
function getCache($cachename, $expired = 7100)
{
    if(!file_exists($cachename.".php")){
        return false;
    }
    $access_token_array = include($cachename.".php");
    if (filemtime($cachename.".php") + $expired > time()) {
        return $access_token_array['access_token'];
    }
    return false;
}

//=======================================后端函数=====================================================

/**
 * 获取第三方应用凭证(suite_access_token)。
 * @param $suite_id
 * @param $suite_secret
 * @param $suite_ticket
 */
function getSuiteAccessToken($suite_id, $suite_secret, $suite_ticket) {
    $cachename = './cache/suite_access_token';
    $access_token = getCache($cachename);
    if (!$access_token){
        $url = "https://qyapi.weixin.qq.com/cgi-bin/service/get_suite_token";
        $data = array(
            'suite_id' => trim($suite_id),
            'suite_secret' => trim($suite_secret),
            'suite_ticket' => trim($suite_ticket)
        );

        $response = http_post($url, $data);
        if ($response['base_resp']['ret'] == 0) {
            $data = json_decode($response['content'], true);
            $access_token = $data['suite_access_token'];
            setCache($cachename, $access_token, $data['expires_in']);
        }
    }
    return $access_token;
}

/**
 * 发送消息
 * @param $corpId
 * @param $secret
 * @param $touser
 * @param $msgtype
 * @param $agentid
 * @param $content
 */
function sendAgentMessage($corpId, $secret,$agentid, $touser, $msgtype, $title,  $content, $urls)
{
    $access_token = getAccessToken($corpId, $secret);
    $url = "https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=".$access_token;
    $data = array(
        'touser' => $touser,
        'msgtype' => $msgtype,
        'agentid' => $agentid,
        'textcard' => array(
            'title' => $title,
            'description' => $content,
            'url' => $urls,
            'btntxt' => '查看详情'
        )
    );
    $response = http_post($url, $data);
    return $response['base_resp'];
}

/**
 * 获取预授权码。预授权码用于企业授权时的第三方服务商安全验证。
 * @param $suite_access_token
 * @return mixed
 */
function getPreAuthCode($suite_access_token) {
    $cachename = './cache/pre_auth_code';
    $access_token = getCache($cachename, 3500);
    if (!$access_token){
        $url = "https://qyapi.weixin.qq.com/cgi-bin/service/get_pre_auth_code?suite_access_token=".$suite_access_token;
        $response = http_get($url);
        if ($response['base_resp']['ret'] == 0) {
            write_log($response['content'], 'api');
            $data = json_decode($response['content'], true);
            $access_token = $data['pre_auth_code'];
            setCache($cachename, $access_token, $data['expires_in']);
        }
    }
    return $access_token;
}

/**
 * 获取企业永久授权码
 * @param $auth_code 临时授权码
 * @return null
 */
function getPermanentCode($auth_code){
    $cachename = './cache/suite_access_token';
    $access_token = getCache($cachename);
    if ($access_token){
        $url = "https://qyapi.weixin.qq.com/cgi-bin/service/get_permanent_code?suite_access_token=".$access_token;
        $data = array(
            'auth_code' => $auth_code
        );

        $response = http_post($url, $data);
        if ($response['base_resp']['ret'] == 0) {
            return $response['content'];
        }
    }
    return null;
}

//=======================================后端函数=====================================================

//=======================================前端函数=====================================================

/**
 * 获取企业自建应用用户信息
 * @param $code
 */
function getUserInfo($corpId, $secret, $code) {
    $access_token = getAccessToken($corpId, $secret);
    $url = "https://qyapi.weixin.qq.com/cgi-bin/user/getuserinfo?access_token=$access_token&code=$code";
    $response = http_get($url);
    if ($response['base_resp']['ret'] == 0) {
        $data = json_decode($response['content'], true);
        return $data;
    }
    return null;
}

/**
 * 获取企业自建应用用户详细信息
 * @param $corpId
 * @param $secret
 * @param $userid
 * @return mixed
 */
function getUserDetail($corpId, $secret, $userid) {
    $access_token = getAccessToken($corpId, $secret);
    $url = "https://qyapi.weixin.qq.com/cgi-bin/user/get?access_token=$access_token&userid=$userid";
    $response = http_get($url);
    if ($response['base_resp']['ret'] == 0){
        //保存access_token
        return json_decode($response['content'], true);
    }
}

/**
 * jssdk获取
 * @param $corpid
 * @param $secret
 * @return array
 */
function getAgentConfigSignPackage($corpid, $secret) {
    $jsapiTicket = getAgentConfigJsApiTicket($corpid, $secret);
    // 注意 URL 一定要动态获取,不能 hardcode.
    $protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off' || $_SERVER['SERVER_PORT'] == 443) ? "https://" : "http://";
    $url = "$protocol$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";

    $timestamp = time();
    $nonceStr  = createNonceStr();

    //这里参数的顺序要按照 key 值 ASCII 码升序排序
    $string = "jsapi_ticket=$jsapiTicket&noncestr=$nonceStr&timestamp=$timestamp&url=$url";

    $signature = sha1($string);

    $signPackage = array(
        "appId"     => $corpid,
        "nonceStr"  => $nonceStr,
        "timestamp" => $timestamp,
        "url"       => $url,
        "signature" => $signature,
        "rawString" => $string
    );
    return $signPackage;
}
/**
 * jssdk获取
 * @param $corpid
 * @param $secret
 * @return array
 */
function getSignPackage($corpid, $secret) {
    $jsapiTicket = getJsApiTicket($corpid, $secret);
    // 注意 URL 一定要动态获取,不能 hardcode.
    $protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off' || $_SERVER['SERVER_PORT'] == 443) ? "https://" : "http://";
    $url = "$protocol$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";

    $timestamp = time();
    $nonceStr  = createNonceStr();

    //这里参数的顺序要按照 key 值 ASCII 码升序排序
    $string = "jsapi_ticket=$jsapiTicket&noncestr=$nonceStr&timestamp=$timestamp&url=$url";

    $signature = sha1($string);

    $signPackage = array(
        "appId"     => $corpid,
        "nonceStr"  => $nonceStr,
        "timestamp" => $timestamp,
        "url"       => $url,
        "signature" => $signature,
        "rawString" => $string
    );
    return $signPackage;
}

function getJsApiTicket($corpid,$secret) {
    // jsapi_ticket 应该全局存储与更新,以下代码以写入到文件中做示例
    $path = "./cache/{$corpid}_jsapi_ticket.php";
    $data = json_decode(get_php_file($path));
    if($data->expire_time < time()){
        $app_access_token = getAccessToken($corpid,$secret);
        $url = "https://qyapi.weixin.qq.com/cgi-bin/get_jsapi_ticket?access_token=$app_access_token";
        $res = json_decode(http_get($url)["content"]);
        $ticket = $res->ticket;
        if ($ticket) {
            $data->expire_time = time() + 7000;
            $data->jsapi_ticket = $ticket;
            set_php_file($path, json_encode($data));
        }
    } else {
        $ticket = $data->jsapi_ticket;
    }
    return $ticket;
}

function getAgentConfigJsApiTicket($corpid,$secret) {
    // jsapi_ticket 应该全局存储与更新,以下代码以写入到文件中做示例
    $path = "./cache/{$corpid}_ticket.php";
    $data = json_decode(get_php_file($path));
    if($data->expire_time < time()){
        $app_access_token = getAccessToken($corpid,$secret);
        $url = "https://qyapi.weixin.qq.com/cgi-bin/ticket/get?access_token=$app_access_token&type=agent_config";
        $res = json_decode(http_get($url)["content"]);
        $ticket = $res->ticket;
        if ($ticket) {
            $data->expire_time = time() + 7000;
            $data->jsapi_ticket = $ticket;
            set_php_file($path, json_encode($data));
        }
    } else {
        $ticket = $data->jsapi_ticket;
    }
    return $ticket;
}

/**
 * 获取企业自建应用access_token
 * @param $corpId
 * @param $secret
 * @return mixed
 */
function getAccessToken($corpId, $secret){
    $cachename = './cache/'.$corpId.'_access_token';
    $access_token = getCache($cachename);
    if (!$access_token) {
        $url = "https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=$corpId&corpsecret=$secret";
        $response = http_get($url);
        if ($response['base_resp']['ret'] == 0){
            //保存access_token
            $data = json_decode($response['content'], true);
            $access_token = $data['access_token'];
            setCache($cachename, $access_token, $data['expires_in']);
        }
    }
    return $access_token;
}




/**
 * 获取访问用户身份
 * @param $code
 */
function getUserInfo3rd($code) {
    $cachename = './cache/suite_access_token';
    $access_token = getCache($cachename);
    $url = "https://qyapi.weixin.qq.com/cgi-bin/service/getuserinfo3rd?suite_access_token=$access_token&code=$code";
    $response = http_get($url);
    if ($response['base_resp']['ret'] == 0) {
        $data = json_decode($response['content'], true);
        return $data;
    }
    return null;
}

/**
 * 获取授权企业的access_token
 * @param $auth_corpid
 * @return mixed
 */
function getCorpToken($auth_corpid) {
    //判断是否过期
    $access_token_filename = "./cache/{$auth_corpid}_access_token";
    $access_token = getCache($access_token_filename);
    if (!$access_token) {
        $permanent_code = getCache("./cache/{$auth_corpid}_permanent_code", 3 * 365 * 24 * 3600);
        $suite_access_token = getCache("./cache/suite_access_token");
        $url = "https://qyapi.weixin.qq.com/cgi-bin/service/get_corp_token?suite_access_token=".$suite_access_token;
        $data = array(
            'auth_corpid' => $auth_corpid,
            'permanent_code' => $permanent_code
        );
        $response = http_post($url, $data);
        if ($response['base_resp']['ret'] == 0){
            //保存access_token
            $data = json_decode($response['content'], true);
            $access_token = $data['access_token'];
            setCache($access_token_filename, $access_token, $data['expires_in']);
        }
    }
    return $access_token;
}

/**
 * 获取用户信息
 * @param $corpId
 * @param $userId
 */
function getUserById($corpId, $userId){
    //获取授权企业access_token
    $access_token = getCorpToken($corpId);
    $url = "https://qyapi.weixin.qq.com/cgi-bin/user/get?access_token=$access_token&userid=$userId";
    $response = http_get($url);
    if ($response['base_resp']['ret'] == 0){
        $data = json_decode($response['content'], true);
        return $data;
    }
    return null;
}

/**
 * 获取访问用户敏感信息
 * @param $corpId
 * @param $user_ticket
 * @return mixed|null
 */
function getUserDetail3rd($user_ticket){
    $cachename = './cache/suite_access_token';
    $suite_access_token = getCache($cachename);
    $url = "https://qyapi.weixin.qq.com/cgi-bin/service/getuserdetail3rd?suite_access_token=$suite_access_token";
    $response = http_post($url, array('user_ticket' => $user_ticket));
    if ($response['base_resp']['ret'] == 0){
        $data = json_decode($response['content'], true);
        return $data;
    }
    return null;
}
原文地址:https://www.cnblogs.com/yang-2018/p/15237136.html