增加第三方平台开放平台

This commit is contained in:
Anyon 2019-12-09 11:06:51 +08:00
parent 91e80f7ee0
commit af9e8e493b
139 changed files with 13353 additions and 20 deletions

1
.gitignore vendored
View File

@ -3,5 +3,6 @@
.vscode
*.log
runtime
composer.lock
public/upload
/nbproject/private/

View File

@ -15,6 +15,7 @@
namespace app\index\controller;
use app\service\service\ClientService;
use think\admin\Controller;
/**
@ -27,4 +28,9 @@ class Index extends Controller
{
$this->redirect(url('@admin/login'));
}
public function test()
{
ClientService::WeChatCard(1, 2);
}
}

View File

@ -0,0 +1,63 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\controller;
use think\admin\Controller;
/**
* 开放平台参数配置
* Class Config
* @package app\service\controller
*/
class Config extends Controller
{
/**
* 绑定数据表
* @var string
*/
protected $table = 'WechatServiceConfig';
/**
* 开放平台配置
* @auth true
* @menu true
*/
public function index()
{
$this->title = '开放平台参数配置';
$this->fetch();
}
/**
* 修改开放平台参数
* @auth true
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function edit()
{
$this->_applyFormToken();
if ($this->request->isGet()) {
$this->fetch('form');
} else {
$post = $this->request->post();
foreach ($post as $k => $v) sysconf($k, $v);
$this->success('参数修改成功!');
}
}
}

View File

@ -0,0 +1,92 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\controller;
use think\admin\Controller;
/**
* 微信粉丝管理
* Class Fans
* @package app\service\controller
*/
class Fans extends Controller
{
/**
* 绑定数据表
* @var string
*/
protected $table = 'WechatFans';
/**
* 初始化函数
*/
protected function initialize()
{
$this->appid = input('appid', $this->app->session->get('current_appid'));
if (empty($this->appid)) {
$this->where = ['status' => '1', 'service_type' => '2', 'is_deleted' => '0', 'verify_type' => '0'];
$this->appid = $this->app->db->name('WechatServiceConfig')->where($this->where)->value('authorizer_appid');
}
if (empty($this->appid)) {
$this->fetch('/not-auth');
} else {
$this->app->session->set('current_appid', $this->appid);
}
if ($this->request->isGet()) {
$this->where = ['status' => '1', 'service_type' => '2', 'is_deleted' => '0', 'verify_type' => '0'];
$this->wechats = $this->app->db->name('WechatServiceConfig')->where($this->where)->order('id desc')->column('authorizer_appid,nick_name');
}
}
/**
* 微信粉丝管理
* @auth true
* @menu true
*/
public function index()
{
$this->title = '微信粉丝管理';
$query = $this->_query($this->table)->like('nickname')->equal('subscribe,is_black');
$query->dateBetween('subscribe_at')->where(['appid' => $this->appid])->order('subscribe_time desc')->page();
}
/**
* 列表数据处理
* @param array $data
*/
protected function _index_page_filter(array &$data)
{
$tags = $this->app->db->name('WechatFansTags')->column('id,name');
foreach ($data as &$user) {
$user['tags'] = [];
foreach (explode(',', $user['tagid_list']) as $tagid) {
if (isset($tags[$tagid])) $user['tags'][] = $tags[$tagid];
}
}
}
/**
* 删除粉丝信息
* @auth true
* @throws \think\db\exception\DbException
*/
public function remove()
{
$this->_applyFormToken();
$this->_delete($this->table);
}
}

View File

@ -0,0 +1,71 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\controller;
use think\admin\Controller;
/**
* 公众号授权管理
* Class Wechat
* @package app\service\controller
*/
class Wechat extends Controller
{
/**
* 绑定数据表
* @var string
*/
protected $table = 'WechatServiceConfig';
/**
* 公众号授权管理
* @auth true
* @menu true
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function index()
{
$this->title = '公众号授权管理';
$query = $this->_query($this->table)->like('authorizer_appid,nick_name,principal_name');
$query = $query->equal('service_type,status')->dateBetween('create_at');
$query->where(['is_deleted' => '0'])->order('id desc')->page();
}
/**
* 修改公众号状态
* @auth true
* @throws \think\db\exception\DbException
*/
public function state()
{
$this->_applyFormToken();
$this->_save($this->table, ['status' => input('status')]);
}
/**
* 删除公众号授权
* @auth true
* @throws \think\db\exception\DbException
*/
public function remove()
{
$this->_applyFormToken();
$this->_delete($this->table);
}
}

View File

@ -0,0 +1,78 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\controller\api;
use app\service\service\WechatService;
use think\admin\Controller;
use think\Exception;
/**
* 接口获取实例化
* Class Client
* @package app\service\controller\api
*/
class Client extends Controller
{
/**
* YAR 接口标准对接
* @return string
*/
public function yar()
{
try {
$service = new \Yar_Server($this->instance());
$service->handle();
} catch (\Exception $exception) {
return $exception->getMessage();
}
}
/**
* SOAP 接口标准对接
* @return string
*/
public function soap()
{
try {
$service = new \SoapServer(null, ['uri' => 'thinkadmin']);
$service->setObject($this->instance());
$service->handle();
} catch (\Exception $exception) {
return $exception->getMessage();
}
}
/**
* 远程获取实例对象
* @return mixed|\Exception
*/
private function instance()
{
try {
$code = $this->app->request->get('code', '');
$data = json_decode(debase64url($code), true);
list($class, $appid, $time, $sign) = [$data['class'], $data['appid'], $data['time'], $data['sign']];
$config = $this->app->db->name('WechatServiceConfig')->where(['authorizer_appid' => $appid])->find();
if (empty($config)) throw new Exception("抱歉,该公众号{$appid}未授权!");
if (md5("{$class}#{$appid}#{$config['appkey']}#{$time}") !== $sign) {
throw new Exception("抱歉,该公众号{$appid}签名异常!");
}
return WechatService::$class($appid);
} catch (\Exception $exception) {
return new \Exception($exception->getMessage(), $exception->getCode());
}
}
}

View File

@ -0,0 +1,212 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\controller\api;
use app\service\handle\PublishHandle;
use app\service\handle\ReceiveHandle;
use app\service\service\WechatService;
use think\admin\Controller;
use WeOpen\Service;
/**
* 服务平台推送服务
* Class Push
* @package app\service\controller\api
*/
class Push extends Controller
{
/**
* 微信API推送事件处理
* @param string $appid
* @return string
* @throws \WeChat\Exceptions\InvalidDecryptException
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function notify($appid)
{
if (in_array($appid, ['wx570bc396a51b8ff8', 'wxd101a85aa106f53e'])) {
# 全网发布接口测试
return PublishHandle::instance()->handler($appid);
} else {
# 接口类正常服务
return ReceiveHandle::instance()->handler($appid);
}
}
/**
* 一、处理服务推送Ticket
* 二、处理取消公众号授权
* @return string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function ticket()
{
try {
$server = WechatService::WeOpenService();
if (!($data = $server->getComonentTicket())) {
return "Ticket event handling failed.";
}
} catch (\Exception $e) {
return "Ticket event handling failed, {$e->getMessage()}";
}
if (!empty($data['AuthorizerAppid']) && isset($data['InfoType'])) {
# 授权成功通知
if ($data['InfoType'] === 'authorized') {
$this->app->db->name('WechatServiceConfig')->where(['authorizer_appid' => $data['AuthorizerAppid']])->update(['is_deleted' => '0']);
}
# 接收取消授权服务事件
if ($data['InfoType'] === 'unauthorized') {
$this->app->db->name('WechatServiceConfig')->where(['authorizer_appid' => $data['AuthorizerAppid']])->update(['is_deleted' => '1']);
}
# 授权更新通知
if ($data['InfoType'] === 'updateauthorized') {
$_GET['auth_code'] = $data['PreAuthCode'];
$this->applyAuth($server);
}
}
return 'success';
}
/**
* 微信代网页授权
* @throws \think\Exception
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function oauth()
{
list($mode, $appid, $enurl, $sessid) = [
$this->request->get('mode'), $this->request->get('state'),
$this->request->get('enurl'), $this->request->get('sessid'),
];
$result = WechatService::WeOpenService()->getOauthAccessToken($appid);
if (empty($result['openid'])) throw new \think\Exception('网页授权失败, 无法进一步操作!');
$this->app->cache->set("{$appid}_{$sessid}_openid", $result['openid'], 3600);
if (!empty($mode)) {
$fans = WechatService::WeChatOauth($appid)->getUserInfo($result['access_token'], $result['openid']);
if (empty($fans)) throw new \think\Exception('网页授权信息获取失败, 无法进一步操作!');
$this->app->cache->set("{$appid}_{$sessid}_fans", $fans, 3600);
}
$this->redirect(debase64url($enurl));
}
/**
* 跳转到微信服务授权页面
* @return string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function auth()
{
$this->source = input('source');
if (empty($this->source)) {
return '请传入回跳 source 参数 ( 请使用 enbase64url 加密 )';
}
$this->sourceUrl = debase64url($this->source);
if (empty($this->sourceUrl)) {
return '请传入回跳 source 参数 ( 请使用 enbase64url 加密 )';
}
# 预授权码不为空,则表示可以进行授权处理
$service = WechatService::WeOpenService();
if (($auth_code = $this->request->get('auth_code'))) {
return $this->applyAuth($service, $this->sourceUrl);
}
# 生成微信授权链接,使用刷新跳转到授权网页
$redirect = url("@service/api.push/auth", [], true, true) . "?source={$this->source}";
if (($redirect = $service->getAuthRedirect($redirect))) {
ob_clean();
header("Refresh:0;url={$redirect}");
return "<script>window.location.href='{$redirect}';</script><a href='{$redirect}'>跳转中...</a>";
}
# 生成微信授权链接失败
return "<h2>Failed to create authorization. Please return to try again.</h2>";
}
/**
* 公众号授权绑定数据处理
* @param Service $service 平台服务对象
* @param string $redirect 授权成功回跳地址
* @return string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
private function applyAuth(Service $service, $redirect = null)
{
// 通过授权code换取公众号信息
$result = $service->getQueryAuthorizerInfo();
if (empty($result['authorizer_appid'])) {
return "接收微信第三方平台授权失败! ";
}
// 重新通过接口查询公众号参数
if (!($update = array_merge($result, $service->getAuthorizerInfo($result['authorizer_appid'])))) {
return '获取授权数据失败, 请稍候再试!';
}
// 生成公众号授权参数
$update = array_merge($this->buildAuthData($update), [
'status' => '1', 'is_deleted' => '0', 'expires_in' => time() + 7000, 'create_at' => date('y-m-d H:i:s'),
]);
// 微信接口APPKEY处理与更新
$config = $this->app->db->name('WechatServiceConfig')->where(['authorizer_appid' => $result['authorizer_appid']])->find();
$update['appkey'] = empty($config['appkey']) ? md5(uniqid('', true)) : $config['appkey'];
data_save('WechatServiceConfig', $update, 'authorizer_appid');
if (!empty($redirect)) { // 带上appid与appkey跳转到应用
$split = stripos($redirect, '?') > 0 ? '&' : '?';
$realurl = preg_replace(['/appid=\w+/i', '/appkey=\w+/i', '/(\?\&)$/i'], ['', '', ''], $redirect);
return redirect("{$realurl}{$split}appid={$update['authorizer_appid']}&appkey={$update['appkey']}");
}
}
/**
* 生成公众号授权信息
* @param array $info
* @return array
*/
private function buildAuthData(array $info)
{
$info = array_change_key_case($info, CASE_LOWER);
if (isset($info['func_info']) && is_array($info['func_info'])) {
$info['func_info'] = join(',', array_map(function ($tmp) {
return isset($tmp['funcscope_category']['id']) ? $tmp['funcscope_category']['id'] : 0;
}, $info['func_info']));
}
$info['business_info'] = serialize($info['business_info']);
$info['verify_type_info'] = join(',', $info['verify_type_info']);
$info['service_type_info'] = join(',', $info['service_type_info']);
// 微信类型: 0 代表订阅号, 2 代表服务号, 3 代表小程序
$info['service_type'] = intval($info['service_type_info']) === 2 ? 2 : 0;
if (!empty($info['miniprograminfo'])) {
$info['service_type'] = 3;
$info['miniprograminfo'] = serialize($info['miniprograminfo']);
}
// 微信认证: -1 代表未认证, 0 代表微信认证
$info['verify_type'] = intval($info['verify_type_info']) !== 0 ? -1 : 0;
return $info;
}
}

View File

@ -0,0 +1,61 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\handle;
use app\service\service\WechatService;
use think\admin\Service;
/**
* 授权公众上线测试处理
* Class PublishHandle
* @package app\service\serivce
*/
class PublishHandle extends Service
{
/**
* 事件初始化
* @param string $appid
* @return string
* @throws \WeChat\Exceptions\InvalidDecryptException
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function handler($appid)
{
try {
$wechat = WechatService::WeChatReceive($appid);
} catch (\Exception $e) {
return "Wechat message handling failed, {$e->getMessage()}";
}
/* 分别执行对应类型的操作 */
switch (strtolower($wechat->getMsgType())) {
case 'text':
$receive = $wechat->getReceive();
if ($receive['Content'] === 'TESTCOMPONENT_MSG_TYPE_TEXT') {
return $wechat->text('TESTCOMPONENT_MSG_TYPE_TEXT_callback')->reply([], true);
} else {
$key = str_replace("QUERY_AUTH_CODE:", '', $receive['Content']);
WechatService::WeOpenService()->getQueryAuthorizerInfo($key);
return $wechat->text("{$key}_from_api")->reply([], true);
}
case 'event':
$receive = $wechat->getReceive();
return $wechat->text("{$receive['Event']}from_callback")->reply([], true);
default:
return 'success';
}
}
}

View File

@ -0,0 +1,65 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\handle;
use app\service\service\WechatService;
use think\admin\Service;
/**
* 授权公众号消息转发处理
* Class ReceiveHandle
* @package app\service\serivce
*/
class ReceiveHandle extends Service
{
/**
* 事件初始化
* @param string $appid
* @return string
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function handler($appid)
{
try {
$wechat = WechatService::WeChatReceive($appid);
} catch (\Exception $exception) {
return "Wechat message handling failed, {$exception->getMessage()}";
}
// 验证微信配置信息
$config = $this->app->db->name('WechatServiceConfig')->where(['authorizer_appid' => $appid])->find();
if (empty($config) || empty($config['appuri'])) {
sysoplog('微信接口', $message = "微信{$appid}授权配置验证无效");
return $message;
}
try {
list($data, $openid) = [$wechat->getReceive(), $wechat->getOpenid()];
if (isset($data['EventKey']) && is_object($data['EventKey'])) $data['EventKey'] = (array)$data['EventKey'];
$input = ['openid' => $openid, 'appid' => $appid, 'receive' => serialize($data), 'encrypt' => intval($wechat->isEncrypt())];
if (is_string($result = http_post($config['appuri'], $input, ['timeout' => 30]))) {
if (is_array($json = json_decode($result, true))) {
return $wechat->reply($json, true, $wechat->isEncrypt());
} else {
return $result;
}
}
} catch (\Exception $exception) {
sysoplog('微信接口', "微信{$appid}接口调用异常,{$exception->getMessage()}");
}
return 'success';
}
}

View File

@ -0,0 +1,52 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\service;
/**
* Class ClientService
* @package app\service\serivce
*/
class ClientService extends WechatService
{
/**
* 静态调用对象
* @param string $name 请求的类名
* @param array $arguments 调用参数
* @return mixed
* @throws \think\Exception
* @throws \SoapFault
*/
public static function __callStatic($name, $arguments)
{
if (count($arguments) !== 2) {
throw new \think\Exception('请按顺序传入APPID及APPKEY两个参数');
}
list($appid, $appkey) = $arguments;
$data = ['class' => $name, 'appid' => $appid, 'time' => time()];
$data['sign'] = md5("{$data['class']}#{$appid}#{$appkey}#{$data['time']}");
$code = enbase64url(json_encode($data, JSON_UNESCAPED_UNICODE));
if (class_exists('Yar_Client')) {
$url = "http://127.0.0.1:1231/service/api.client/yar?not_init_session=1&code={$code}";
$client = new \Yar_Client($url);
} else {
$url = "http://127.0.0.1:1231/service/api.client/soap?not_init_session=1&code={$code}";
$client = new \SoapClient(null, ['location' => $url, 'uri' => "thinkadmin"]);
}
dump($client->getMessage());
return $client;
}
}

View File

@ -0,0 +1,135 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\service;
use think\admin\Service;
/**
* 公众号授权配置
* Class ConfigService
* @package app\service\service
*/
class ConfigService extends Service
{
/**
* 当前微信APPID
* @var string
*/
protected $appid;
/**
* 当前微信配置
* @var array
*/
protected $config;
/**
* 授权配置初始化
* @param string $appid
* @return $this
* @throws \think\Exception
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function initialize(string $appid): Service
{
$this->appid = $appid;
$this->config = $this->app->db->name('wechatServiceConfig')->where(['authorizer_appid' => $appid])->find();
if (empty($this->config)) {
throw new \think\Exception("公众号{$appid}还没有授权!");
}
return $this;
}
/**
* 获取当前公众号配置
* @return array
*/
public function getConfig()
{
return $this->config;
}
/**
* 设置微信接口通知URL地址
* @param string $notifyUri 接口通知URL地址
* @return boolean
* @throws \think\Exception
* @throws \think\db\exception\DbException
*/
public function setApiNotifyUri($notifyUri)
{
if (empty($notifyUri)) throw new \think\Exception('请传入微信通知URL');
list($where, $data) = [['authorizer_appid' => $this->appid], ['appuri' => $notifyUri]];
return $this->app->db->name('WechatServiceConfig')->where($where)->update($data) !== false;
}
/**
* 更新接口Appkey(成功返回新的Appkey)
* @return bool|string
* @throws \think\db\exception\DbException
*/
public function updateApiAppkey()
{
$data = ['appkey' => md5(uniqid())];
$this->app->db->name('WechatServiceConfig')->where(['authorizer_appid' => $this->appid])->update($data);
return $data['appkey'];
}
/**
* 获取公众号的配置参数
* @param string $name 参数名称
* @return array|string
*/
public function config($name = null)
{
return WechatService::WeChatScript($this->appid)->config->get($name);
}
/**
* 微信网页授权
* @param string $sessid 当前会话id(可用session_id()获取)
* @param string $source 当前会话URL地址(需包含域名的完整URL地址)
* @param integer $type 网页授权模式(0静默模式,1高级授权)
* @return array|boolean
*/
public function oauth($sessid, $source, $type = 0)
{
$fans = $this->app->cache->get("{$this->appid}_{$sessid}_fans");
$openid = $this->app->cache->get("{$this->appid}_{$sessid}_openid");
if (!empty($openid) && (empty($type) || !empty($fans))) {
return ['openid' => $openid, 'fans' => $fans, 'url' => ''];
}
$mode = empty($type) ? 'snsapi_base' : 'snsapi_userinfo';
$url = url('@service/api.push/oauth', [], true, true);
$params = ['mode' => $type, 'sessid' => $sessid, 'enurl' => enbase64url($source)];
$authurl = WechatService::WeOpenService()->getOauthRedirect($this->appid, $url . '?' . http_build_query($params), $mode);
return ['openid' => $openid, 'fans' => $fans, 'url' => $authurl];
}
/**
* 微信网页JS签名
* @param string $url 当前会话URL地址(需包含域名的完整URL地址)
* @return array|boolean
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function jsSign($url)
{
return WechatService::WeChatScript($this->appid)->getJsSign($url);
}
}

View File

@ -0,0 +1,184 @@
<?php
// +----------------------------------------------------------------------
// | ThinkAdmin
// +----------------------------------------------------------------------
// | 版权所有 2014~2019 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://demo.thinkadmin.top
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | gitee 代码仓库https://gitee.com/zoujingli/ThinkAdmin
// | github 代码仓库https://github.com/zoujingli/ThinkAdmin
// +----------------------------------------------------------------------
namespace app\service\service;
use think\admin\Service;
/**
* Class WechatService
* @package app\service\serivce
*
* @method \WeChat\Card WeChatCard($appid) static 微信卡券管理
* @method \WeChat\Custom WeChatCustom($appid) static 微信客服消息
* @method \WeChat\Limit WeChatLimit($appid) static 接口调用频次限制
* @method \WeChat\Media WeChatMedia($appid) static 微信素材管理
* @method \WeChat\Menu WeChatMenu($appid) static 微信菜单管理
* @method \WeChat\Oauth WeChatOauth($appid) static 微信网页授权
* @method \WeChat\Pay WeChatPay($appid) static 微信支付商户
* @method \WeChat\Product WeChatProduct($appid) static 微信商店管理
* @method \WeChat\Qrcode WeChatQrcode($appid) static 微信二维码管理
* @method \WeChat\Receive WeChatReceive($appid) static 微信推送管理
* @method \WeChat\Scan WeChatScan($appid) static 微信扫一扫接入管理
* @method \WeChat\Script WeChatScript($appid) static 微信前端支持
* @method \WeChat\Shake WeChatShake($appid) static 微信揺一揺周边
* @method \WeChat\Tags WeChatTags($appid) static 微信用户标签管理
* @method \WeChat\Template WeChatTemplate($appid) static 微信模板消息
* @method \WeChat\User WeChatUser($appid) static 微信粉丝管理
* @method \WeChat\Wifi WeChatWifi($appid) static 微信门店WIFI管理
*
* ----- WeMini -----
* @method \WeMini\Account WeMiniAccount($appid) static 小程序账号管理
* @method \WeMini\Basic WeMiniBasic($appid) static 小程序基础信息设置
* @method \WeMini\Code WeMiniCode($appid) static 小程序代码管理
* @method \WeMini\Domain WeMiniDomain($appid) static 小程序域名管理
* @method \WeMini\Tester WeMinitester($appid) static 小程序成员管理
* @method \WeMini\User WeMiniUser($appid) static 小程序帐号管理
* --------------------
* @method \WeMini\Crypt WeMiniCrypt($options = []) static 小程序数据加密处理
* @method \WeMini\Delivery WeMiniDelivery($options = []) static 小程序即时配送
* @method \WeMini\Image WeMiniImage($options = []) static 小程序图像处理
* @method \WeMini\Logistics WeMiniLogistics($options = []) static 小程序物流助手
* @method \WeMini\Message WeMiniMessage($options = []) static 小程序动态消息
* @method \WeMini\Ocr WeMiniOcr($options = []) static 小程序ORC服务
* @method \WeMini\Plugs WeMiniPlugs($options = []) static 小程序插件管理
* @method \WeMini\Poi WeMiniPoi($options = []) static 小程序地址管理
* @method \WeMini\Qrcode WeMiniQrcode($options = []) static 小程序二维码管理
* @method \WeMini\Security WeMiniSecurity($options = []) static 小程序内容安全
* @method \WeMini\Soter WeMiniSoter($options = []) static 小程序生物认证
* @method \WeMini\Template WeMiniTemplate($options = []) static 小程序模板消息支持
* @method \WeMini\Total WeMiniTotal($options = []) static 小程序数据接口
*
* ----- WePay -----
* @method \WePay\Bill WePayBill($appid) static 微信商户账单及评论
* @method \WePay\Order WePayOrder($appid) static 微信商户订单
* @method \WePay\Refund WePayRefund($appid) static 微信商户退款
* @method \WePay\Coupon WePayCoupon($appid) static 微信商户代金券
* @method \WePay\Redpack WePayRedpack($appid) static 微信红包支持
* @method \WePay\Transfers WePayTransfers($appid) static 微信商户打款到零钱
* @method \WePay\TransfersBank WePayTransfersBank($appid) static 微信商户打款到银行卡
*
* ----- WeOpen -----
* @method \WeOpen\Login WeOpenLogin() static 第三方微信登录
* @method \WeOpen\Service WeOpenService() static 第三方服务
*
* ----- ThinkService -----
* @method ConfigService ThinkAdminConfig($appid) static 平台服务配置
*/
class WechatService extends Service
{
/**
* 静态初始化对象
* @param string $name
* @param array $arguments
* @return mixed
* @throws \think\Exception
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public static function __callStatic($name, $arguments)
{
list($type, $class) = ['-', '-'];
foreach (['WeChat', 'WeMini', 'WeOpen', 'WePay', 'ThinkAdmin'] as $type) {
if (strpos($name, $type) === 0) {
list(, $class) = explode($type, $name);
break;
}
}
if ("{$type}{$class}" !== $name) {
throw new \think\Exception("class {$name} not defined.");
}
if (in_array($type, ['WeChat', 'WePay', 'WeMini', 'ThinkAdmin'])) {
if (empty($arguments[0])) {
throw new \think\Exception("Appid parameter must be passed in during initialization");
}
}
$classname = "\\{$type}\\{$class}";
if (in_array($type, ['WeChat', 'WeMini', 'WePay'])) {
return new $classname(self::instance()->getWechatConfig($arguments[0]));
} elseif ($type === 'ThinkAdmin' && $class === 'Config') {
return ConfigService::instance()->initialize($arguments[0]);
} elseif ($type === 'WeOpen') {
return new $classname(self::instance()->getServiceConfig());
} else {
throw new \think\Exception("class {$classname} not defined.");
}
}
/**
* 获取公众号配置参数
* @param string $authorizerAppid
* @return array
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function getWechatConfig($authorizerAppid)
{
$conifg = [
'appid' => $authorizerAppid,
'token' => sysconf('service.component_token'),
'appsecret' => sysconf('service.component_appsecret'),
'encodingaeskey' => sysconf('service.component_encodingaeskey'),
'cache_path' => $this->getCachePath(),
];
$conifg['GetAccessTokenCallback'] = function ($authorizerAppid) {
$map = ['authorizer_appid' => $authorizerAppid];
$refreshToken = $this->app->db->name('WechatServiceConfig')->where($map)->value('authorizer_refresh_token');
if (empty($refreshToken)) throw new \think\Exception('The WeChat information is not configured.', '404');
// 刷新公众号原授权 AccessToken
$result = WechatService::WeOpenService()->refreshAccessToken($authorizerAppid, $refreshToken);
if (empty($result['authorizer_access_token']) || empty($result['authorizer_refresh_token'])) {
throw new \think\Exception($result['errmsg']);
}
// 更新公众号授权信息
$this->app->db->name('WechatServiceConfig')->where($map)->update([
'authorizer_access_token' => $result['authorizer_access_token'],
'authorizer_refresh_token' => $result['authorizer_refresh_token'],
]);
return $result['authorizer_access_token'];
};
return $conifg;
}
/**
* 获取服务平台配置参数
* @return array
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public function getServiceConfig()
{
return [
'cache_path' => $this->getCachePath(),
'component_appid' => sysconf('service.component_appid'),
'component_token' => sysconf('service.component_token'),
'component_appsecret' => sysconf('service.component_appsecret'),
'component_encodingaeskey' => sysconf('service.component_encodingaeskey'),
];
}
/**
* 获取缓存目录
* @return string
*/
private function getCachePath()
{
return $this->app->getRuntimePath() . 'wechat';
}
}

View File

@ -0,0 +1,44 @@
<form onsubmit="return false;" action="{:request()->url()}" data-auto="true" method="post" class='layui-form layui-card' autocomplete="off">
<div class="layui-card-body padding-left-40">
<div class="layui-form-item">
<label class="relative block">
<span class="color-green font-w7">开放平台服务 AppID</span>
<input name="service.component_appid" required pattern="^.{18}$" maxlength="18" placeholder="请输入18位开放平台服务AppID" value="{:sysconf('service.component_appid')}" class="layui-input">
</label>
<p class="help-block">开放平台服务 AppID需要在微信开放平台获取</p>
</div>
<div class="layui-form-item">
<label class="relative block">
<span class="color-green font-w7">开放平台服务 AppSecret</span>
<input name="service.component_appsecret" required pattern="^.{32}$" maxlength="32" placeholder="请输入32位开放平台服务AppSecret" value="{:sysconf('service.component_appsecret')}" class="layui-input">
</label>
<p class="help-block">开放平台服务 AppSecret需要在微信开放平台获取</p>
</div>
<div class="layui-form-item">
<label class="relative block">
<span class="color-green font-w7">开放平台消息校验 Token</span>
<input name="service.component_token" required placeholder="请输入微信消息校验Token" value="{:sysconf('service.component_token')}" class="layui-input">
</label>
<p class="help-block">开发者在代替微信接收到消息时,用此 Token 来校验消息</p>
</div>
<div class="layui-form-item">
<label class="relative block">
<span class="color-green font-w7">开放平台消息加解密 AesKey</span>
<input name="service.component_encodingaeskey" required pattern="^.{43}$" maxlength="43" placeholder="请输入43位微信消息加解密Key" value="{:sysconf('service.component_encodingaeskey')}" class="layui-input">
</label>
<p class="help-block">在代替微信收发消息时使用必须是长度为43位字母和数字组合的字符串</p>
</div>
<div class="hr-line-dashed"></div>
<div class="text-center padding-bottom-15 margin-bottom-20">
<button class="layui-btn" type="submit">保存配置</button>
</div>
</div>
</form>

View File

@ -0,0 +1,98 @@
{extend name='../../admin/view/main'}
{block name="button"}
{if auth("edit")}
<button data-modal="{:url('edit')}" class='layui-btn layui-btn-sm layui-btn-primary'>配置平台参数</button>
{/if}
{/block}
{block name="content"}
<div class="relative">
<div class="think-box-shadow border-0 margin-bottom-20">
强烈建议安装 YAR 扩展来实现接口通信SOAP 不能正常显示接口的异常信息
</div>
<div class="think-box-shadow padding-right-40 padding-left-40">
<div class="layui-row layui-col-space18">
<div class="layui-col-md6">
<div class="layui-form-item">
<span class="color-green font-w7">开放平台服务</span>
<span class="color-desc margin-left-5">AppID</span>
<label class="relative block">
<input disabled class="layui-input layui-bg-gray" value="{:sysconf('service.component_appid')}">
<a data-copy="{:sysconf('service.component_appid')}" class="fa fa-copy input-right-icon"></a>
</label>
<p class="help-block">开放平台服务 AppID需要在微信开放平台获取</p>
</div>
<div class="layui-form-item">
<span class="color-green font-w7">开放平台服务</span>
<span class="color-desc margin-left-5">AppSecret</span>
<label class="relative block">
<input disabled class="layui-input layui-bg-gray" value="{:sysconf('service.component_appsecret')}">
<a data-copy="{:sysconf('service.component_appsecret')}" class="fa fa-copy input-right-icon"></a>
</label>
<p class="help-block">开放平台服务 AppSecret需要在微信开放平台获取</p>
</div>
<div class="layui-form-item">
<span class="color-green font-w7">开放平台消息校验</span>
<span class="color-desc margin-left-5">Token</span>
<label class="relative block">
<input disabled class="layui-input layui-bg-gray" value="{:sysconf('service.component_token')}">
<a data-copy="{:sysconf('service.component_token')}" class="fa fa-copy input-right-icon"></a>
</label>
<p class="help-block">开发者在代替微信接收到消息时,用此 Token 来校验消息</p>
</div>
<div class="layui-form-item">
<span class="color-green font-w7">开放平台消息加解密</span>
<span class="color-desc margin-left-5">AesKey</span>
<label class="relative block">
<input disabled class="layui-input layui-bg-gray" value="{:sysconf('service.component_encodingaeskey')}">
<a data-copy="{:sysconf('service.component_encodingaeskey')}" class="fa fa-copy input-right-icon"></a>
</label>
<p class="help-block">在代替微信收发消息时使用必须是长度为43位字母和数字组合的字符串</p>
</div>
</div>
<div class="layui-col-md6">
<div class="layui-form-item">
<p class="color-green font-w7">授权发起页域名</p>
<label class="relative block">
<input disabled class="layui-input layui-bg-gray" value="{:request()->host()}">
<a data-copy="{:request()->host()}" class="fa fa-copy input-right-icon"></a>
</label>
<p class="help-block">从本域名跳转到登录授权页才可以完成登录授权,无需填写域名协议前缀</p>
</div>
<div class="layui-form-item">
<span class="color-green font-w7">授权事件接收地址</span>
<label class="relative block">
<input disabled class="layui-input layui-bg-gray" value="{:url('@service/api.push/ticket',[],false,true)}">
<a data-copy="{:url('@service/api.push/ticket',[],false,true)}" class="fa fa-copy input-right-icon"></a>
</label>
<p class="help-block">用于接收取消授权通知、授权成功通知、授权更新通知、接收 TICKET 凭据</p>
</div>
<div class="layui-form-item">
<span class="color-green font-w7">微信消息与事件接收</span>
<label class="relative block">
<input disabled class="layui-input layui-bg-gray" value="{:url('@service/api.push/notify/\$APPID\$',[],false,true)}">
<a data-copy="{:url('@service/api.push/notify/\$APPID\$',[],false,true)}" class="fa fa-copy input-right-icon"></a>
</label>
<p class="help-block">通过该 URL 接收微信消息和事件推送,$APPID$ 将被替换为微信 AppId</p>
</div>
<div class="layui-form-item">
<p class="color-green font-w7">客户端系统 Yar 模块接口</p>
<label class="relative block"><input disabled class="layui-input layui-bg-gray" value="{:url('@service/api.client/yar/PARAM',[],false,true)}"></label>
<p class="help-block">客户端 Yar 接口PARAM 规则 AppName-AppId-AppKey-AppType</p>
</div>
<div class="layui-form-item">
<p class="color-green font-w7">客户端系统 Soap 模块接口</p>
<label class="relative block"><input disabled class="layui-input layui-bg-gray" value="{:url('@service/api.client/soap/PARAM',[],false,true)}"></label>
<p class="help-block">客户端 Soap 接口PARAM 规则 AppName-AppId-AppKey-AppType</p>
</div>
</div>
</div>
</div>
</div>
{/block}

View File

@ -0,0 +1 @@
还没有授权,请授权公众号

View File

@ -0,0 +1,85 @@
{extend name='../../admin/view/main'}
{block name="button"}
{if auth("syncall")}
<button data-load="{:url('syncall')}" class='layui-btn layui-btn-sm layui-btn-primary'>同步所有授权</button>
{/if}
{/block}
{block name="content"}
<div class="think-box-shadow">
{include file='index/index_search'}
<table class="layui-table margin-top-10" lay-skin="line">
{notempty name='list'}
<thead>
<tr>
<th class='text-left nowrap' style="width:390px">接口信息</th>
<th class='text-left nowrap' style="width:120px">服务号信息</th>
<th class='text-left nowrap'></th>
<th class='text-left nowrap'></th>
</tr>
</thead>
{/notempty}
<tbody>
{foreach $list as $key=>$vo}
<tr>
<td class='text-left nowrap'>
<div class="inline-block text-top margin-right-5">
<img alt="" style="width:60px;height:60px" data-tips-text="微信头像" data-tips-image src="{$vo.head_img|default=''}">
</div>
<div class="inline-block">
公众号APPID{$vo.authorizer_appid}&nbsp;&nbsp;&nbsp;&nbsp;调用次数:{$vo.total}<br>
接口授权密钥:{$vo.appkey|default='<span class="color-desc">未生成接口服务密码, 请稍候授权绑定</span>'|raw}<br>
消息推送接口:{$vo.appuri|default='<span class="color-desc">未配置消息推送接口</span>'|raw}
</div>
</td>
<td class='text-left nowrap'>
<div class="inline-block text-top margin-right-5">
<img onerror="this.src='__ROOT__/static/theme/img/404_icon.png'" style="width:60px;height:60px" data-tips-text="微信二维码" data-tips-image src="{$vo.qrcode_url|local_image}">
</div>
<div class="inline-block">
昵称:{$vo.nick_name|default='<span class="color-desc">未获取到公众号昵称</span>'|raw}<br>
公司:{$vo.principal_name|default='<span class="color-desc">未获取到公司名字</span>'|raw}<br>
状态:{if $vo.service_type eq 2}服务号{elseif $vo.service_type eq 3}小程序{else}订阅号{/if} /
{$vo.verify_type == -1 ? '<span class="color-red">未认证</span>' : '<span class="color-green">已认证</span>'} /
{if $vo.status eq 0}<span class="color-red">已禁用</span>{elseif $vo.status eq 1}<span class="color-green">使用中</span>{/if}
</div>
</td>
<td class="text-left nowrap">
账号:{$vo.user_name|default='--'}<br>
日期:{$vo.create_at|format_datetime|str_replace=' ','<br>时间:',###|raw}
</td>
<td class='text-left nowrap'>
{if $vo.status eq 1 and auth("state")}
<a class="layui-btn layui-btn-sm layui-btn-warm" data-action="{:url('state')}" data-csrf="{:systoken('state')}" data-value="id#{$vo.id};status#0">禁 用</a>
{elseif auth("state")}
<a class="layui-btn layui-btn-sm layui-btn-warm" data-action="{:url('state')}" data-csrf="{:systoken('state')}" data-value="id#{$vo.id};status#1">启 用</a>
{/if}
{if auth("remove")}
<a class="layui-btn layui-btn-sm layui-btn-danger" data-confirm="确定要删除该公众号吗?" data-action="{:url('remove')}" data-csrf="{:systoken('remove')}" data-value="id#{$vo.id}">删 除</a>
{/if}
{if auth("sync")}
<a class="layui-btn layui-btn-sm" data-load='{:url("sync")}?appid={$vo.authorizer_appid}'>同 步</a>
{/if}
{if auth("clearquota")}
<a class="layui-btn layui-btn-sm layui-btn-primary" data-confirm="每个公众号每个月有10次清零机会请谨慎使用" data-load='{:url("clearquota")}?appid={$vo.authorizer_appid}'>清 零</a>
{/if}
</td>
</tr>
{/foreach}
</tbody>
</table>
{empty name='list'}<span class="notdata">没有记录哦</span>{else}{$pagehtml|raw|default=''}{/empty}
</div>
{/block}

View File

@ -0,0 +1,76 @@
<fieldset>
<legend>条件搜索</legend>
<form class="layui-form layui-form-pane form-search" action="{:request()->url()}" onsubmit="return false" method="get" autocomplete="off">
<div class="layui-form-item layui-inline">
<label class="layui-form-label">微信标识</label>
<div class="layui-input-inline">
<input name="authorizer_appid" value="{$Think.get.authorizer_appid|default=''}" placeholder="请输入微信APPID" class="layui-input">
</div>
</div>
<div class="layui-form-item layui-inline">
<label class="layui-form-label">微信名称</label>
<div class="layui-input-inline">
<input name="nick_name" value="{$Think.get.nick_name|default=''}" placeholder="请输入微信名称" class="layui-input">
</div>
</div>
<div class="layui-form-item layui-inline">
<label class="layui-form-label">类型过滤</label>
<div class="layui-input-inline">
<select name="service_type" class="layui-select">
<option value="">- 全部 -</option>
{foreach ['0'=>'显示订阅号类型','2'=>'显示服务号类型','3'=>'显示小程序类型'] as $k=>$v}
<!--{if $k.'' eq $Think.get.service_type}-->
<option selected value="{$k}">{$v}</option>
<!--{else}-->
<option value="{$k}">{$v}</option>
<!--{/if}-->
{/foreach}
</select>
</div>
</div>
<div class="layui-form-item layui-inline">
<label class="layui-form-label">使用状态</label>
<div class="layui-input-inline">
<select class="layui-select" name="status">
{foreach [''=>'- 全部 -','0'=>'已禁用的账号','1'=>'使用中的账号'] as $k=>$v}
{eq name='Think.get.status' value='$k.""'}
<option selected value="{$k}">{$v}</option>
{else}
<option value="{$k}">{$v}</option>
{/eq}
{/foreach}
</select>
</div>
</div>
<div class="layui-form-item layui-inline">
<label class="layui-form-label">注册公司</label>
<div class="layui-input-inline">
<input name="principal_name" value="{$Think.get.principal_name|default=''}" placeholder="请输入注册公司" class="layui-input">
</div>
</div>
<div class="layui-form-item layui-inline">
<label class="layui-form-label">授权时间</label>
<div class="layui-input-inline">
<input data-date-range name="create_at" value="{$Think.get.create_at|default=''}" placeholder="请选择授权时间" class="layui-input">
</div>
</div>
<div class="layui-form-item layui-inline">
<button class="layui-btn layui-btn-primary"><i class="layui-icon">&#xe615;</i> 搜 索</button>
</div>
</form>
</fieldset>
<script>
window.form.render();
</script>

View File

@ -19,6 +19,7 @@
"require": {
"php": ">=7.1.0",
"ext-gd": "*",
"ext-soap": "*",
"ext-json": "*",
"ext-curl": "*",
"ext-iconv": "*",
@ -26,7 +27,8 @@
"topthink/think-view": "^1.0",
"topthink/think-multi-app": "^1.0",
"zoujingli/ip2region": "^1.0",
"zoujingli/think-library": "6.0.*-dev"
"zoujingli/think-library": "6.0.*-dev",
"zoujingli/weopen-developer": "dev-master"
},
"autoload": {
"psr-4": {

135
composer.lock generated
View File

@ -4,20 +4,20 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
"content-hash": "44a6bc247971794be9edd9df4f3dd0b9",
"content-hash": "1b0862db0bebe6fd5b8f1edc448e3f5a",
"packages": [
{
"name": "league/flysystem",
"version": "1.0.57",
"version": "1.0.61",
"source": {
"type": "git",
"url": "https://github.com/thephpleague/flysystem.git",
"reference": "0e9db7f0b96b9f12dcf6f65bc34b72b1a30ea55a"
"reference": "4fb13c01784a6c9f165a351e996871488ca2d8c9"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/thephpleague/flysystem/zipball/0e9db7f0b96b9f12dcf6f65bc34b72b1a30ea55a",
"reference": "0e9db7f0b96b9f12dcf6f65bc34b72b1a30ea55a",
"url": "https://api.github.com/repos/thephpleague/flysystem/zipball/4fb13c01784a6c9f165a351e996871488ca2d8c9",
"reference": "4fb13c01784a6c9f165a351e996871488ca2d8c9",
"shasum": "",
"mirrors": [
{
@ -94,7 +94,7 @@
"sftp",
"storage"
],
"time": "2019-10-16T21:01:05+00:00"
"time": "2019-12-08T21:46:50+00:00"
},
{
"name": "league/flysystem-cached-adapter",
@ -833,19 +833,140 @@
"description": "ThinkPHP v6.0 Development Library",
"homepage": "http://framework.thinkadmin.top",
"time": "2019-12-07T06:46:30+00:00"
},
{
"name": "zoujingli/wechat-developer",
"version": "v1.2.15",
"source": {
"type": "git",
"url": "https://github.com/zoujingli/WeChatDeveloper.git",
"reference": "4b81e72cff7a3acfde2cca919bd8e173355bc53c"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/zoujingli/WeChatDeveloper/zipball/4b81e72cff7a3acfde2cca919bd8e173355bc53c",
"reference": "4b81e72cff7a3acfde2cca919bd8e173355bc53c",
"shasum": "",
"mirrors": [
{
"url": "https://mirrors.aliyun.com/composer/dists/%package%/%reference%.%type%",
"preferred": true
}
]
},
"require": {
"ext-curl": "*",
"ext-json": "*",
"ext-libxml": "*",
"ext-mbstring": "*",
"ext-openssl": "*",
"ext-simplexml": "*",
"php": ">=5.4"
},
"type": "library",
"autoload": {
"classmap": [
"We.php"
],
"psr-4": {
"WePay\\": "WePay",
"WeMini\\": "WeMini",
"WeChat\\": "WeChat",
"AliPay\\": "AliPay"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Anyon",
"email": "zoujingli@qq.com",
"homepage": "http://ctolog.com"
}
],
"description": "WeChat platform and WeChat payment development tools",
"homepage": "https://github.com/zoujingli/WeChatDeveloper",
"keywords": [
"WeChatDeveloper",
"WeMini",
"alipay",
"wechat",
"wechatpay",
"wepay"
],
"time": "2019-11-25T10:40:50+00:00"
},
{
"name": "zoujingli/weopen-developer",
"version": "dev-master",
"source": {
"type": "git",
"url": "https://github.com/zoujingli/WeOpenDeveloper.git",
"reference": "4d0d3c064e54556621453845fc65ba52de58a880"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/zoujingli/WeOpenDeveloper/zipball/4d0d3c064e54556621453845fc65ba52de58a880",
"reference": "4d0d3c064e54556621453845fc65ba52de58a880",
"shasum": "",
"mirrors": [
{
"url": "https://mirrors.aliyun.com/composer/dists/%package%/%reference%.%type%",
"preferred": true
}
]
},
"require": {
"ext-curl": "*",
"ext-json": "*",
"ext-openssl": "*",
"php": ">=5.4",
"zoujingli/wechat-developer": "^1.0"
},
"type": "library",
"autoload": {
"psr-4": {
"WeOpen\\": "WeOpen",
"WeChat\\": "WeChat",
"WeMini\\": "WeMini"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Anyon",
"email": "zoujingli@qq.com",
"homepage": "http://ctolog.com"
}
],
"description": "WeChat Open development of SDK",
"homepage": "https://github.com/zoujingli/WeOpenDeveloper",
"keywords": [
"WeChatOpen",
"WeChatOpenDeveloper",
"wechat"
],
"time": "2019-10-10T10:18:05+00:00"
}
],
"packages-dev": [],
"aliases": [],
"minimum-stability": "stable",
"stability-flags": {
"zoujingli/think-library": 20
"zoujingli/think-library": 20,
"zoujingli/weopen-developer": 20
},
"prefer-stable": false,
"prefer-lowest": false,
"platform": {
"php": ">=7.1.0",
"ext-gd": "*",
"ext-soap": "*",
"ext-json": "*",
"ext-curl": "*",
"ext-iconv": "*"

View File

@ -6,6 +6,13 @@ $vendorDir = dirname(dirname(__FILE__));
$baseDir = dirname($vendorDir);
return array(
'AliPay\\App' => $vendorDir . '/zoujingli/wechat-developer/AliPay/App.php',
'AliPay\\Bill' => $vendorDir . '/zoujingli/wechat-developer/AliPay/Bill.php',
'AliPay\\Pos' => $vendorDir . '/zoujingli/wechat-developer/AliPay/Pos.php',
'AliPay\\Scan' => $vendorDir . '/zoujingli/wechat-developer/AliPay/Scan.php',
'AliPay\\Transfer' => $vendorDir . '/zoujingli/wechat-developer/AliPay/Transfer.php',
'AliPay\\Wap' => $vendorDir . '/zoujingli/wechat-developer/AliPay/Wap.php',
'AliPay\\Web' => $vendorDir . '/zoujingli/wechat-developer/AliPay/Web.php',
'Ip2Region' => $vendorDir . '/zoujingli/ip2region/Ip2Region.php',
'League\\Flysystem\\AdapterInterface' => $vendorDir . '/league/flysystem/src/AdapterInterface.php',
'League\\Flysystem\\Adapter\\AbstractAdapter' => $vendorDir . '/league/flysystem/src/Adapter/AbstractAdapter.php',
@ -95,6 +102,68 @@ return array(
'Psr\\SimpleCache\\CacheException' => $vendorDir . '/psr/simple-cache/src/CacheException.php',
'Psr\\SimpleCache\\CacheInterface' => $vendorDir . '/psr/simple-cache/src/CacheInterface.php',
'Psr\\SimpleCache\\InvalidArgumentException' => $vendorDir . '/psr/simple-cache/src/InvalidArgumentException.php',
'We' => $vendorDir . '/zoujingli/wechat-developer/We.php',
'WeChat\\Bind' => $vendorDir . '/zoujingli/weopen-developer/WeChat/Bind.php',
'WeChat\\Card' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Card.php',
'WeChat\\Contracts\\BasicAliPay' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/BasicAliPay.php',
'WeChat\\Contracts\\BasicPushEvent' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/BasicPushEvent.php',
'WeChat\\Contracts\\BasicWeChat' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/BasicWeChat.php',
'WeChat\\Contracts\\BasicWePay' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/BasicWePay.php',
'WeChat\\Contracts\\DataArray' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/DataArray.php',
'WeChat\\Contracts\\DataError' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/DataError.php',
'WeChat\\Contracts\\MyCurlFile' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/MyCurlFile.php',
'WeChat\\Contracts\\Tools' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Contracts/Tools.php',
'WeChat\\Custom' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Custom.php',
'WeChat\\Exceptions\\InvalidArgumentException' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidArgumentException.php',
'WeChat\\Exceptions\\InvalidDecryptException' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidDecryptException.php',
'WeChat\\Exceptions\\InvalidInstanceException' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidInstanceException.php',
'WeChat\\Exceptions\\InvalidResponseException' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidResponseException.php',
'WeChat\\Exceptions\\LocalCacheException' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Exceptions/LocalCacheException.php',
'WeChat\\Limit' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Limit.php',
'WeChat\\Media' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Media.php',
'WeChat\\Menu' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Menu.php',
'WeChat\\Mini' => $vendorDir . '/zoujingli/weopen-developer/WeChat/Mini.php',
'WeChat\\Oauth' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Oauth.php',
'WeChat\\Pay' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Pay.php',
'WeChat\\Product' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Product.php',
'WeChat\\Qrcode' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Qrcode.php',
'WeChat\\Receive' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Receive.php',
'WeChat\\Scan' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Scan.php',
'WeChat\\Script' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Script.php',
'WeChat\\Shake' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Shake.php',
'WeChat\\Tags' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Tags.php',
'WeChat\\Template' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Template.php',
'WeChat\\User' => $vendorDir . '/zoujingli/wechat-developer/WeChat/User.php',
'WeChat\\Wifi' => $vendorDir . '/zoujingli/wechat-developer/WeChat/Wifi.php',
'WeMini\\Account' => $vendorDir . '/zoujingli/weopen-developer/WeMini/Account.php',
'WeMini\\Basic' => $vendorDir . '/zoujingli/weopen-developer/WeMini/Basic.php',
'WeMini\\Code' => $vendorDir . '/zoujingli/weopen-developer/WeMini/Code.php',
'WeMini\\Crypt' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Crypt.php',
'WeMini\\Delivery' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Delivery.php',
'WeMini\\Domain' => $vendorDir . '/zoujingli/weopen-developer/WeMini/Domain.php',
'WeMini\\Image' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Image.php',
'WeMini\\Logistics' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Logistics.php',
'WeMini\\Message' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Message.php',
'WeMini\\Ocr' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Ocr.php',
'WeMini\\Plugs' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Plugs.php',
'WeMini\\Poi' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Poi.php',
'WeMini\\Qrcode' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Qrcode.php',
'WeMini\\Security' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Security.php',
'WeMini\\Soter' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Soter.php',
'WeMini\\Template' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Template.php',
'WeMini\\Tester' => $vendorDir . '/zoujingli/weopen-developer/WeMini/Tester.php',
'WeMini\\Total' => $vendorDir . '/zoujingli/wechat-developer/WeMini/Total.php',
'WeMini\\User' => $vendorDir . '/zoujingli/weopen-developer/WeMini/User.php',
'WeOpen\\Login' => $vendorDir . '/zoujingli/weopen-developer/WeOpen/Login.php',
'WeOpen\\MiniApp' => $vendorDir . '/zoujingli/weopen-developer/WeOpen/MiniApp.php',
'WeOpen\\Service' => $vendorDir . '/zoujingli/weopen-developer/WeOpen/Service.php',
'WePay\\Bill' => $vendorDir . '/zoujingli/wechat-developer/WePay/Bill.php',
'WePay\\Coupon' => $vendorDir . '/zoujingli/wechat-developer/WePay/Coupon.php',
'WePay\\Order' => $vendorDir . '/zoujingli/wechat-developer/WePay/Order.php',
'WePay\\Redpack' => $vendorDir . '/zoujingli/wechat-developer/WePay/Redpack.php',
'WePay\\Refund' => $vendorDir . '/zoujingli/wechat-developer/WePay/Refund.php',
'WePay\\Transfers' => $vendorDir . '/zoujingli/wechat-developer/WePay/Transfers.php',
'WePay\\TransfersBank' => $vendorDir . '/zoujingli/wechat-developer/WePay/TransfersBank.php',
'app\\admin\\controller\\Auth' => $baseDir . '/app/admin/controller/Auth.php',
'app\\admin\\controller\\Config' => $baseDir . '/app/admin/controller/Config.php',
'app\\admin\\controller\\Index' => $baseDir . '/app/admin/controller/Index.php',
@ -107,6 +176,16 @@ return array(
'app\\admin\\controller\\api\\Update' => $baseDir . '/app/admin/controller/api/Update.php',
'app\\admin\\controller\\api\\Upload' => $baseDir . '/app/admin/controller/api/Upload.php',
'app\\index\\controller\\Index' => $baseDir . '/app/index/controller/Index.php',
'app\\service\\controller\\Config' => $baseDir . '/app/service/controller/Config.php',
'app\\service\\controller\\Fans' => $baseDir . '/app/service/controller/Fans.php',
'app\\service\\controller\\Wechat' => $baseDir . '/app/service/controller/Wechat.php',
'app\\service\\controller\\api\\Client' => $baseDir . '/app/service/controller/api/Client.php',
'app\\service\\controller\\api\\Push' => $baseDir . '/app/service/controller/api/Push.php',
'app\\service\\serivce\\ClientService' => $baseDir . '/app/service/serivce/ClientService.php',
'app\\service\\serivce\\ConfigService' => $baseDir . '/app/service/serivce/ConfigService.php',
'app\\service\\serivce\\PublishService' => $baseDir . '/app/service/serivce/PublishService.php',
'app\\service\\serivce\\ReceiveService' => $baseDir . '/app/service/serivce/ReceiveService.php',
'app\\service\\serivce\\WechatService' => $baseDir . '/app/service/serivce/WechatService.php',
'think\\App' => $vendorDir . '/topthink/framework/src/think/App.php',
'think\\Cache' => $vendorDir . '/topthink/framework/src/think/Cache.php',
'think\\Collection' => $vendorDir . '/topthink/think-helper/src/Collection.php',

View File

@ -11,6 +11,10 @@ return array(
'think\\admin\\' => array($vendorDir . '/zoujingli/think-library/src'),
'think\\' => array($vendorDir . '/topthink/framework/src/think', $vendorDir . '/topthink/think-helper/src', $vendorDir . '/topthink/think-orm/src', $vendorDir . '/topthink/think-template/src'),
'app\\' => array($baseDir . '/app'),
'WePay\\' => array($vendorDir . '/zoujingli/wechat-developer/WePay'),
'WeOpen\\' => array($vendorDir . '/zoujingli/weopen-developer/WeOpen'),
'WeMini\\' => array($vendorDir . '/zoujingli/wechat-developer/WeMini', $vendorDir . '/zoujingli/weopen-developer/WeMini'),
'WeChat\\' => array($vendorDir . '/zoujingli/wechat-developer/WeChat', $vendorDir . '/zoujingli/weopen-developer/WeChat'),
'Psr\\SimpleCache\\' => array($vendorDir . '/psr/simple-cache/src'),
'Psr\\Log\\' => array($vendorDir . '/psr/log/Psr/Log'),
'Psr\\Container\\' => array($vendorDir . '/psr/container/src'),
@ -18,4 +22,5 @@ return array(
'Opis\\Closure\\' => array($vendorDir . '/opis/closure/src'),
'League\\Flysystem\\Cached\\' => array($vendorDir . '/league/flysystem-cached-adapter/src'),
'League\\Flysystem\\' => array($vendorDir . '/league/flysystem/src'),
'AliPay\\' => array($vendorDir . '/zoujingli/wechat-developer/AliPay'),
);

View File

@ -24,6 +24,13 @@ class ComposerStaticInit078c2496db47e2e94f2057948fdfa517
array (
'app\\' => 4,
),
'W' =>
array (
'WePay\\' => 6,
'WeOpen\\' => 7,
'WeMini\\' => 7,
'WeChat\\' => 7,
),
'P' =>
array (
'Psr\\SimpleCache\\' => 16,
@ -40,6 +47,10 @@ class ComposerStaticInit078c2496db47e2e94f2057948fdfa517
'League\\Flysystem\\Cached\\' => 24,
'League\\Flysystem\\' => 17,
),
'A' =>
array (
'AliPay\\' => 7,
),
);
public static $prefixDirsPsr4 = array (
@ -66,6 +77,24 @@ class ComposerStaticInit078c2496db47e2e94f2057948fdfa517
array (
0 => __DIR__ . '/../..' . '/app',
),
'WePay\\' =>
array (
0 => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay',
),
'WeOpen\\' =>
array (
0 => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeOpen',
),
'WeMini\\' =>
array (
0 => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini',
1 => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeMini',
),
'WeChat\\' =>
array (
0 => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat',
1 => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeChat',
),
'Psr\\SimpleCache\\' =>
array (
0 => __DIR__ . '/..' . '/psr/simple-cache/src',
@ -94,9 +123,20 @@ class ComposerStaticInit078c2496db47e2e94f2057948fdfa517
array (
0 => __DIR__ . '/..' . '/league/flysystem/src',
),
'AliPay\\' =>
array (
0 => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay',
),
);
public static $classMap = array (
'AliPay\\App' => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay/App.php',
'AliPay\\Bill' => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay/Bill.php',
'AliPay\\Pos' => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay/Pos.php',
'AliPay\\Scan' => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay/Scan.php',
'AliPay\\Transfer' => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay/Transfer.php',
'AliPay\\Wap' => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay/Wap.php',
'AliPay\\Web' => __DIR__ . '/..' . '/zoujingli/wechat-developer/AliPay/Web.php',
'Ip2Region' => __DIR__ . '/..' . '/zoujingli/ip2region/Ip2Region.php',
'League\\Flysystem\\AdapterInterface' => __DIR__ . '/..' . '/league/flysystem/src/AdapterInterface.php',
'League\\Flysystem\\Adapter\\AbstractAdapter' => __DIR__ . '/..' . '/league/flysystem/src/Adapter/AbstractAdapter.php',
@ -186,6 +226,68 @@ class ComposerStaticInit078c2496db47e2e94f2057948fdfa517
'Psr\\SimpleCache\\CacheException' => __DIR__ . '/..' . '/psr/simple-cache/src/CacheException.php',
'Psr\\SimpleCache\\CacheInterface' => __DIR__ . '/..' . '/psr/simple-cache/src/CacheInterface.php',
'Psr\\SimpleCache\\InvalidArgumentException' => __DIR__ . '/..' . '/psr/simple-cache/src/InvalidArgumentException.php',
'We' => __DIR__ . '/..' . '/zoujingli/wechat-developer/We.php',
'WeChat\\Bind' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeChat/Bind.php',
'WeChat\\Card' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Card.php',
'WeChat\\Contracts\\BasicAliPay' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/BasicAliPay.php',
'WeChat\\Contracts\\BasicPushEvent' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/BasicPushEvent.php',
'WeChat\\Contracts\\BasicWeChat' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/BasicWeChat.php',
'WeChat\\Contracts\\BasicWePay' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/BasicWePay.php',
'WeChat\\Contracts\\DataArray' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/DataArray.php',
'WeChat\\Contracts\\DataError' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/DataError.php',
'WeChat\\Contracts\\MyCurlFile' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/MyCurlFile.php',
'WeChat\\Contracts\\Tools' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Contracts/Tools.php',
'WeChat\\Custom' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Custom.php',
'WeChat\\Exceptions\\InvalidArgumentException' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidArgumentException.php',
'WeChat\\Exceptions\\InvalidDecryptException' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidDecryptException.php',
'WeChat\\Exceptions\\InvalidInstanceException' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidInstanceException.php',
'WeChat\\Exceptions\\InvalidResponseException' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Exceptions/InvalidResponseException.php',
'WeChat\\Exceptions\\LocalCacheException' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Exceptions/LocalCacheException.php',
'WeChat\\Limit' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Limit.php',
'WeChat\\Media' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Media.php',
'WeChat\\Menu' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Menu.php',
'WeChat\\Mini' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeChat/Mini.php',
'WeChat\\Oauth' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Oauth.php',
'WeChat\\Pay' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Pay.php',
'WeChat\\Product' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Product.php',
'WeChat\\Qrcode' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Qrcode.php',
'WeChat\\Receive' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Receive.php',
'WeChat\\Scan' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Scan.php',
'WeChat\\Script' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Script.php',
'WeChat\\Shake' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Shake.php',
'WeChat\\Tags' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Tags.php',
'WeChat\\Template' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Template.php',
'WeChat\\User' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/User.php',
'WeChat\\Wifi' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeChat/Wifi.php',
'WeMini\\Account' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeMini/Account.php',
'WeMini\\Basic' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeMini/Basic.php',
'WeMini\\Code' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeMini/Code.php',
'WeMini\\Crypt' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Crypt.php',
'WeMini\\Delivery' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Delivery.php',
'WeMini\\Domain' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeMini/Domain.php',
'WeMini\\Image' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Image.php',
'WeMini\\Logistics' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Logistics.php',
'WeMini\\Message' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Message.php',
'WeMini\\Ocr' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Ocr.php',
'WeMini\\Plugs' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Plugs.php',
'WeMini\\Poi' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Poi.php',
'WeMini\\Qrcode' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Qrcode.php',
'WeMini\\Security' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Security.php',
'WeMini\\Soter' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Soter.php',
'WeMini\\Template' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Template.php',
'WeMini\\Tester' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeMini/Tester.php',
'WeMini\\Total' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WeMini/Total.php',
'WeMini\\User' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeMini/User.php',
'WeOpen\\Login' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeOpen/Login.php',
'WeOpen\\MiniApp' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeOpen/MiniApp.php',
'WeOpen\\Service' => __DIR__ . '/..' . '/zoujingli/weopen-developer/WeOpen/Service.php',
'WePay\\Bill' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay/Bill.php',
'WePay\\Coupon' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay/Coupon.php',
'WePay\\Order' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay/Order.php',
'WePay\\Redpack' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay/Redpack.php',
'WePay\\Refund' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay/Refund.php',
'WePay\\Transfers' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay/Transfers.php',
'WePay\\TransfersBank' => __DIR__ . '/..' . '/zoujingli/wechat-developer/WePay/TransfersBank.php',
'app\\admin\\controller\\Auth' => __DIR__ . '/../..' . '/app/admin/controller/Auth.php',
'app\\admin\\controller\\Config' => __DIR__ . '/../..' . '/app/admin/controller/Config.php',
'app\\admin\\controller\\Index' => __DIR__ . '/../..' . '/app/admin/controller/Index.php',
@ -198,6 +300,16 @@ class ComposerStaticInit078c2496db47e2e94f2057948fdfa517
'app\\admin\\controller\\api\\Update' => __DIR__ . '/../..' . '/app/admin/controller/api/Update.php',
'app\\admin\\controller\\api\\Upload' => __DIR__ . '/../..' . '/app/admin/controller/api/Upload.php',
'app\\index\\controller\\Index' => __DIR__ . '/../..' . '/app/index/controller/Index.php',
'app\\service\\controller\\Config' => __DIR__ . '/../..' . '/app/service/controller/Config.php',
'app\\service\\controller\\Fans' => __DIR__ . '/../..' . '/app/service/controller/Fans.php',
'app\\service\\controller\\Wechat' => __DIR__ . '/../..' . '/app/service/controller/Wechat.php',
'app\\service\\controller\\api\\Client' => __DIR__ . '/../..' . '/app/service/controller/api/Client.php',
'app\\service\\controller\\api\\Push' => __DIR__ . '/../..' . '/app/service/controller/api/Push.php',
'app\\service\\serivce\\ClientService' => __DIR__ . '/../..' . '/app/service/serivce/ClientService.php',
'app\\service\\serivce\\ConfigService' => __DIR__ . '/../..' . '/app/service/serivce/ConfigService.php',
'app\\service\\serivce\\PublishService' => __DIR__ . '/../..' . '/app/service/serivce/PublishService.php',
'app\\service\\serivce\\ReceiveService' => __DIR__ . '/../..' . '/app/service/serivce/ReceiveService.php',
'app\\service\\serivce\\WechatService' => __DIR__ . '/../..' . '/app/service/serivce/WechatService.php',
'think\\App' => __DIR__ . '/..' . '/topthink/framework/src/think/App.php',
'think\\Cache' => __DIR__ . '/..' . '/topthink/framework/src/think/Cache.php',
'think\\Collection' => __DIR__ . '/..' . '/topthink/think-helper/src/Collection.php',

View File

@ -1,17 +1,17 @@
[
{
"name": "league/flysystem",
"version": "1.0.57",
"version_normalized": "1.0.57.0",
"version": "1.0.61",
"version_normalized": "1.0.61.0",
"source": {
"type": "git",
"url": "https://github.com/thephpleague/flysystem.git",
"reference": "0e9db7f0b96b9f12dcf6f65bc34b72b1a30ea55a"
"reference": "4fb13c01784a6c9f165a351e996871488ca2d8c9"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/thephpleague/flysystem/zipball/0e9db7f0b96b9f12dcf6f65bc34b72b1a30ea55a",
"reference": "0e9db7f0b96b9f12dcf6f65bc34b72b1a30ea55a",
"url": "https://api.github.com/repos/thephpleague/flysystem/zipball/4fb13c01784a6c9f165a351e996871488ca2d8c9",
"reference": "4fb13c01784a6c9f165a351e996871488ca2d8c9",
"shasum": "",
"mirrors": [
{
@ -47,7 +47,7 @@
"spatie/flysystem-dropbox": "Allows you to use Dropbox storage",
"srmklive/flysystem-dropbox-v2": "Allows you to use Dropbox storage for PHP 5 applications"
},
"time": "2019-10-16T21:01:05+00:00",
"time": "2019-12-08T21:46:50+00:00",
"type": "library",
"extra": {
"branch-alias": {
@ -856,5 +856,128 @@
],
"description": "ThinkPHP v6.0 Development Library",
"homepage": "http://framework.thinkadmin.top"
},
{
"name": "zoujingli/wechat-developer",
"version": "v1.2.15",
"version_normalized": "1.2.15.0",
"source": {
"type": "git",
"url": "https://github.com/zoujingli/WeChatDeveloper.git",
"reference": "4b81e72cff7a3acfde2cca919bd8e173355bc53c"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/zoujingli/WeChatDeveloper/zipball/4b81e72cff7a3acfde2cca919bd8e173355bc53c",
"reference": "4b81e72cff7a3acfde2cca919bd8e173355bc53c",
"shasum": "",
"mirrors": [
{
"url": "https://mirrors.aliyun.com/composer/dists/%package%/%reference%.%type%",
"preferred": true
}
]
},
"require": {
"ext-curl": "*",
"ext-json": "*",
"ext-libxml": "*",
"ext-mbstring": "*",
"ext-openssl": "*",
"ext-simplexml": "*",
"php": ">=5.4"
},
"time": "2019-11-25T10:40:50+00:00",
"type": "library",
"installation-source": "dist",
"autoload": {
"classmap": [
"We.php"
],
"psr-4": {
"WePay\\": "WePay",
"WeMini\\": "WeMini",
"WeChat\\": "WeChat",
"AliPay\\": "AliPay"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Anyon",
"email": "zoujingli@qq.com",
"homepage": "http://ctolog.com"
}
],
"description": "WeChat platform and WeChat payment development tools",
"homepage": "https://github.com/zoujingli/WeChatDeveloper",
"keywords": [
"WeChatDeveloper",
"WeMini",
"alipay",
"wechat",
"wechatpay",
"wepay"
]
},
{
"name": "zoujingli/weopen-developer",
"version": "dev-master",
"version_normalized": "9999999-dev",
"source": {
"type": "git",
"url": "https://github.com/zoujingli/WeOpenDeveloper.git",
"reference": "4d0d3c064e54556621453845fc65ba52de58a880"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/zoujingli/WeOpenDeveloper/zipball/4d0d3c064e54556621453845fc65ba52de58a880",
"reference": "4d0d3c064e54556621453845fc65ba52de58a880",
"shasum": "",
"mirrors": [
{
"url": "https://mirrors.aliyun.com/composer/dists/%package%/%reference%.%type%",
"preferred": true
}
]
},
"require": {
"ext-curl": "*",
"ext-json": "*",
"ext-openssl": "*",
"php": ">=5.4",
"zoujingli/wechat-developer": "^1.0"
},
"time": "2019-10-10T10:18:05+00:00",
"type": "library",
"installation-source": "dist",
"autoload": {
"psr-4": {
"WeOpen\\": "WeOpen",
"WeChat\\": "WeChat",
"WeMini\\": "WeMini"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Anyon",
"email": "zoujingli@qq.com",
"homepage": "http://ctolog.com"
}
],
"description": "WeChat Open development of SDK",
"homepage": "https://github.com/zoujingli/WeOpenDeveloper",
"keywords": [
"WeChatOpen",
"WeChatOpenDeveloper",
"wechat"
]
}
]

View File

@ -287,6 +287,8 @@ class Local extends AbstractAdapter
$result[] = $this->normalizeFileInfo($file);
}
unset($iterator);
return array_filter($result);
}
@ -412,6 +414,8 @@ class Local extends AbstractAdapter
$this->deleteFileInfoObject($file);
}
unset($contents);
return rmdir($location);
}

View File

@ -365,7 +365,7 @@ class Filesystem implements FilesystemInterface
if ( ! $handler) {
$metadata = $this->getMetadata($path);
$handler = $metadata['type'] === 'file' ? new File($this, $path) : new Directory($this, $path);
$handler = ($metadata && $metadata['type'] === 'file') ? new File($this, $path) : new Directory($this, $path);
}
$handler->setPath($path);

View File

@ -60,7 +60,7 @@ abstract class Handler
{
$metadata = $this->filesystem->getMetadata($this->path);
return $metadata['type'];
return $metadata ? $metadata['type'] : 'dir';
}
/**

View File

@ -291,13 +291,13 @@ class Util
$listedDirectories[] = $object['path'];
}
if (empty($object['dirname'])) {
if ( ! isset($object['dirname']) || trim($object['dirname']) === '') {
return [$directories, $listedDirectories];
}
$parent = $object['dirname'];
while ( ! empty($parent) && ! in_array($parent, $directories)) {
while (isset($parent) && trim($parent) !== '' && ! in_array($parent, $directories)) {
$directories[] = $parent;
$parent = static::dirname($parent);
}

View File

@ -120,7 +120,7 @@ class MimeType
'docm' => 'application/vnd.ms-word.template.macroEnabled.12',
'dotm' => 'application/vnd.ms-word.template.macroEnabled.12',
'dot' => 'application/msword',
'dotx' => 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
'dotx' => 'application/vnd.openxmlformats-officedocument.wordprocessingml.template',
'xlsx' => 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
'xltx' => 'application/vnd.openxmlformats-officedocument.spreadsheetml.template',
'xlsm' => 'application/vnd.ms-excel.sheet.macroEnabled.12',

2
vendor/services.php vendored
View File

@ -1,5 +1,5 @@
<?php
// This file is automatically generated at:2019-12-07 14:48:02
// This file is automatically generated at:2019-12-09 09:56:31
declare (strict_types = 1);
return array (
0 => 'think\\app\\Service',

View File

@ -0,0 +1,9 @@
/.git
/.idea
/.DS_Store
/vendor
/Cache
/Test/cert
/nbproject
/composer.lock
/_test/cert

View File

@ -0,0 +1,48 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace AliPay;
use WeChat\Contracts\BasicAliPay;
/**
* 支付宝App支付网关
* Class App
* @package AliPay
*/
class App extends BasicAliPay
{
/**
* App constructor.
* @param array $options
*/
public function __construct(array $options)
{
parent::__construct($options);
$this->options->set('method', 'alipay.trade.app.pay');
$this->params->set('product_code', 'QUICK_MSECURITY_PAY');
}
/**
* 创建数据操作
* @param array $options
* @return string
*/
public function apply($options)
{
$this->applyData($options);
return http_build_query($this->options->get());
}
}

View File

@ -0,0 +1,47 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace AliPay;
use WeChat\Contracts\BasicAliPay;
/**
* 支付宝电子面单下载
* Class Bill
* @package AliPay
*/
class Bill extends BasicAliPay
{
/**
* Bill constructor.
* @param array $options
*/
public function __construct(array $options)
{
parent::__construct($options);
$this->options->set('method', 'alipay.data.dataservice.bill.downloadurl.query');
}
/**
* 创建数据操作
* @param array $options
* @return mixed
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function apply($options)
{
return $this->getResult($options);
}
}

View File

@ -0,0 +1,48 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace AliPay;
use WeChat\Contracts\BasicAliPay;
/**
* 支付宝刷卡支付
* Class Pos
* @package AliPay
*/
class Pos extends BasicAliPay
{
/**
* Pos constructor.
* @param array $options
*/
public function __construct(array $options)
{
parent::__construct($options);
$this->options->set('method', 'alipay.trade.pay');
$this->params->set('product_code', 'FACE_TO_FACE_PAYMENT');
}
/**
* 创建数据操作
* @param array $options
* @return mixed
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function apply($options)
{
return $this->getResult($options);
}
}

View File

@ -0,0 +1,47 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace AliPay;
use WeChat\Contracts\BasicAliPay;
/**
* 支付宝扫码支付
* Class Scan
* @package AliPay
*/
class Scan extends BasicAliPay
{
/**
* Scan constructor.
* @param array $options
*/
public function __construct(array $options)
{
parent::__construct($options);
$this->options->set('method', 'alipay.trade.precreate');
}
/**
* 创建数据操作
* @param array $options
* @return mixed
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function apply($options)
{
return $this->getResult($options);
}
}

View File

@ -0,0 +1,48 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace AliPay;
use WeChat\Contracts\BasicAliPay;
/**
* 支付宝转账到账户
* Class Transfer
* @package AliPay
*/
class Transfer extends BasicAliPay
{
/**
* Transfer constructor.
* @param array $options
*/
public function __construct(array $options)
{
parent::__construct($options);
$this->options->set('method', 'alipay.fund.trans.toaccount.transfer');
}
/**
* 创建数据操作
* @param array $options
* @return mixed
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function apply($options)
{
return $this->getResult($options);
}
}

View File

@ -0,0 +1,47 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace AliPay;
use WeChat\Contracts\BasicAliPay;
/**
* 手机WAP网站支付支持
* Class Wap
* @package AliPay
*/
class Wap extends BasicAliPay
{
/**
* Wap constructor.
* @param array $options
*/
public function __construct(array $options)
{
parent::__construct($options);
$this->options->set('method', 'alipay.trade.wap.pay');
$this->params->set('product_code', 'QUICK_WAP_WAY');
}
/**
* 创建数据操作
* @param array $options
* @return string
*/
public function apply($options)
{
parent::applyData($options);
return $this->buildPayHtml();
}
}

View File

@ -0,0 +1,47 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace AliPay;
use WeChat\Contracts\BasicAliPay;
/**
* 支付宝网站支付
* Class Web
* @package AliPay
*/
class Web extends BasicAliPay
{
/**
* Web constructor.
* @param array $options
*/
public function __construct(array $options)
{
parent::__construct($options);
$this->options->set('method', 'alipay.trade.page.pay');
$this->params->set('product_code', 'FAST_INSTANT_TRADE_PAY');
}
/**
* 创建数据操作
* @param array $options
* @return string
*/
public function apply($options)
{
parent::applyData($options);
return $this->buildPayHtml();
}
}

View File

@ -0,0 +1,21 @@
The MIT License
Copyright (c) 2014-2018 Anyon<zoujingli@qq.com>
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

134
vendor/zoujingli/wechat-developer/We.php vendored Normal file
View File

@ -0,0 +1,134 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
use WeChat\Contracts\DataArray;
use WeChat\Exceptions\InvalidInstanceException;
/**
* 加载缓存器
*
* Class We
* @library WeChatDeveloper
* @author Anyon<zoujingli@qq.com>
* @date 2018/05/24 13:23
*
* ----- WeChat -----
* @method \WeChat\Card WeChatCard($options = []) static 微信卡券管理
* @method \WeChat\Custom WeChatCustom($options = []) static 微信客服消息
* @method \WeChat\Limit WeChatLimit($options = []) static 接口调用频次限制
* @method \WeChat\Media WeChatMedia($options = []) static 微信素材管理
* @method \WeChat\Menu WeChatMenu($options = []) static 微信菜单管理
* @method \WeChat\Oauth WeChatOauth($options = []) static 微信网页授权
* @method \WeChat\Pay WeChatPay($options = []) static 微信支付商户
* @method \WeChat\Product WeChatProduct($options = []) static 微信商店管理
* @method \WeChat\Qrcode WeChatQrcode($options = []) static 微信二维码管理
* @method \WeChat\Receive WeChatReceive($options = []) static 微信推送管理
* @method \WeChat\Scan WeChatScan($options = []) static 微信扫一扫接入管理
* @method \WeChat\Script WeChatScript($options = []) static 微信前端支持
* @method \WeChat\Shake WeChatShake($options = []) static 微信揺一揺周边
* @method \WeChat\Tags WeChatTags($options = []) static 微信用户标签管理
* @method \WeChat\Template WeChatTemplate($options = []) static 微信模板消息
* @method \WeChat\User WeChatUser($options = []) static 微信粉丝管理
* @method \WeChat\Wifi WeChatWifi($options = []) static 微信门店WIFI管理
*
* ----- WeMini -----
* @method \WeMini\Crypt WeMiniCrypt($options = []) static 小程序数据加密处理
* @method \WeMini\Delivery WeMiniDelivery($options = []) static 小程序即时配送
* @method \WeMini\Image WeMiniImage($options = []) static 小程序图像处理
* @method \WeMini\Logistics WeMiniLogistics($options = []) static 小程序物流助手
* @method \WeMini\Message WeMiniMessage($options = []) static 小程序动态消息
* @method \WeMini\Ocr WeMiniOcr($options = []) static 小程序ORC服务
* @method \WeMini\Plugs WeMiniPlugs($options = []) static 小程序插件管理
* @method \WeMini\Poi WeMiniPoi($options = []) static 小程序地址管理
* @method \WeMini\Qrcode WeMiniQrcode($options = []) static 小程序二维码管理
* @method \WeMini\Security WeMiniSecurity($options = []) static 小程序内容安全
* @method \WeMini\Soter WeMiniSoter($options = []) static 小程序生物认证
* @method \WeMini\Template WeMiniTemplate($options = []) static 小程序模板消息支持
* @method \WeMini\Total WeMiniTotal($options = []) static 小程序数据接口
*
* ----- WePay -----
* @method \WePay\Bill WePayBill($options = []) static 微信商户账单及评论
* @method \WePay\Order WePayOrder($options = []) static 微信商户订单
* @method \WePay\Refund WePayRefund($options = []) static 微信商户退款
* @method \WePay\Coupon WePayCoupon($options = []) static 微信商户代金券
* @method \WePay\Redpack WePayRedpack($options = []) static 微信红包支持
* @method \WePay\Transfers WePayTransfers($options = []) static 微信商户打款到零钱
* @method \WePay\TransfersBank WePayTransfersBank($options = []) static 微信商户打款到银行卡
*
* ----- AliPay ----
* @method \AliPay\App AliPayApp($options) static 支付宝App支付网关
* @method \AliPay\Bill AliPayBill($options) static 支付宝电子面单下载
* @method \AliPay\Pos AliPayPos($options) static 支付宝刷卡支付
* @method \AliPay\Scan AliPayScan($options) static 支付宝扫码支付
* @method \AliPay\Transfer AliPayTransfer($options) static 支付宝转账到账户
* @method \AliPay\Wap AliPayWap($options) static 支付宝手机网站支付
* @method \AliPay\Web AliPayWeb($options) static 支付宝网站支付
*/
class We
{
/**
* 定义当前版本
* @var string
*/
const VERSION = '1.2.13';
/**
* 静态配置
* @var DataArray
*/
private static $config;
/**
* 设置及获取参数
* @param array $option
* @return array
*/
public static function config($option = null)
{
if (is_array($option)) {
self::$config = new DataArray($option);
}
if (self::$config instanceof DataArray) {
return self::$config->get();
}
return [];
}
/**
* 静态魔术加载方法
* @param string $name 静态类名
* @param array $arguments 参数集合
* @return mixed
* @throws InvalidInstanceException
*/
public static function __callStatic($name, $arguments)
{
if (substr($name, 0, 6) === 'WeChat') {
$class = 'WeChat\\' . substr($name, 6);
} elseif (substr($name, 0, 6) === 'WeMini') {
$class = 'WeMini\\' . substr($name, 6);
} elseif (substr($name, 0, 6) === 'AliPay') {
$class = 'AliPay\\' . substr($name, 6);
} elseif (substr($name, 0, 5) === 'WePay') {
$class = 'WePay\\' . substr($name, 5);
}
if (!empty($class) && class_exists($class)) {
$option = array_shift($arguments);
$config = is_array($option) ? $option : self::$config->get();
return new $class($config);
}
throw new InvalidInstanceException("class {$name} not found");
}
}

View File

@ -0,0 +1,672 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 卡券管理
* Class Card
* @package WeChat
*/
class Card extends BasicWeChat
{
/**
* 创建卡券
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function create(array $data)
{
$url = "https://api.weixin.qq.com/card/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 设置买单接口
* @param string $card_id
* @param bool $is_open
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setPaycell($card_id, $is_open = true)
{
$url = "https://api.weixin.qq.com/card/paycell/set?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id, 'is_open' => $is_open]);
}
/**
* 设置自助核销接口
* @param string $card_id
* @param bool $is_open
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setConsumeCell($card_id, $is_open = true)
{
$url = "https://api.weixin.qq.com/card/selfconsumecell/set?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id, 'is_open' => $is_open]);
}
/**
* 创建二维码接口
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function createQrc(array $data)
{
$url = "https://api.weixin.qq.com/card/qrcode/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 创建货架接口
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function createLandingPage(array $data)
{
$url = "https://api.weixin.qq.com/card/landingpage/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 导入自定义code
* @param string $card_id
* @param array $code
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function deposit($card_id, array $code)
{
$url = "https://api.weixin.qq.com/card/code/deposit?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id, 'code' => $code]);
}
/**
* 查询导入code数目
* @param string $card_id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getDepositCount($card_id)
{
$url = "https://api.weixin.qq.com/card/code/getdepositcount?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id]);
}
/**
* 核查code接口
* @param string $card_id 进行导入code的卡券ID
* @param array $code 已经微信卡券后台的自定义code上限为100个
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function checkCode($card_id, array $code)
{
$url = "https://api.weixin.qq.com/card/code/checkcode?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id, 'code' => $code]);
}
/**
* 图文消息群发卡券
* @param string $card_id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getNewsHtml($card_id)
{
$url = "https://api.weixin.qq.com/card/mpnews/gethtml?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id]);
}
/**
* 设置测试白名单
* @param array $openids
* @param array $usernames
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setTestWhiteList($openids = [], $usernames = [])
{
$url = "https://api.weixin.qq.com/card/testwhitelist/set?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['openid' => $openids, 'username' => $usernames]);
}
/**
* 线下核销查询Code
* @param string $code 单张卡券的唯一标准
* @param string $card_id 卡券ID代表一类卡券。自定义code卡券必填
* @param bool $check_consume 是否校验code核销状态填入true和false时的code异常状态返回数据不同
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCode($code, $card_id = null, $check_consume = null)
{
$data = ['code' => $code];
is_null($card_id) || $data['card_id'] = $card_id;
is_null($check_consume) || $data['check_consume'] = $check_consume;
$url = "https://api.weixin.qq.com/card/code/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 线下核销核销Code
* @param string $code 需核销的Code码
* @param null $card_id 券ID。创建卡券时use_custom_code填写true时必填。非自定义Code不必填写
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function consume($code, $card_id = null)
{
$data = ['code' => $code];
is_null($card_id) || $data['card_id'] = $card_id;
$url = "https://api.weixin.qq.com/card/code/consume?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* Code解码接口
* @param string $encrypt_code
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function decrypt($encrypt_code)
{
$url = "https://api.weixin.qq.com/card/code/decrypt?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['encrypt_code' => $encrypt_code]);
}
/**
* 获取用户已领取卡券接口
* @param string $openid
* @param null|string $card_id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCardList($openid, $card_id = null)
{
$data = ['openid' => $openid];
is_null($card_id) || $data['card_id'] = $card_id;
$url = "https://api.weixin.qq.com/card/user/getcardlist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查看卡券详情
* @param string $card_id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCard($card_id)
{
$url = "https://api.weixin.qq.com/card/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id]);
}
/**
* 批量查询卡券列表
* @param int $offset 查询卡列表的起始偏移量从0开始即offset: 5是指从从列表里的第六个开始读取
* @param int $count 需要查询的卡片的数量数量最大50
* @param array $status_list 支持开发者拉出指定状态的卡券列表
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function batchGet($offset, $count = 50, array $status_list = [])
{
$data = ['offset' => $offset, 'count' => $count];
empty($status_list) || $data['status_list'] = $status_list;
$url = "https://api.weixin.qq.com/card/batchget?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 更改卡券信息接口
* @param string $card_id
* @param array $member_card
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateCard($card_id, array $member_card)
{
$url = "https://api.weixin.qq.com/card/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id, 'member_card' => $member_card]);
}
/**
* 修改库存接口
* @param string $card_id 卡券ID
* @param null|integer $increase_stock_value 增加多少库存支持不填或填0
* @param null|integer $reduce_stock_value 减少多少库存可以不填或填0
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function modifyStock($card_id, $increase_stock_value = null, $reduce_stock_value = null)
{
$data = ['card_id' => $card_id];
is_null($increase_stock_value) || $data['increase_stock_value'] = $increase_stock_value;
is_null($reduce_stock_value) || $data['reduce_stock_value'] = $reduce_stock_value;
$url = "https://api.weixin.qq.com/card/modifystock?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 更改Code接口
* @param string $code 需变更的Code码
* @param string $new_code 变更后的有效Code码
* @param null|string $card_id 卡券ID
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateCode($code, $new_code, $card_id = null)
{
$data = ['code' => $code, 'new_code' => $new_code];
is_null($card_id) || $data['card_id'] = $card_id;
$url = "https://api.weixin.qq.com/card/code/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 删除卡券接口
* @param string $card_id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function deleteCard($card_id)
{
$url = "https://api.weixin.qq.com/card/delete?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id]);
}
/**
* 设置卡券失效接口
* @param string $code
* @param string $card_id
* @param null|string $reason
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function unAvailable($code, $card_id, $reason = null)
{
$data = ['code' => $code, 'card_id' => $card_id];
is_null($reason) || $data['reason'] = $reason;
$url = "https://api.weixin.qq.com/card/code/unavailable?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 拉取卡券概况数据接口
* @param string $begin_date 查询数据的起始时间
* @param string $end_date 查询数据的截至时间
* @param string $cond_source 卡券来源(0为公众平台创建的卡券数据 1是API创建的卡券数据)
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCardBizuininfo($begin_date, $end_date, $cond_source)
{
$data = ['begin_date' => $begin_date, 'end_date' => $end_date, 'cond_source' => $cond_source];
$url = "https://api.weixin.qq.com/datacube/getcardbizuininfo?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 获取免费券数据接口
* @param string $begin_date 查询数据的起始时间
* @param string $end_date 查询数据的截至时间
* @param integer $cond_source 卡券来源0为公众平台创建的卡券数据、1是API创建的卡券数据
* @param null $card_id 卡券ID
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCardCardinfo($begin_date, $end_date, $cond_source, $card_id = null)
{
$data = ['begin_date' => $begin_date, 'end_date' => $end_date, 'cond_source' => $cond_source];
is_null($card_id) || $data['card_id'] = $card_id;
$url = "https://api.weixin.qq.com/datacube/getcardcardinfo?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 激活会员卡
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function activateMemberCard(array $data)
{
$url = 'https://api.weixin.qq.com/card/membercard/activate?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 设置开卡字段接口
* 用户激活时需要填写的选项
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setActivateMemberCardUser(array $data)
{
$url = 'https://api.weixin.qq.com/card/membercard/activateuserform/set?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 获取用户提交资料
* 根据activate_ticket获取到用户填写的信息
* @param string $activate_ticket
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getActivateMemberCardTempinfo($activate_ticket)
{
$url = 'https://api.weixin.qq.com/card/membercard/activatetempinfo/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['activate_ticket' => $activate_ticket]);
}
/**
* 更新会员信息
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateMemberCardUser(array $data)
{
$url = 'https://api.weixin.qq.com/card/membercard/updateuser?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 拉取会员卡概况数据接口
* @param string $begin_date 查询数据的起始时间
* @param string $end_date 查询数据的截至时间
* @param string $cond_source 卡券来源(0为公众平台创建的卡券数据 1是API创建的卡券数据)
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCardMemberCardinfo($begin_date, $end_date, $cond_source)
{
$data = ['begin_date' => $begin_date, 'end_date' => $end_date, 'cond_source' => $cond_source];
$url = "https://api.weixin.qq.com/datacube/getcardmembercardinfo?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 拉取单张会员卡数据接口
* @param string $begin_date 查询数据的起始时间
* @param string $end_date 查询数据的截至时间
* @param string $card_id 卡券id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCardMemberCardDetail($begin_date, $end_date, $card_id)
{
$data = ['begin_date' => $begin_date, 'end_date' => $end_date, 'card_id' => $card_id];
$url = "https://api.weixin.qq.com/datacube/getcardmembercarddetail?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 拉取会员信息(积分查询)接口
* @param string $card_id 查询会员卡的cardid
* @param string $code 所查询用户领取到的code值
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCardMemberCard($card_id, $code)
{
$data = ['card_id' => $card_id, 'code' => $code];
$url = "https://api.weixin.qq.com/card/membercard/userinfo/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 设置支付后投放卡券接口
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function payGiftCard(array $data)
{
$url = "https://api.weixin.qq.com/card/paygiftcard/add?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 删除支付后投放卡券规则
* @param integer $rule_id 支付即会员的规则名称
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function delPayGiftCard($rule_id)
{
$url = "https://api.weixin.qq.com/card/paygiftcard/add?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['rule_id' => $rule_id]);
}
/**
* 查询支付后投放卡券规则详情
* @param integer $rule_id 要查询规则id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getPayGiftCard($rule_id)
{
$url = "https://api.weixin.qq.com/card/paygiftcard/getbyid?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['rule_id' => $rule_id]);
}
/**
* 批量查询支付后投放卡券规则
* @param integer $offset 起始偏移量
* @param integer $count 查询的数量
* @param bool $effective 是否仅查询生效的规则
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function batchGetPayGiftCard($offset = 0, $count = 10, $effective = true)
{
$data = ['type' => 'RULE_TYPE_PAY_MEMBER_CARD', 'offset' => $offset, 'count' => $count, 'effective' => $effective];
$url = "https://api.weixin.qq.com/card/paygiftcard/batchget?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 创建支付后领取立减金活动
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addActivity(array $data)
{
$url = "https://api.weixin.qq.com/card/mkt/activity/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 开通券点账户接口
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function payActivate()
{
$url = "https://api.weixin.qq.com/card/pay/activate?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 对优惠券批价
* @param string $card_id 需要来配置库存的card_id
* @param integer $quantity 本次需要兑换的库存数目
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getPayprice($card_id, $quantity)
{
$url = "POST https://api.weixin.qq.com/card/pay/getpayprice?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['card_id' => $card_id, 'quantity' => $quantity]);
}
/**
* 查询券点余额接口
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCoinsInfo()
{
$url = "https://api.weixin.qq.com/card/pay/getcoinsinfo?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 确认兑换库存接口
* @param string $card_id 需要来兑换库存的card_id
* @param integer $quantity 本次需要兑换的库存数目
* @param string $order_id 仅可以使用上面得到的订单号,保证批价有效性
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function payConfirm($card_id, $quantity, $order_id)
{
$data = ['card_id' => $card_id, 'quantity' => $quantity, 'order_id' => $order_id];
$url = "https://api.weixin.qq.com/card/pay/confirm?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 充值券点接口
* @param integer $coin_count
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function payRecharge($coin_count)
{
$url = "https://api.weixin.qq.com/card/pay/recharge?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['coin_count' => $coin_count]);
}
/**
* 查询订单详情接口
* @param string $order_id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function payGetOrder($order_id)
{
$url = "https://api.weixin.qq.com/card/pay/getorder?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['order_id' => $order_id]);
}
/**
* 查询券点流水详情接口
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function payGetList(array $data)
{
$url = "https://api.weixin.qq.com/card/pay/getorderlist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
}

View File

@ -0,0 +1,286 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Contracts;
use WeChat\Exceptions\InvalidArgumentException;
use WeChat\Exceptions\InvalidResponseException;
/**
* 支付宝支付基类
* Class AliPay
* @package AliPay\Contracts
*/
abstract class BasicAliPay
{
/**
* 支持配置
* @var DataArray
*/
protected $config;
/**
* 当前请求数据
* @var DataArray
*/
protected $options;
/**
* DzContent数据
* @var DataArray
*/
protected $params;
/**
* 静态缓存
* @var static
*/
protected static $cache;
/**
* 正常请求网关
* @var string
*/
protected $gateway = 'https://openapi.alipay.com/gateway.do?charset=utf-8';
/**
* AliPay constructor.
* @param array $options
*/
public function __construct($options)
{
$this->params = new DataArray([]);
$this->config = new DataArray($options);
if (empty($options['appid'])) {
throw new InvalidArgumentException("Missing Config -- [appid]");
}
if (empty($options['public_key'])) {
throw new InvalidArgumentException("Missing Config -- [public_key]");
}
if (empty($options['private_key'])) {
throw new InvalidArgumentException("Missing Config -- [private_key]");
}
if (!empty($options['debug'])) {
$this->gateway = 'https://openapi.alipaydev.com/gateway.do?charset=utf-8';
}
$this->options = new DataArray([
'app_id' => $this->config->get('appid'),
'charset' => empty($options['charset']) ? 'utf-8' : $options['charset'],
'format' => 'JSON',
'version' => '1.0',
'sign_type' => empty($options['sign_type']) ? 'RSA2' : $options['sign_type'],
'timestamp' => date('Y-m-d H:i:s'),
]);
if (isset($options['notify_url']) && $options['notify_url'] !== '') {
$this->options->set('notify_url', $options['notify_url']);
}
if (isset($options['return_url']) && $options['return_url'] !== '') {
$this->options->set('return_url', $options['return_url']);
}
if (isset($options['app_auth_token']) && $options['app_auth_token'] !== '') {
$this->options->set('app_auth_token', $options['app_auth_token']);
}
}
/**
* 静态创建对象
* @param array $config
* @return static
*/
public static function instance(array $config)
{
$key = md5(get_called_class() . serialize($config));
if (isset(self::$cache[$key])) return self::$cache[$key];
return self::$cache[$key] = new static($config);
}
/**
* 查询支付宝订单状态
* @param string $out_trade_no
* @return array|boolean
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function query($out_trade_no = '')
{
$this->options->set('method', 'alipay.trade.query');
return $this->getResult(['out_trade_no' => $out_trade_no]);
}
/**
* 支付宝订单退款操作
* @param array|string $options 退款参数或退款商户订单号
* @param null $refund_amount 退款金额
* @return array|boolean
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function refund($options, $refund_amount = null)
{
if (!is_array($options)) $options = ['out_trade_no' => $options, 'refund_amount' => $refund_amount];
$this->options->set('method', 'alipay.trade.refund');
return $this->getResult($options);
}
/**
* 关闭支付宝进行中的订单
* @param array|string $options
* @return array|boolean
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function close($options)
{
if (!is_array($options)) $options = ['out_trade_no' => $options];
$this->options->set('method', 'alipay.trade.close');
return $this->getResult($options);
}
/**
* 获取通知数据
* @param boolean $needSignType 是否需要sign_type字段
* @return boolean|array
* @throws InvalidResponseException
*/
public function notify($needSignType = false)
{
$data = $_POST;
if (empty($data) || empty($data['sign'])) {
throw new InvalidResponseException('Illegal push request.', 0, $data);
}
$string = $this->getSignContent($data, $needSignType);
$content = wordwrap($this->config->get('public_key'), 64, "\n", true);
$res = "-----BEGIN PUBLIC KEY-----\n{$content}\n-----END PUBLIC KEY-----";
if (openssl_verify($string, base64_decode($data['sign']), $res, OPENSSL_ALGO_SHA256) !== 1) {
throw new InvalidResponseException('Data signature verification failed.', 0, $data);
}
return $data;
}
/**
* 验证接口返回的数据签名
* @param array $data 通知数据
* @param null|string $sign 数据签名
* @return array|boolean
* @throws InvalidResponseException
*/
protected function verify($data, $sign)
{
$content = wordwrap($this->config->get('public_key'), 64, "\n", true);
$res = "-----BEGIN PUBLIC KEY-----\n{$content}\n-----END PUBLIC KEY-----";
if ($this->options->get('sign_type') === 'RSA2') {
if (openssl_verify(json_encode($data, 256), base64_decode($sign), $res, OPENSSL_ALGO_SHA256) !== 1) {
throw new InvalidResponseException('Data signature verification failed.');
}
} else {
if (openssl_verify(json_encode($data, 256), base64_decode($sign), $res, OPENSSL_ALGO_SHA1) !== 1) {
throw new InvalidResponseException('Data signature verification failed.');
}
}
return $data;
}
/**
* 获取数据签名
* @return string
*/
protected function getSign()
{
$content = wordwrap($this->config->get('private_key'), 64, "\n", true);
$string = "-----BEGIN RSA PRIVATE KEY-----\n{$content}\n-----END RSA PRIVATE KEY-----";
if ($this->options->get('sign_type') === 'RSA2') {
openssl_sign($this->getSignContent($this->options->get(), true), $sign, $string, OPENSSL_ALGO_SHA256);
} else {
openssl_sign($this->getSignContent($this->options->get(), true), $sign, $string, OPENSSL_ALGO_SHA1);
}
return base64_encode($sign);
}
/**
* 数据签名处理
* @param array $data 需要进行签名数据
* @param boolean $needSignType 是否需要sign_type字段
* @return bool|string
*/
private function getSignContent(array $data, $needSignType = false)
{
list($attrs,) = [[], ksort($data)];
if (isset($data['sign'])) unset($data['sign']);
if (empty($needSignType)) unset($data['sign_type']);
foreach ($data as $key => $value) {
if ($value === '' || is_null($value)) continue;
array_push($attrs, "{$key}={$value}");
}
return join('&', $attrs);
}
/**
* 数据包生成及数据签名
* @param array $options
*/
protected function applyData($options)
{
$this->options->set('biz_content', json_encode($this->params->merge($options), 256));
$this->options->set('sign', $this->getSign());
}
/**
* 请求接口并验证访问数据
* @param array $options
* @return array|boolean
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
protected function getResult($options)
{
$this->applyData($options);
$method = str_replace('.', '_', $this->options['method']) . '_response';
$data = json_decode(Tools::get($this->gateway, $this->options->get()), true);
if (!isset($data[$method]['code']) || $data[$method]['code'] !== '10000') {
throw new InvalidResponseException(
"Error: " .
(empty($data[$method]['code']) ? '' : "{$data[$method]['msg']} [{$data[$method]['code']}]\r\n") .
(empty($data[$method]['sub_code']) ? '' : "{$data[$method]['sub_msg']} [{$data[$method]['sub_code']}]\r\n"),
$data[$method]['code'], $data
);
}
return $data[$method];
// 去除返回结果签名检查
// return $this->verify($data[$method], $data['sign']);
}
/**
* 生成支付HTML代码
* @return string
*/
protected function buildPayHtml()
{
$html = "<form id='alipaysubmit' name='alipaysubmit' action='{$this->gateway}' method='post'>";
foreach ($this->options->get() as $key => $value) {
$value = str_replace("'", '&apos;', $value);
$html .= "<input type='hidden' name='{$key}' value='{$value}'/>";
}
$html .= "<input type='submit' value='ok' style='display:none;'></form>";
return "{$html}<script>document.forms['alipaysubmit'].submit();</script>";
}
/**
* 应用数据操作
* @param array $options
* @return mixed
*/
abstract public function apply($options);
}

View File

@ -0,0 +1,231 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Contracts;
use WeChat\Exceptions\InvalidArgumentException;
use WeChat\Exceptions\InvalidDecryptException;
use WeChat\Exceptions\InvalidResponseException;
/**
* 微信通知处理基本类
* Class BasicPushEvent
* @package WeChat\Contracts
*/
class BasicPushEvent
{
/**
* 公众号APPID
* @var string
*/
protected $appid;
/**
* 公众号推送XML内容
* @var string
*/
protected $postxml;
/**
* 公众号推送加密类型
* @var string
*/
protected $encryptType;
/**
* 公众号的推送请求参数
* @var DataArray
*/
protected $input;
/**
* 当前公众号配置对象
* @var DataArray
*/
protected $config;
/**
* 公众号推送内容对象
* @var DataArray
*/
protected $receive;
/**
* 准备回复的消息内容
* @var array
*/
protected $message;
/**
* BasicPushEvent constructor.
* @param array $options
* @throws InvalidResponseException
*/
public function __construct(array $options)
{
if (empty($options['appid'])) {
throw new InvalidArgumentException("Missing Config -- [appid]");
}
if (empty($options['appsecret'])) {
throw new InvalidArgumentException("Missing Config -- [appsecret]");
}
if (empty($options['token'])) {
throw new InvalidArgumentException("Missing Config -- [token]");
}
// 参数初始化
$this->config = new DataArray($options);
$this->input = new DataArray($_REQUEST);
$this->appid = $this->config->get('appid');
// 推送消息处理
if ($_SERVER['REQUEST_METHOD'] == "POST") {
$this->postxml = file_get_contents("php://input");
$this->encryptType = $this->input->get('encrypt_type');
if ($this->isEncrypt()) {
if (empty($options['encodingaeskey'])) {
throw new InvalidArgumentException("Missing Config -- [encodingaeskey]");
}
if (!class_exists('Prpcrypt', false)) {
require __DIR__ . '/Prpcrypt.php';
}
$prpcrypt = new \Prpcrypt($this->config->get('encodingaeskey'));
$result = Tools::xml2arr($this->postxml);
$array = $prpcrypt->decrypt($result['Encrypt']);
if (intval($array[0]) > 0) {
throw new InvalidResponseException($array[1], $array[0]);
}
list($this->postxml, $this->appid) = [$array[1], $array[2]];
}
$this->receive = new DataArray(Tools::xml2arr($this->postxml));
} elseif ($_SERVER['REQUEST_METHOD'] == "GET" && $this->checkSignature()) {
@ob_clean();
exit($this->input->get('echostr'));
} else {
throw new InvalidResponseException('Invalid interface request.', '0');
}
}
/**
* 消息是否需要加密
* @return boolean
*/
public function isEncrypt()
{
return $this->encryptType === 'aes';
}
/**
* 回复消息
* @param array $data 消息内容
* @param boolean $return 是否返回XML内容
* @param boolean $isEncrypt 是否加密内容
* @return string
* @throws InvalidDecryptException
*/
public function reply(array $data = [], $return = false, $isEncrypt = false)
{
$xml = Tools::arr2xml(empty($data) ? $this->message : $data);
if ($this->isEncrypt() || $isEncrypt) {
if (!class_exists('Prpcrypt', false)) {
require __DIR__ . '/Prpcrypt.php';
}
$prpcrypt = new \Prpcrypt($this->config->get('encodingaeskey'));
// 如果是第三方平台,加密得使用 component_appid
$component_appid = $this->config->get('component_appid');
$appid = empty($component_appid) ? $this->appid : $component_appid;
$array = $prpcrypt->encrypt($xml, $appid);
if ($array[0] > 0) throw new InvalidDecryptException('Encrypt Error.', '0');
list($timestamp, $encrypt) = [time(), $array[1]];
$nonce = rand(77, 999) * rand(605, 888) * rand(11, 99);
$tmpArr = [$this->config->get('token'), $timestamp, $nonce, $encrypt];
sort($tmpArr, SORT_STRING);
$signature = sha1(implode($tmpArr));
$format = "<xml><Encrypt><![CDATA[%s]]></Encrypt><MsgSignature><![CDATA[%s]]></MsgSignature><TimeStamp>%s</TimeStamp><Nonce><![CDATA[%s]]></Nonce></xml>";
$xml = sprintf($format, $encrypt, $signature, $timestamp, $nonce);
}
if ($return) return $xml;
@ob_clean();
echo $xml;
}
/**
* 验证来自微信服务器
* @param string $str
* @return bool
*/
private function checkSignature($str = '')
{
$nonce = $this->input->get('nonce');
$timestamp = $this->input->get('timestamp');
$msg_signature = $this->input->get('msg_signature');
$signature = empty($msg_signature) ? $this->input->get('signature') : $msg_signature;
$tmpArr = [$this->config->get('token'), $timestamp, $nonce, $str];
sort($tmpArr, SORT_STRING);
return sha1(implode($tmpArr)) === $signature;
}
/**
* 获取公众号推送对象
* @param null|string $field 指定获取字段
* @return array
*/
public function getReceive($field = null)
{
return $this->receive->get($field);
}
/**
* 获取当前微信OPENID
* @return string
*/
public function getOpenid()
{
return $this->receive->get('FromUserName');
}
/**
* 获取当前推送消息类型
* @return string
*/
public function getMsgType()
{
return $this->receive->get('MsgType');
}
/**
* 获取当前推送消息ID
* @return string
*/
public function getMsgId()
{
return $this->receive->get('MsgId');
}
/**
* 获取当前推送时间
* @return integer
*/
public function getMsgTime()
{
return $this->receive->get('CreateTime');
}
/**
* 获取当前推送公众号
* @return string
*/
public function getToOpenid()
{
return $this->receive->get('ToUserName');
}
}

View File

@ -0,0 +1,249 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Contracts;
use WeChat\Exceptions\InvalidArgumentException;
use WeChat\Exceptions\InvalidResponseException;
/**
* Class BasicWeChat
* @package WeChat\Contracts
*/
class BasicWeChat
{
/**
* 当前微信配置
* @var DataArray
*/
public $config;
/**
* 访问AccessToken
* @var string
*/
public $access_token = '';
/**
* 当前请求方法参数
* @var array
*/
protected $currentMethod = [];
/**
* 当前模式
* @var bool
*/
protected $isTry = false;
/**
* 静态缓存
* @var static
*/
protected static $cache;
/**
* 注册代替函数
* @var string
*/
protected $GetAccessTokenCallback;
/**
* BasicWeChat constructor.
* @param array $options
*/
public function __construct(array $options)
{
if (empty($options['appid'])) {
throw new InvalidArgumentException("Missing Config -- [appid]");
}
if (empty($options['appsecret'])) {
throw new InvalidArgumentException("Missing Config -- [appsecret]");
}
if (isset($options['GetAccessTokenCallback']) && is_callable($options['GetAccessTokenCallback'])) {
$this->GetAccessTokenCallback = $options['GetAccessTokenCallback'];
}
if (!empty($options['cache_path'])) {
Tools::$cache_path = $options['cache_path'];
}
$this->config = new DataArray($options);
}
/**
* 静态创建对象
* @param array $config
* @return static
*/
public static function instance(array $config)
{
$key = md5(get_called_class() . serialize($config));
if (isset(self::$cache[$key])) return self::$cache[$key];
return self::$cache[$key] = new static($config);
}
/**
* 获取访问accessToken
* @return string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getAccessToken()
{
if (!empty($this->access_token)) {
return $this->access_token;
}
$cache = $this->config->get('appid') . '_access_token';
$this->access_token = Tools::getCache($cache);
if (!empty($this->access_token)) {
return $this->access_token;
}
// 处理开放平台授权公众号获取AccessToken
if (!empty($this->GetAccessTokenCallback) && is_callable($this->GetAccessTokenCallback)) {
$this->access_token = call_user_func_array($this->GetAccessTokenCallback, [$this->config->get('appid'), $this]);
if (!empty($this->access_token)) {
Tools::setCache($cache, $this->access_token, 7000);
}
return $this->access_token;
}
list($appid, $secret) = [$this->config->get('appid'), $this->config->get('appsecret')];
$url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid={$appid}&secret={$secret}";
$result = Tools::json2arr(Tools::get($url));
if (!empty($result['access_token'])) {
Tools::setCache($cache, $result['access_token'], 7000);
}
return $this->access_token = $result['access_token'];
}
/**
* 设置外部接口 AccessToken
* @param string $access_token
* @throws \WeChat\Exceptions\LocalCacheException
* @author 高一平 <iam@gaoyiping.com>
*
* 当用户使用自己的缓存驱动时,直接实例化对象后可直接设置 AccessToekn
* - 多用于分布式项目时保持 AccessToken 统一
* - 使用此方法后就由用户来保证传入的 AccessToekn 为有效 AccessToekn
*/
public function setAccessToken($access_token)
{
if (!is_string($access_token)) {
throw new InvalidArgumentException("Invalid AccessToken type, need string.");
}
$cache = $this->config->get('appid') . '_access_token';
Tools::setCache($cache, $this->access_token = $access_token);
}
/**
* 清理删除 AccessToken
* @return bool
*/
public function delAccessToken()
{
$this->access_token = '';
return Tools::delCache($this->config->get('appid') . '_access_token');
}
/**
* 以GET获取接口数据并转为数组
* @param string $url 接口地址
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
protected function httpGetForJson($url)
{
try {
return Tools::json2arr(Tools::get($url));
} catch (InvalidResponseException $e) {
if (isset($this->currentMethod['method']) && empty($this->isTry)) {
if (in_array($e->getCode(), ['40014', '40001', '41001', '42001'])) {
$this->delAccessToken();
$this->isTry = true;
return call_user_func_array([$this, $this->currentMethod['method']], $this->currentMethod['arguments']);
}
}
throw new InvalidResponseException($e->getMessage(), $e->getCode());
}
}
/**
* 以POST获取接口数据并转为数组
* @param string $url 接口地址
* @param array $data 请求数据
* @param bool $buildToJson
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
protected function httpPostForJson($url, array $data, $buildToJson = true)
{
try {
return Tools::json2arr(Tools::post($url, $buildToJson ? Tools::arr2json($data) : $data));
} catch (InvalidResponseException $e) {
if (!$this->isTry && in_array($e->getCode(), ['40014', '40001', '41001', '42001'])) {
[$this->delAccessToken(), $this->isTry = true];
return call_user_func_array([$this, $this->currentMethod['method']], $this->currentMethod['arguments']);
}
throw new InvalidResponseException($e->getMessage(), $e->getCode());
}
}
/**
* 注册当前请求接口
* @param string $url 接口地址
* @param string $method 当前接口方法
* @param array $arguments 请求参数
* @return mixed
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
protected function registerApi(&$url, $method, $arguments = [])
{
$this->currentMethod = ['method' => $method, 'arguments' => $arguments];
if (empty($this->access_token)) {
$this->access_token = $this->getAccessToken();
}
return $url = str_replace('ACCESS_TOKEN', $this->access_token, $url);
}
/**
* 接口通用POST请求方法
* @param string $url 接口URL
* @param array $data POST提交接口参数
* @param bool $isBuildJson
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function callPostApi($url, array $data, $isBuildJson = true)
{
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data, $isBuildJson);
}
/**
* 接口通用GET请求方法
* @param string $url 接口URL
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function callGetApi($url)
{
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
}

View File

@ -0,0 +1,203 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Contracts;
use WeChat\Exceptions\InvalidArgumentException;
use WeChat\Exceptions\InvalidResponseException;
/**
* 微信支付基础类
* Class BasicPay
* @package WeChat\Contracts
*/
class BasicWePay
{
/**
* 商户配置
* @var DataArray
*/
protected $config;
/**
* 当前请求数据
* @var DataArray
*/
protected $params;
/**
* 静态缓存
* @var static
*/
protected static $cache;
/**
* WeChat constructor.
* @param array $options
*/
public function __construct(array $options)
{
if (empty($options['appid'])) {
throw new InvalidArgumentException("Missing Config -- [appid]");
}
if (empty($options['mch_id'])) {
throw new InvalidArgumentException("Missing Config -- [mch_id]");
}
if (empty($options['mch_key'])) {
throw new InvalidArgumentException("Missing Config -- [mch_key]");
}
if (!empty($options['cache_path'])) {
Tools::$cache_path = $options['cache_path'];
}
$this->config = new DataArray($options);
// 商户基础参数
$this->params = new DataArray([
'appid' => $this->config->get('appid'),
'mch_id' => $this->config->get('mch_id'),
'nonce_str' => Tools::createNoncestr(),
]);
// 商户参数支持
if ($this->config->get('sub_appid')) {
$this->params->set('sub_appid', $this->config->get('sub_appid'));
}
if ($this->config->get('sub_mch_id')) {
$this->params->set('sub_mch_id', $this->config->get('sub_mch_id'));
}
}
/**
* 静态创建对象
* @param array $config
* @return static
*/
public static function instance(array $config)
{
$key = md5(get_called_class() . serialize($config));
if (isset(self::$cache[$key])) return self::$cache[$key];
return self::$cache[$key] = new static($config);
}
/**
* 获取微信支付通知
* @return array
* @throws InvalidResponseException
*/
public function getNotify()
{
$data = Tools::xml2arr(file_get_contents('php://input'));
if (isset($data['sign']) && $this->getPaySign($data) === $data['sign']) {
return $data;
}
throw new InvalidResponseException('Invalid Notify.', '0');
}
/**
* 获取微信支付通知回复内容
* @return string
*/
public function getNotifySuccessReply()
{
return Tools::arr2xml(['return_code' => 'SUCCESS', 'return_msg' => 'OK']);
}
/**
* 生成支付签名
* @param array $data 参与签名的数据
* @param string $signType 参与签名的类型
* @param string $buff 参与签名字符串前缀
* @return string
*/
public function getPaySign(array $data, $signType = 'MD5', $buff = '')
{
ksort($data);
if (isset($data['sign'])) unset($data['sign']);
foreach ($data as $k => $v) $buff .= "{$k}={$v}&";
$buff .= ("key=" . $this->config->get('mch_key'));
if (strtoupper($signType) === 'MD5') {
return strtoupper(md5($buff));
}
return strtoupper(hash_hmac('SHA256', $buff, $this->config->get('mch_key')));
}
/**
* 转换短链接
* @param string $longUrl 需要转换的URL签名用原串传输需URLencode
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function shortUrl($longUrl)
{
$url = 'https://api.mch.weixin.qq.com/tools/shorturl';
return $this->callPostApi($url, ['long_url' => $longUrl]);
}
/**
* 数组直接转xml数据输出
* @param array $data
* @param bool $isReturn
* @return string
*/
public function toXml(array $data, $isReturn = false)
{
$xml = Tools::arr2xml($data);
if ($isReturn) {
return $xml;
}
echo $xml;
}
/**
* 以Post请求接口
* @param string $url 请求
* @param array $data 接口参数
* @param bool $isCert 是否需要使用双向证书
* @param string $signType 数据签名类型 MD5|SHA256
* @param bool $needSignType 是否需要传签名类型参数
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
protected function callPostApi($url, array $data, $isCert = false, $signType = 'HMAC-SHA256', $needSignType = true)
{
$option = [];
if ($isCert) {
$option['ssl_p12'] = $this->config->get('ssl_p12');
$option['ssl_cer'] = $this->config->get('ssl_cer');
$option['ssl_key'] = $this->config->get('ssl_key');
if (is_string($option['ssl_p12']) && file_exists($option['ssl_p12'])) {
$content = file_get_contents($option['ssl_p12']);
if (openssl_pkcs12_read($content, $certs, $this->config->get('mch_id'))) {
$option['ssl_key'] = Tools::pushFile(md5($certs['pkey']) . '.pem', $certs['pkey']);
$option['ssl_cer'] = Tools::pushFile(md5($certs['cert']) . '.pem', $certs['cert']);
} else throw new InvalidArgumentException("P12 certificate does not match MCH_ID --- ssl_p12");
}
if (empty($option['ssl_cer']) || !file_exists($option['ssl_cer'])) {
throw new InvalidArgumentException("Missing Config -- ssl_cer", '0');
}
if (empty($option['ssl_key']) || !file_exists($option['ssl_key'])) {
throw new InvalidArgumentException("Missing Config -- ssl_key", '0');
}
}
$params = $this->params->merge($data);
$needSignType && ($params['sign_type'] = strtoupper($signType));
$params['sign'] = $this->getPaySign($params, $signType);
$result = Tools::xml2arr(Tools::post($url, Tools::arr2xml($params), $option));
if ($result['return_code'] !== 'SUCCESS') {
throw new InvalidResponseException($result['return_msg'], '0');
}
return $result;
}
}

View File

@ -0,0 +1,124 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Contracts;
use ArrayAccess;
/**
* Class DataArray
* @package WeChat
*/
class DataArray implements ArrayAccess
{
/**
* 当前配置值
* @var array
*/
private $config = [];
/**
* Config constructor.
* @param array $options
*/
public function __construct(array $options)
{
$this->config = $options;
}
/**
* 设置配置项值
* @param string $offset
* @param string|array|null|integer $value
*/
public function set($offset, $value)
{
$this->offsetSet($offset, $value);
}
/**
* 获取配置项参数
* @param string|null $offset
* @return array|string|null
*/
public function get($offset = null)
{
return $this->offsetGet($offset);
}
/**
* 合并数据到对象
* @param array $data 需要合并的数据
* @param bool $append 是否追加数据
* @return array
*/
public function merge(array $data, $append = false)
{
if ($append) {
return $this->config = array_merge($this->config, $data);
}
return array_merge($this->config, $data);
}
/**
* 设置配置项值
* @param string $offset
* @param string|array|null|integer $value
*/
public function offsetSet($offset, $value)
{
if (is_null($offset)) {
$this->config[] = $value;
} else {
$this->config[$offset] = $value;
}
}
/**
* 判断配置Key是否存在
* @param string $offset
* @return bool
*/
public function offsetExists($offset)
{
return isset($this->config[$offset]);
}
/**
* 清理配置项
* @param string|null $offset
*/
public function offsetUnset($offset = null)
{
if (is_null($offset)) {
$this->config = [];
} else {
unset($this->config[$offset]);
}
}
/**
* 获取配置项参数
* @param string|null $offset
* @return array|string|null
*/
public function offsetGet($offset = null)
{
if (is_null($offset)) {
return $this->config;
}
return isset($this->config[$offset]) ? $this->config[$offset] : null;
}
}

View File

@ -0,0 +1,194 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Contracts;
/**
* 错误消息处理
* Class DataError
* @package WeChat\Contracts
*/
class DataError
{
/**
* 接口代码错误
* @var array
*/
static $message = [
-1 => '系统繁忙,此时请开发者稍候再试',
0 => '请求成功',
40001 => '获取 access_token 时 AppSecret 错误,或者 access_token 无效。请开发者认真比对 AppSecret 的正确性,或查看是否正在为恰当的公众号调用接口',
40002 => '不合法的凭证类型',
40003 => '不合法的 OpenID ,请开发者确认 OpenID (该用户)是否已关注公众号,或是否是其他公众号的 OpenID',
40004 => '不合法的媒体文件类型',
40005 => '不合法的文件类型',
40006 => '不合法的文件大小',
40007 => '不合法的媒体文件 id',
40008 => '不合法的消息类型',
40009 => '不合法的图片文件大小',
40010 => '不合法的语音文件大小',
40011 => '不合法的视频文件大小',
40012 => '不合法的缩略图文件大小',
40013 => '不合法的 AppID ,请开发者检查 AppID 的正确性,避免异常字符,注意大小写',
40014 => '不合法的 access_token ,请开发者认真比对 access_token 的有效性(如是否过期),或查看是否正在为恰当的公众号调用接口',
40015 => '不合法的菜单类型',
40016 => '不合法的按钮个数',
40017 => '不合法的按钮个数',
40018 => '不合法的按钮名字长度',
40019 => '不合法的按钮 KEY 长度',
40020 => '不合法的按钮 URL 长度',
40021 => '不合法的菜单版本号',
40022 => '不合法的子菜单级数',
40023 => '不合法的子菜单按钮个数',
40024 => '不合法的子菜单按钮类型',
40025 => '不合法的子菜单按钮名字长度',
40026 => '不合法的子菜单按钮 KEY 长度',
40027 => '不合法的子菜单按钮 URL 长度',
40028 => '不合法的自定义菜单使用用户',
40029 => '不合法的 oauth_code',
40030 => '不合法的 refresh_token',
40031 => '不合法的 openid 列表',
40032 => '不合法的 openid 列表长度',
40033 => '不合法的请求字符,不能包含 \\uxxxx 格式的字符',
40035 => '不合法的参数',
40038 => '不合法的请求格式',
40039 => '不合法的 URL 长度',
40050 => '不合法的分组 id',
40051 => '分组名字不合法',
40060 => '删除单篇图文时,指定的 article_idx 不合法',
40117 => '分组名字不合法',
40118 => 'media_id 大小不合法',
40119 => 'button 类型错误',
40120 => 'button 类型错误',
40121 => '不合法的 media_id 类型',
40132 => '微信号不合法',
40137 => '不支持的图片格式',
40155 => '请勿添加其他公众号的主页链接',
41001 => '缺少 access_token 参数',
41002 => '缺少 appid 参数',
41003 => '缺少 refresh_token 参数',
41004 => '缺少 secret 参数',
41005 => '缺少多媒体文件数据',
41006 => '缺少 media_id 参数',
41007 => '缺少子菜单数据',
41008 => '缺少 oauth code',
41009 => '缺少 openid',
42001 => 'access_token 超时,请检查 access_token 的有效期,请参考基础支持 - 获取 access_token 中,对 access_token 的详细机制说明',
42002 => 'refresh_token 超时',
42003 => 'oauth_code 超时',
42007 => '用户修改微信密码, accesstoken 和 refreshtoken 失效,需要重新授权',
43001 => '需要 GET 请求',
43002 => '需要 POST 请求',
43003 => '需要 HTTPS 请求',
43004 => '需要接收者关注',
43005 => '需要好友关系',
43019 => '需要将接收者从黑名单中移除',
44001 => '多媒体文件为空',
44002 => 'POST 的数据包为空',
44003 => '图文消息内容为空',
44004 => '文本消息内容为空',
45001 => '多媒体文件大小超过限制',
45002 => '消息内容超过限制',
45003 => '标题字段超过限制',
45004 => '描述字段超过限制',
45005 => '链接字段超过限制',
45006 => '图片链接字段超过限制',
45007 => '语音播放时间超过限制',
45008 => '图文消息超过限制',
45009 => '接口调用超过限制',
45010 => '创建菜单个数超过限制',
45011 => 'API 调用太频繁,请稍候再试',
45015 => '回复时间超过限制',
45016 => '系统分组,不允许修改',
45017 => '分组名字过长',
45018 => '分组数量超过上限',
45047 => '客服接口下行条数超过上限',
46001 => '不存在媒体数据',
46002 => '不存在的菜单版本',
46003 => '不存在的菜单数据',
46004 => '不存在的用户',
47001 => '解析 JSON/XML 内容错误',
48001 => 'api 功能未授权,请确认公众号已获得该接口,可以在公众平台官网 - 开发者中心页中查看接口权限',
48002 => '粉丝拒收消息(粉丝在公众号选项中,关闭了 “ 接收消息 ” ',
48004 => 'api 接口被封禁,请登录 mp.weixin.qq.com 查看详情',
48005 => 'api 禁止删除被自动回复和自定义菜单引用的素材',
48006 => 'api 禁止清零调用次数,因为清零次数达到上限',
48008 => '没有该类型消息的发送权限',
50001 => '用户未授权该 api',
50002 => '用户受限,可能是违规后接口被封禁',
61451 => '参数错误 (invalid parameter)',
61452 => '无效客服账号 (invalid kf_account)',
61453 => '客服帐号已存在 (kf_account exsited)',
61454 => '客服帐号名长度超过限制 ( 仅允许 10 个英文字符,不包括 @ 及 @ 后的公众号的微信号 )(invalid kf_acount length)',
61455 => '客服帐号名包含非法字符 ( 仅允许英文 + 数字 )(illegal character in kf_account)',
61456 => '客服帐号个数超过限制 (10 个客服账号 )(kf_account count exceeded)',
61457 => '无效头像文件类型 (invalid file type)',
61450 => '系统错误 (system error)',
61500 => '日期格式错误',
65301 => '不存在此 menuid 对应的个性化菜单',
65302 => '没有相应的用户',
65303 => '没有默认菜单,不能创建个性化菜单',
65304 => 'MatchRule 信息为空',
65305 => '个性化菜单数量受限',
65306 => '不支持个性化菜单的帐号',
65307 => '个性化菜单信息为空',
65308 => '包含没有响应类型的 button',
65309 => '个性化菜单开关处于关闭状态',
65310 => '填写了省份或城市信息,国家信息不能为空',
65311 => '填写了城市信息,省份信息不能为空',
65312 => '不合法的国家信息',
65313 => '不合法的省份信息',
65314 => '不合法的城市信息',
65316 => '该公众号的菜单设置了过多的域名外跳(最多跳转到 3 个域名的链接)',
65317 => '不合法的 URL',
9001001 => 'POST 数据参数不合法',
9001002 => '远端服务不可用',
9001003 => 'Ticket 不合法',
9001004 => '获取摇周边用户信息失败',
9001005 => '获取商户信息失败',
9001006 => '获取 OpenID 失败',
9001007 => '上传文件缺失',
9001008 => '上传素材的文件类型不合法',
9001009 => '上传素材的文件尺寸不合法',
9001010 => '上传失败',
9001020 => '帐号不合法',
9001021 => '已有设备激活率低于 50% ,不能新增设备',
9001022 => '设备申请数不合法,必须为大于 0 的数字',
9001023 => '已存在审核中的设备 ID 申请',
9001024 => '一次查询设备 ID 数量不能超过 50',
9001025 => '设备 ID 不合法',
9001026 => '页面 ID 不合法',
9001027 => '页面参数不合法',
9001028 => '一次删除页面 ID 数量不能超过 10',
9001029 => '页面已应用在设备中,请先解除应用关系再删除',
9001030 => '一次查询页面 ID 数量不能超过 50',
9001031 => '时间区间不合法',
9001032 => '保存设备与页面的绑定关系参数错误',
9001033 => '门店 ID 不合法',
9001034 => '设备备注信息过长',
9001035 => '设备申请参数不合法',
9001036 => '查询起始值 begin 不合法',
];
/**
* 异常代码解析描述
* @param string $code
* @return string
*/
public static function toMessage($code)
{
return isset(self::$message[$code]) ? self::$message[$code] : $code;
}
}

View File

@ -0,0 +1,63 @@
<?php
namespace WeChat\Contracts;
/**
* 自定义CURL文件类
* Class MyCurlFile
* @package WeChat\Contracts
*/
class MyCurlFile extends \stdClass
{
/**
* 当前数据类型
* @var string
*/
public $datatype = 'MY_CURL_FILE';
/**
* MyCurlFile constructor.
* @param string|array $filename
* @param string $mimetype
* @param string $postname
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function __construct($filename, $mimetype = '', $postname = '')
{
if (is_array($filename)) {
foreach ($filename as $k => $v) $this->{$k} = $v;
} else {
$this->mimetype = $mimetype;
$this->postname = $postname;
$this->extension = pathinfo($filename, PATHINFO_EXTENSION);
if (empty($this->extension)) $this->extension = 'tmp';
if (empty($this->mimetype)) $this->mimetype = Tools::getExtMine($this->extension);
if (empty($this->postname)) $this->postname = pathinfo($filename, PATHINFO_BASENAME);
$this->content = base64_encode(file_get_contents($filename));
$this->tempname = md5($this->content) . ".{$this->extension}";
}
}
/**
* 获取文件信息
* @return \CURLFile|string
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function get()
{
$this->filename = Tools::pushFile($this->tempname, base64_decode($this->content));
if (class_exists('CURLFile')) {
return new \CURLFile($this->filename, $this->mimetype, $this->postname);
}
return "@{$this->tempname};filename={$this->postname};type={$this->mimetype}";
}
/**
* 类销毁处理
*/
public function __destruct()
{
// Tools::delCache($this->tempname);
}
}

View File

@ -0,0 +1,189 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
/**
* PKCS7算法 - 加解密
* Class PKCS7Encoder
*/
class PKCS7Encoder
{
public static $blockSize = 32;
/**
* 对需要加密的明文进行填充补位
* @param string $text 需要进行填充补位操作的明文
* @return string 补齐明文字符串
*/
function encode($text)
{
$amount_to_pad = PKCS7Encoder::$blockSize - (strlen($text) % PKCS7Encoder::$blockSize);
if ($amount_to_pad == 0) {
$amount_to_pad = PKCS7Encoder::$blockSize;
}
list($pad_chr, $tmp) = [chr($amount_to_pad), ''];
for ($index = 0; $index < $amount_to_pad; $index++) {
$tmp .= $pad_chr;
}
return $text . $tmp;
}
/**
* 对解密后的明文进行补位删除
* @param string $text 解密后的明文
* @return string 删除填充补位后的明文
*/
function decode($text)
{
$pad = ord(substr($text, -1));
if ($pad < 1 || $pad > PKCS7Encoder::$blockSize) {
$pad = 0;
}
return substr($text, 0, strlen($text) - $pad);
}
}
/**
* 公众号消息 - 加解密
* Class Prpcrypt
*/
class Prpcrypt
{
public $key;
/**
* Prpcrypt constructor.
* @param $key
*/
function __construct($key)
{
$this->key = base64_decode("{$key}=");
}
/**
* 对明文进行加密
* @param string $text 需要加密的明文
* @param string $appid 公众号APPID
* @return array
*/
public function encrypt($text, $appid)
{
try {
$random = $this->getRandomStr();
$iv = substr($this->key, 0, 16);
$pkcEncoder = new PKCS7Encoder();
$text = $pkcEncoder->encode($random . pack("N", strlen($text)) . $text . $appid);
$encrypted = openssl_encrypt($text, 'AES-256-CBC', substr($this->key, 0, 32), OPENSSL_ZERO_PADDING, $iv);
return [ErrorCode::$OK, $encrypted];
} catch (Exception $e) {
return [ErrorCode::$EncryptAESError, null];
}
}
/**
* 对密文进行解密
* @param string $encrypted 需要解密的密文
* @return array
*/
public function decrypt($encrypted)
{
try {
$iv = substr($this->key, 0, 16);
$decrypted = openssl_decrypt($encrypted, 'AES-256-CBC', substr($this->key, 0, 32), OPENSSL_ZERO_PADDING, $iv);
} catch (Exception $e) {
return [ErrorCode::$DecryptAESError, null];
}
try {
$pkcEncoder = new PKCS7Encoder();
$result = $pkcEncoder->decode($decrypted);
if (strlen($result) < 16) {
return [ErrorCode::$DecryptAESError, null];
}
$content = substr($result, 16, strlen($result));
$len_list = unpack("N", substr($content, 0, 4));
$xml_len = $len_list[1];
return [0, substr($content, 4, $xml_len), substr($content, $xml_len + 4)];
} catch (Exception $e) {
return [ErrorCode::$IllegalBuffer, null];
}
}
/**
* 随机生成16位字符串
* @param string $str
* @return string 生成的字符串
*/
function getRandomStr($str = "")
{
$str_pol = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrstuvwxyz";
$max = strlen($str_pol) - 1;
for ($i = 0; $i < 16; $i++) {
$str .= $str_pol[mt_rand(0, $max)];
}
return $str;
}
}
/**
* 仅用作类内部使用
* 不用于官方API接口的errCode码
* Class ErrorCode
*/
class ErrorCode
{
public static $OK = 0;
public static $ParseXmlError = 40002;
public static $IllegalAesKey = 40004;
public static $IllegalBuffer = 40008;
public static $EncryptAESError = 40006;
public static $DecryptAESError = 40007;
public static $EncodeBase64Error = 40009;
public static $DecodeBase64Error = 40010;
public static $GenReturnXmlError = 40011;
public static $ValidateAppidError = 40005;
public static $ComputeSignatureError = 40003;
public static $ValidateSignatureError = 40001;
public static $errCode = [
'0' => '处理成功',
'40001' => '校验签名失败',
'40002' => '解析xml失败',
'40003' => '计算签名失败',
'40004' => '不合法的AESKey',
'40005' => '校验AppID失败',
'40006' => 'AES加密失败',
'40007' => 'AES解密失败',
'40008' => '公众平台发送的xml不合法',
'40009' => 'Base64编码失败',
'40010' => 'Base64解码失败',
'40011' => '公众帐号生成回包xml失败',
];
/**
* 获取错误消息内容
* @param string $code 错误代码
* @return bool
*/
public static function getErrText($code)
{
if (isset(self::$errCode[$code])) {
return self::$errCode[$code];
}
return false;
}
}

View File

@ -0,0 +1,450 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Contracts;
use WeChat\Exceptions\InvalidArgumentException;
use WeChat\Exceptions\InvalidResponseException;
use WeChat\Exceptions\LocalCacheException;
/**
* 网络请求支持
* Class Tools
* @package WeChat\Contracts
*/
class Tools
{
/**
* 缓存路径
* @var null
*/
public static $cache_path = null;
/**
* 缓存写入操作
* @var array
*/
public static $cache_callable = [
'set' => null, // 写入缓存
'get' => null, // 获取缓存
'del' => null, // 删除缓存
'put' => null, // 写入文件
];
/**
* 网络缓存
* @var array
*/
private static $cache_curl = [];
/**
* 产生随机字符串
* @param int $length 指定字符长度
* @param string $str 字符串前缀
* @return string
*/
public static function createNoncestr($length = 32, $str = "")
{
$chars = "abcdefghijklmnopqrstuvwxyz0123456789";
for ($i = 0; $i < $length; $i++) {
$str .= substr($chars, mt_rand(0, strlen($chars) - 1), 1);
}
return $str;
}
/**
* 根据文件后缀获取文件类型
* @param string|array $ext 文件后缀
* @param array $mine 文件后缀MINE信息
* @return string
* @throws LocalCacheException
*/
public static function getExtMine($ext, $mine = [])
{
$mines = self::getMines();
foreach (is_string($ext) ? explode(',', $ext) : $ext as $e) {
$mine[] = isset($mines[strtolower($e)]) ? $mines[strtolower($e)] : 'application/octet-stream';
}
return join(',', array_unique($mine));
}
/**
* 获取所有文件扩展的类型
* @return array
* @throws LocalCacheException
*/
private static function getMines()
{
$mines = self::getCache('all_ext_mine');
if (empty($mines)) {
$content = file_get_contents('http://svn.apache.org/repos/asf/httpd/httpd/trunk/docs/conf/mime.types');
preg_match_all('#^([^\s]{2,}?)\s+(.+?)$#ism', $content, $matches, PREG_SET_ORDER);
foreach ($matches as $match) foreach (explode(" ", $match[2]) as $ext) $mines[$ext] = $match[1];
self::setCache('all_ext_mine', $mines);
}
return $mines;
}
/**
* 创建CURL文件对象
* @param $filename
* @param string $mimetype
* @param string $postname
* @return \CURLFile|string
* @throws LocalCacheException
*/
public static function createCurlFile($filename, $mimetype = null, $postname = null)
{
if (is_string($filename) && file_exists($filename)) {
if (is_null($postname)) $postname = basename($filename);
if (is_null($mimetype)) $mimetype = self::getExtMine(pathinfo($filename, 4));
if (function_exists('curl_file_create')) {
return curl_file_create($filename, $mimetype, $postname);
}
return "@{$filename};filename={$postname};type={$mimetype}";
}
return $filename;
}
/**
* 数组转XML内容
* @param array $data
* @return string
*/
public static function arr2xml($data)
{
return "<xml>" . self::_arr2xml($data) . "</xml>";
}
/**
* XML内容生成
* @param array $data 数据
* @param string $content
* @return string
*/
private static function _arr2xml($data, $content = '')
{
foreach ($data as $key => $val) {
is_numeric($key) && $key = 'item';
$content .= "<{$key}>";
if (is_array($val) || is_object($val)) {
$content .= self::_arr2xml($val);
} elseif (is_string($val)) {
$content .= '<![CDATA[' . preg_replace("/[\\x00-\\x08\\x0b-\\x0c\\x0e-\\x1f]/", '', $val) . ']]>';
} else {
$content .= $val;
}
$content .= "</{$key}>";
}
return $content;
}
/**
* 解析XML内容到数组
* @param string $xml
* @return array
*/
public static function xml2arr($xml)
{
$entity = libxml_disable_entity_loader(true);
$data = (array)simplexml_load_string($xml, 'SimpleXMLElement', LIBXML_NOCDATA);
libxml_disable_entity_loader($entity);
return json_decode(json_encode($data), true);
}
/**
* 数组转xml内容
* @param array $data
* @return null|string|string
*/
public static function arr2json($data)
{
$json = json_encode(self::buildEnEmojiData($data), JSON_UNESCAPED_UNICODE);
return $json === '[]' ? '{}' : $json;
}
/**
* 数组对象Emoji编译处理
* @param array $data
* @return array
*/
public static function buildEnEmojiData(array $data)
{
foreach ($data as $key => $value) {
if (is_array($value)) {
$data[$key] = self::buildEnEmojiData($value);
} elseif (is_string($value)) {
$data[$key] = self::emojiEncode($value);
} else {
$data[$key] = $value;
}
}
return $data;
}
/**
* 数组对象Emoji反解析处理
* @param array $data
* @return array
*/
public static function buildDeEmojiData(array $data)
{
foreach ($data as $key => $value) {
if (is_array($value)) {
$data[$key] = self::buildDeEmojiData($value);
} elseif (is_string($value)) {
$data[$key] = self::emojiDecode($value);
} else {
$data[$key] = $value;
}
}
return $data;
}
/**
* Emoji原形转换为String
* @param string $content
* @return string
*/
public static function emojiEncode($content)
{
return json_decode(preg_replace_callback("/(\\\u[ed][0-9a-f]{3})/i", function ($string) {
return addslashes($string[0]);
}, json_encode($content)));
}
/**
* Emoji字符串转换为原形
* @param string $content
* @return string
*/
public static function emojiDecode($content)
{
return json_decode(preg_replace_callback('/\\\\\\\\/i', function () {
return '\\';
}, json_encode($content)));
}
/**
* 解析JSON内容到数组
* @param string $json
* @return array
* @throws InvalidResponseException
*/
public static function json2arr($json)
{
$result = json_decode($json, true);
if (empty($result)) {
throw new InvalidResponseException('invalid response.', '0');
}
if (!empty($result['errcode'])) {
throw new InvalidResponseException($result['errmsg'], $result['errcode'], $result);
}
return $result;
}
/**
* 以get访问模拟访问
* @param string $url 访问URL
* @param array $query GET数
* @param array $options
* @return boolean|string
* @throws LocalCacheException
*/
public static function get($url, $query = [], $options = [])
{
$options['query'] = $query;
return self::doRequest('get', $url, $options);
}
/**
* 以post访问模拟访问
* @param string $url 访问URL
* @param array $data POST数据
* @param array $options
* @return boolean|string
* @throws LocalCacheException
*/
public static function post($url, $data = [], $options = [])
{
$options['data'] = $data;
return self::doRequest('post', $url, $options);
}
/**
* CURL模拟网络请求
* @param string $method 请求方法
* @param string $url 请求方法
* @param array $options 请求参数[headers,data,ssl_cer,ssl_key]
* @return boolean|string
* @throws LocalCacheException
*/
public static function doRequest($method, $url, $options = [])
{
$curl = curl_init();
// GET参数设置
if (!empty($options['query'])) {
$url .= (stripos($url, '?') !== false ? '&' : '?') . http_build_query($options['query']);
}
// CURL头信息设置
if (!empty($options['headers'])) {
curl_setopt($curl, CURLOPT_HTTPHEADER, $options['headers']);
}
// POST数据设置
if (strtolower($method) === 'post') {
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, self::_buildHttpData($options['data']));
}
// 证书文件设置
if (!empty($options['ssl_cer'])) if (file_exists($options['ssl_cer'])) {
curl_setopt($curl, CURLOPT_SSLCERTTYPE, 'PEM');
curl_setopt($curl, CURLOPT_SSLCERT, $options['ssl_cer']);
} else throw new InvalidArgumentException("Certificate files that do not exist. --- [ssl_cer]");
// 证书文件设置
if (!empty($options['ssl_key'])) if (file_exists($options['ssl_key'])) {
curl_setopt($curl, CURLOPT_SSLKEYTYPE, 'PEM');
curl_setopt($curl, CURLOPT_SSLKEY, $options['ssl_key']);
} else throw new InvalidArgumentException("Certificate files that do not exist. --- [ssl_key]");
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_TIMEOUT, 60);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
list($content) = [curl_exec($curl), curl_close($curl)];
// 清理 CURL 缓存文件
if (!empty(self::$cache_curl)) foreach (self::$cache_curl as $key => $file) {
Tools::delCache($file);
unset(self::$cache_curl[$key]);
}
return $content;
}
/**
* POST数据过滤处理
* @param array $data 需要处理的数据
* @param boolean $build 是否编译数据
* @return array|string
* @throws \WeChat\Exceptions\LocalCacheException
*/
private static function _buildHttpData($data, $build = true)
{
if (!is_array($data)) return $data;
foreach ($data as $key => $value) if (is_object($value) && $value instanceof \CURLFile) {
$build = false;
} elseif (is_object($value) && isset($value->datatype) && $value->datatype === 'MY_CURL_FILE') {
$build = false;
$mycurl = new MyCurlFile((array)$value);
$data[$key] = $mycurl->get();
array_push(self::$cache_curl, $mycurl->tempname);
} elseif (is_string($value) && class_exists('CURLFile', false) && stripos($value, '@') === 0) {
if (($filename = realpath(trim($value, '@'))) && file_exists($filename)) {
$build = false;
$data[$key] = self::createCurlFile($filename);
}
}
return $build ? http_build_query($data) : $data;
}
/**
* 写入文件
* @param string $name 文件名称
* @param string $content 文件内容
* @return string
* @throws LocalCacheException
*/
public static function pushFile($name, $content)
{
if (is_callable(self::$cache_callable['put'])) {
return call_user_func_array(self::$cache_callable['put'], func_get_args());
}
$file = self::_getCacheName($name);
if (!file_put_contents($file, $content)) {
throw new LocalCacheException('local file write error.', '0');
}
return $file;
}
/**
* 缓存配置与存储
* @param string $name 缓存名称
* @param string $value 缓存内容
* @param int $expired 缓存时间(0表示永久缓存)
* @return string
* @throws LocalCacheException
*/
public static function setCache($name, $value = '', $expired = 3600)
{
if (is_callable(self::$cache_callable['set'])) {
return call_user_func_array(self::$cache_callable['set'], func_get_args());
}
$file = self::_getCacheName($name);
$data = ['name' => $name, 'value' => $value, 'expired' => time() + intval($expired)];
if (!file_put_contents($file, serialize($data))) {
throw new LocalCacheException('local cache error.', '0');
}
return $file;
}
/**
* 获取缓存内容
* @param string $name 缓存名称
* @return null|mixed
*/
public static function getCache($name)
{
if (is_callable(self::$cache_callable['get'])) {
return call_user_func_array(self::$cache_callable['get'], func_get_args());
}
$file = self::_getCacheName($name);
if (file_exists($file) && ($content = file_get_contents($file))) {
$data = unserialize($content);
if (isset($data['expired']) && (intval($data['expired']) === 0 || intval($data['expired']) >= time())) {
return $data['value'];
}
self::delCache($name);
}
return null;
}
/**
* 移除缓存文件
* @param string $name 缓存名称
* @return boolean
*/
public static function delCache($name)
{
if (is_callable(self::$cache_callable['del'])) {
return call_user_func_array(self::$cache_callable['del'], func_get_args());
}
$file = self::_getCacheName($name);
return file_exists($file) ? unlink($file) : true;
}
/**
* 应用缓存目录
* @param string $name
* @return string
*/
private static function _getCacheName($name)
{
if (empty(self::$cache_path)) {
self::$cache_path = dirname(dirname(__DIR__)) . DIRECTORY_SEPARATOR . 'Cache' . DIRECTORY_SEPARATOR;
}
self::$cache_path = rtrim(self::$cache_path, '/\\') . DIRECTORY_SEPARATOR;
file_exists(self::$cache_path) || mkdir(self::$cache_path, 0755, true);
return self::$cache_path . $name;
}
}

View File

@ -0,0 +1,247 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
use WeChat\Contracts\Tools;
/**
* 客服消息处理
* Class Custom
* @package WeChat
*/
class Custom extends BasicWeChat
{
/**
* 添加客服帐号
* @param string $kf_account 客服账号
* @param string $nickname 客服昵称
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addAccount($kf_account, $nickname)
{
$data = ['kf_account' => $kf_account, 'nickname' => $nickname];
$url = "https://api.weixin.qq.com/customservice/kfaccount/add?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 修改客服帐号
* @param string $kf_account 客服账号
* @param string $nickname 客服昵称
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateAccount($kf_account, $nickname)
{
$data = ['kf_account' => $kf_account, 'nickname' => $nickname];
$url = "https://api.weixin.qq.com/customservice/kfaccount/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 删除客服帐号
* @param string $kf_account 客服账号
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function deleteAccount($kf_account)
{
$data = ['kf_account' => $kf_account];
$url = "https://api.weixin.qq.com/customservice/kfaccount/del?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 邀请绑定客服帐号
* @param string $kf_account 完整客服帐号,格式为:帐号前缀@公众号微信号
* @param string $invite_wx 接收绑定邀请的客服微信号
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function inviteWorker($kf_account, $invite_wx)
{
$url = 'https://api.weixin.qq.com/customservice/kfaccount/inviteworker?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['kf_account' => $kf_account, 'invite_wx' => $invite_wx]);
}
/**
* 获取所有客服账号
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getAccountList()
{
$url = "https://api.weixin.qq.com/cgi-bin/customservice/getkflist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 设置客服帐号的头像
* @param string $kf_account 客户账号
* @param string $image 头像文件位置
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function uploadHeadimg($kf_account, $image)
{
$url = "http://api.weixin.qq.com/customservice/kfaccount/uploadheadimg?access_token=ACCESS_TOKEN&kf_account={$kf_account}";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['media' => Tools::createCurlFile($image)]);
}
/**
* 客服接口-发消息
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function send(array $data)
{
$url = "https://api.weixin.qq.com/cgi-bin/message/custom/send?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 客服输入状态
* @param string $openid 普通用户openid
* @param string $command Typing:正在输入,CancelTyping:取消正在输入
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function typing($openid, $command = 'Typing')
{
$url = "https://api.weixin.qq.com/cgi-bin/message/custom/typing?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['touser' => $openid, 'command' => $command]);
}
/**
* 根据标签进行群发【订阅号与服务号认证后均可用】
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function massSendAll(array $data)
{
$url = "https://api.weixin.qq.com/cgi-bin/message/mass/sendall?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 根据OpenID列表群发【订阅号不可用服务号认证后可用】
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function massSend(array $data)
{
$url = "https://api.weixin.qq.com/cgi-bin/message/mass/send?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 删除群发【订阅号与服务号认证后均可用】
* @param integer $msg_id 发送出去的消息ID
* @param null|integer $article_idx 要删除的文章在图文消息中的位置第一篇编号为1该字段不填或填0会删除全部文章
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function massDelete($msg_id, $article_idx = null)
{
$data = ['msg_id' => $msg_id];
is_null($article_idx) || $data['article_idx'] = $article_idx;
$url = "https://api.weixin.qq.com/cgi-bin/message/mass/delete?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 预览接口【订阅号与服务号认证后均可用】
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function massPreview(array $data)
{
$url = "https://api.weixin.qq.com/cgi-bin/message/mass/preview?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询群发消息发送状态【订阅号与服务号认证后均可用】
* @param integer $msg_id 群发消息后返回的消息id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function massGet($msg_id)
{
$url = "https://api.weixin.qq.com/cgi-bin/message/mass/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['msg_id' => $msg_id]);
}
/**
* 获取群发速度
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function massGetSeed()
{
$url = "https://api.weixin.qq.com/cgi-bin/message/mass/speed/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, []);
}
/**
* 设置群发速度
* @param integer $speed 群发速度的级别
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function massSetSeed($speed)
{
$url = "https://api.weixin.qq.com/cgi-bin/message/mass/speed/set?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['speed' => $speed]);
}
}

View File

@ -0,0 +1,40 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Exceptions;
/**
* 接口参数异常
* Class InvalidArgumentException
* @package WeChat
*/
class InvalidArgumentException extends \InvalidArgumentException
{
/**
* @var array
*/
public $raw = [];
/**
* InvalidArgumentException constructor.
* @param string $message
* @param integer $code
* @param array $raw
*/
public function __construct($message, $code = 0, $raw = [])
{
parent::__construct($message, intval($code));
$this->raw = $raw;
}
}

View File

@ -0,0 +1,40 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Exceptions;
/**
* 加密解密异常
* Class InvalidResponseException
* @package WeChat
*/
class InvalidDecryptException extends \Exception
{
/**
* @var array
*/
public $raw = [];
/**
* InvalidDecryptException constructor.
* @param string $message
* @param integer $code
* @param array $raw
*/
public function __construct($message, $code = 0, $raw = [])
{
parent::__construct($message, intval($code));
$this->raw = $raw;
}
}

View File

@ -0,0 +1,40 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Exceptions;
/**
* 加载类异常
* Class InvalidInstanceException
* @package WeChat\Exceptions
*/
class InvalidInstanceException extends \Exception
{
/**
* @var array
*/
public $raw = [];
/**
* InvalidResponseException constructor.
* @param string $message
* @param integer $code
* @param array $raw
*/
public function __construct($message, $code = 0, $raw = [])
{
parent::__construct($message, intval($code));
$this->raw = $raw;
}
}

View File

@ -0,0 +1,41 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Exceptions;
/**
* 返回异常
* Class InvalidResponseException
* @package WeChat
*/
class InvalidResponseException extends \Exception
{
/**
* @var array
*/
public $raw = [];
/**
* InvalidResponseException constructor.
* @param string $message
* @param integer $code
* @param array $raw
*/
public function __construct($message, $code = 0, $raw = [])
{
parent::__construct($message, intval($code));
$this->raw = $raw;
}
}

View File

@ -0,0 +1,42 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat\Exceptions;
/***
* 本地缓存异常
* Class LocalCacheException
* @package WeChat
*/
class LocalCacheException extends \Exception
{
/**
* @var array
*/
public $raw = [];
/**
* LocalCacheException constructor.
* @param string $message
* @param integer $code
* @param array $raw
*/
public function __construct($message, $code = 0, $raw = [])
{
parent::__construct($message, intval($code));
$this->raw = $raw;
}
}

View File

@ -0,0 +1,68 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 接口调用频次限制
* Class Limit
* @package WeChat
*/
class Limit extends BasicWeChat
{
/**
* 公众号调用或第三方平台帮公众号调用对公众号的所有api调用包括第三方帮其调用次数进行清零
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function clearQuota()
{
$url = 'https://api.weixin.qq.com/cgi-bin/clear_quota?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['appid' => $this->config->get('appid')]);
}
/**
* 网络检测
* @param string $action 执行的检测动作
* @param string $operator 指定平台从某个运营商进行检测
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function ping($action = 'all', $operator = 'DEFAULT')
{
$url = 'https://api.weixin.qq.com/cgi-bin/callback/check?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['action' => $action, 'check_operator' => $operator]);
}
/**
* 获取微信服务器IP地址
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCallbackIp()
{
$url = 'https://api.weixin.qq.com/cgi-bin/getcallbackip?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
}

View File

@ -0,0 +1,201 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\Tools;
use WeChat\Contracts\BasicWeChat;
use WeChat\Exceptions\InvalidResponseException;
/**
* 微信素材管理
* Class Media
* @package WeChat
*/
class Media extends BasicWeChat
{
/**
* 新增临时素材
* @param string $filename 文件名称
* @param string $type 媒体文件类型(image|voice|video|thumb)
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function add($filename, $type = 'image')
{
if (!in_array($type, ['image', 'voice', 'video', 'thumb'])) {
throw new InvalidResponseException('Invalid Media Type.', '0');
}
$url = "https://api.weixin.qq.com/cgi-bin/media/upload?access_token=ACCESS_TOKEN&type={$type}";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['media' => Tools::createCurlFile($filename)], false);
}
/**
* 获取临时素材
* @param string $media_id
* @param string $outType 返回处理函数
* @return array|string
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function get($media_id, $outType = null)
{
$url = "https://api.weixin.qq.com/cgi-bin/media/get?access_token=ACCESS_TOKEN&media_id={$media_id}";
$this->registerApi($url, __FUNCTION__, func_get_args());
$result = Tools::get($url);
if (is_array($json = json_decode($result, true))) {
if (!$this->isTry && isset($json['errcode']) && in_array($json['errcode'], ['40014', '40001', '41001', '42001'])) {
[$this->delAccessToken(), $this->isTry = true];
return call_user_func_array([$this, $this->currentMethod['method']], $this->currentMethod['arguments']);
}
return Tools::json2arr($result);
}
return is_null($outType) ? $result : $outType($result);
}
/**
* 新增图文素材
* @param array $data 文件名称
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function addNews($data)
{
$url = "https://api.weixin.qq.com/cgi-bin/material/add_news?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 更新图文素材
* @param string $media_id 要修改的图文消息的id
* @param int $index 要更新的文章在图文消息中的位置多图文消息时此字段才有意义第一篇为0
* @param array $news 文章内容
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function updateNews($media_id, $index, $news)
{
$data = ['media_id' => $media_id, 'index' => $index, 'articles' => $news];
$url = "https://api.weixin.qq.com/cgi-bin/material/update_news?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 上传图文消息内的图片获取URL
* @param string $filename
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function uploadImg($filename)
{
$url = "https://api.weixin.qq.com/cgi-bin/media/uploadimg?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['media' => Tools::createCurlFile($filename)], false);
}
/**
* 新增其他类型永久素材
* @param string $filename 文件名称
* @param string $type 媒体文件类型(image|voice|video|thumb)
* @param array $description 包含素材的描述信息
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function addMaterial($filename, $type = 'image', $description = [])
{
if (!in_array($type, ['image', 'voice', 'video', 'thumb'])) {
throw new InvalidResponseException('Invalid Media Type.', '0');
}
$url = "https://api.weixin.qq.com/cgi-bin/material/add_material?access_token=ACCESS_TOKEN&type={$type}";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['media' => Tools::createCurlFile($filename), 'description' => Tools::arr2json($description)], false);
}
/**
* 获取永久素材
* @param string $media_id
* @param null|string $outType 输出类型
* @return array|string
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function getMaterial($media_id, $outType = null)
{
$url = "https://api.weixin.qq.com/cgi-bin/material/get_material?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
$result = Tools::post($url, ['media_id' => $media_id]);
if (is_array($json = json_decode($result, true))) {
if (!$this->isTry && isset($json['errcode']) && in_array($json['errcode'], ['40014', '40001', '41001', '42001'])) {
[$this->delAccessToken(), $this->isTry = true];
return call_user_func_array([$this, $this->currentMethod['method']], $this->currentMethod['arguments']);
}
return Tools::json2arr($result);
}
return is_null($outType) ? $result : $outType($result);
}
/**
* 删除永久素材
* @param string $media_id
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function delMaterial($media_id)
{
$url = "https://api.weixin.qq.com/cgi-bin/material/del_material?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['media_id' => $media_id]);
}
/**
* 获取素材总数
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function getMaterialCount()
{
$url = "https://api.weixin.qq.com/cgi-bin/material/get_materialcount?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 获取素材列表
* @param string $type
* @param int $offset
* @param int $count
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function batchGetMaterial($type = 'image', $offset = 0, $count = 20)
{
if (!in_array($type, ['image', 'voice', 'video', 'news'])) {
throw new InvalidResponseException('Invalid Media Type.', '0');
}
$url = "https://api.weixin.qq.com/cgi-bin/material/batchget_material?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['type' => $type, 'offset' => $offset, 'count' => $count]);
}
}

View File

@ -0,0 +1,109 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 微信菜单管理
* Class Menu
* @package WeChat
*/
class Menu extends BasicWeChat
{
/**
* 自定义菜单查询接口
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function get()
{
$url = "https://api.weixin.qq.com/cgi-bin/menu/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 自定义菜单删除接口
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function delete()
{
$url = "https://api.weixin.qq.com/cgi-bin/menu/delete?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 自定义菜单创建
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function create(array $data)
{
$url = "https://api.weixin.qq.com/cgi-bin/menu/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 创建个性化菜单
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addConditional(array $data)
{
$url = "https://api.weixin.qq.com/cgi-bin/menu/addconditional?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 删除个性化菜单
* @param string $menuid
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function delConditional($menuid)
{
$url = "https://api.weixin.qq.com/cgi-bin/menu/delconditional?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['menuid' => $menuid]);
}
/**
* 测试个性化菜单匹配结果
* @param string $openid
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function tryConditional($openid)
{
$url = "https://api.weixin.qq.com/cgi-bin/menu/trymatch?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['user_id' => $openid]);
}
}

View File

@ -0,0 +1,99 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 微信网页授权
* Class Oauth
* @package WeChat
*/
class Oauth extends BasicWeChat
{
/**
* Oauth 授权跳转接口
* @param string $redirect_url 授权回跳地址
* @param string $state 为重定向后会带上state参数填写a-zA-Z0-9的参数值最多128字节
* @param string $scope 授权类类型(可选值snsapi_base|snsapi_userinfo)
* @return string
*/
public function getOauthRedirect($redirect_url, $state = '', $scope = 'snsapi_base')
{
$appid = $this->config->get('appid');
$redirect_uri = urlencode($redirect_url);
return "https://open.weixin.qq.com/connect/oauth2/authorize?appid={$appid}&redirect_uri={$redirect_uri}&response_type=code&scope={$scope}&state={$state}#wechat_redirect";
}
/**
* 通过 code 获取 AccessToken openid
* @return bool|array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getOauthAccessToken()
{
$appid = $this->config->get('appid');
$appsecret = $this->config->get('appsecret');
$code = isset($_GET['code']) ? $_GET['code'] : '';
$url = "https://api.weixin.qq.com/sns/oauth2/access_token?appid={$appid}&secret={$appsecret}&code={$code}&grant_type=authorization_code";
return $this->httpGetForJson($url);
}
/**
* 刷新AccessToken并续期
* @param string $refresh_token
* @return bool|array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getOauthRefreshToken($refresh_token)
{
$appid = $this->config->get('appid');
$url = "https://api.weixin.qq.com/sns/oauth2/refresh_token?appid={$appid}&grant_type=refresh_token&refresh_token={$refresh_token}";
return $this->httpGetForJson($url);
}
/**
* 检验授权凭证access_token是否有效
* @param string $access_token 网页授权接口调用凭证,注意此access_token与基础支持的access_token不同
* @param string $openid 用户的唯一标识
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function checkOauthAccessToken($access_token, $openid)
{
$url = "https://api.weixin.qq.com/sns/auth?access_token={$access_token}&openid={$openid}";
return $this->httpGetForJson($url);
}
/**
* 拉取用户信息(需scope为 snsapi_userinfo)
* @param string $access_token 网页授权接口调用凭证,注意此access_token与基础支持的access_token不同
* @param string $openid 用户的唯一标识
* @param string $lang 返回国家地区语言版本zh_CN 简体zh_TW 繁体en 英语
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getUserInfo($access_token, $openid, $lang = 'zh_CN')
{
$url = "https://api.weixin.qq.com/sns/userinfo?access_token={$access_token}&openid={$openid}&lang={$lang}";
return $this->httpGetForJson($url);
}
}

View File

@ -0,0 +1,232 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWePay;
use WeChat\Exceptions\InvalidResponseException;
use WePay\Bill;
use WePay\Order;
use WePay\Refund;
use WePay\Transfers;
use WePay\TransfersBank;
/**
* 微信支付商户
* Class Pay
* @package WeChat\Contracts
*/
class Pay extends BasicWePay
{
/**
* 统一下单
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function createOrder(array $options)
{
return Order::instance($this->config->get())->create($options);
}
/**
* 刷卡支付
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function createMicropay($options)
{
return Order::instance($this->config->get())->micropay($options);
}
/**
* 创建JsApi及H5支付参数
* @param string $prepay_id 统一下单预支付码
* @return array
*/
public function createParamsForJsApi($prepay_id)
{
return Order::instance($this->config->get())->jsapiParams($prepay_id);
}
/**
* 获取APP支付参数
* @param string $prepay_id 统一下单预支付码
* @return array
*/
public function createParamsForApp($prepay_id)
{
return Order::instance($this->config->get())->appParams($prepay_id);
}
/**
* 获取支付规则二维码
* @param string $product_id 商户定义的商品id 或者订单号
* @return string
*/
public function createParamsForRuleQrc($product_id)
{
return Order::instance($this->config->get())->qrcParams($product_id);
}
/**
* 查询订单
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function queryOrder(array $options)
{
return Order::instance($this->config->get())->query($options);
}
/**
* 关闭订单
* @param string $out_trade_no 商户订单号
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function closeOrder($out_trade_no)
{
return Order::instance($this->config->get())->close($out_trade_no);
}
/**
* 申请退款
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function createRefund(array $options)
{
return Refund::instance($this->config->get())->create($options);
}
/**
* 查询退款
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function queryRefund(array $options)
{
return Refund::instance($this->config->get())->query($options);
}
/**
* 交易保障
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function report(array $options)
{
return Order::instance($this->config->get())->report($options);
}
/**
* 授权码查询openid
* @param string $authCode 扫码支付授权码,设备读取用户微信中的条码或者二维码信息
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function queryAuthCode($authCode)
{
return Order::instance($this->config->get())->queryAuthCode($authCode);
}
/**
* 下载对账单
* @param array $options 静音参数
* @param null|string $outType 输出类型
* @return bool|string
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function billDownload(array $options, $outType = null)
{
return Bill::instance($this->config->get())->download($options, $outType);
}
/**
* 拉取订单评价数据
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function billCommtent(array $options)
{
return Bill::instance($this->config->get())->comment($options);
}
/**
* 企业付款到零钱
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function createTransfers(array $options)
{
return Transfers::instance($this->config->get())->create($options);
}
/**
* 查询企业付款到零钱
* @param string $partner_trade_no 商户调用企业付款API时使用的商户订单号
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function queryTransfers($partner_trade_no)
{
return Transfers::instance($this->config->get())->query($partner_trade_no);
}
/**
* 企业付款到银行卡
* @param array $options
* @return array
* @throws Exceptions\LocalCacheException
* @throws Exceptions\InvalidDecryptException
* @throws Exceptions\InvalidResponseException
*/
public function createTransfersBank(array $options)
{
return TransfersBank::instance($this->config->get())->create($options);
}
/**
* 商户企业付款到银行卡操作进行结果查询
* @param string $partner_trade_no 商户订单号,需保持唯一
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function queryTransFresBank($partner_trade_no)
{
return TransfersBank::instance($this->config->get())->query($partner_trade_no);
}
}

View File

@ -0,0 +1,177 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 商店管理
* Class Product
* @package WeChat
*/
class Product extends BasicWeChat
{
/**
* 提交审核/取消发布商品
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @param string $status 设置发布状态。on为提交审核off为取消发布
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function modStatus($keystandard, $keystr, $status = 'on')
{
$data = ['keystandard' => $keystandard, 'keystr' => $keystr, 'status' => $status];
$url = "https://api.weixin.qq.com/scan/product/modstatus?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 设置测试人员白名单
* @param array $openids 测试人员的openid列表
* @param array $usernames 测试人员的微信号列表
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setTestWhiteList(array $openids = [], array $usernames = [])
{
$data = ['openid' => $openids, 'username' => $usernames];
$url = "https://api.weixin.qq.com/scan/testwhitelist/set?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 获取商品二维码
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @param integer $qrcode_size 二维码的尺寸整型数值代表边长像素数不填写默认值为100
* @param array $extinfo 由商户自定义传入,建议仅使用大小写字母、数字及-_().*这6个常用字符
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getQrcode($keystandard, $keystr, $qrcode_size, $extinfo = [])
{
$data = ['keystandard' => $keystandard, 'keystr' => $keystr, 'qrcode_size' => $qrcode_size];
empty($extinfo) || $data['extinfo'] = $extinfo;
$url = "https://api.weixin.qq.com/scan/product/getqrcode?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询商品信息
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getProduct($keystandard, $keystr)
{
$data = ['keystandard' => $keystandard, 'keystr' => $keystr];
empty($extinfo) || $data['extinfo'] = $extinfo;
$url = "https://api.weixin.qq.com/scan/product/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 批量查询商品信息
* @param integer $offset 批量查询的起始位置从0开始包含该起始位置
* @param integer $limit 批量查询的数量
* @param null|string $status 支持按状态拉取。on为发布状态off为未发布状态check为审核中状态reject为审核未通过状态all为所有状态
* @param string $keystr 支持按部分编码内容拉取。填写该参数后,可将编码内容中包含所传参数的商品信息拉出。类似关键词搜索
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getProductList($offset, $limit = 10, $status = null, $keystr = '')
{
$data = ['offset' => $offset, 'limit' => $limit];
is_null($status) || $data['status'] = $status;
empty($keystr) || $data['keystr'] = $keystr;
$url = "https://api.weixin.qq.com/scan/product/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 更新商品信息
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateProduct(array $data)
{
$url = "https://api.weixin.qq.com/scan/product/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 清除商品信息
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function clearProduct($keystandard, $keystr)
{
$url = "https://api.weixin.qq.com/scan/product/clear?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['keystandard' => $keystandard, 'keystr' => $keystr]);
}
/**
* 检查wxticket参数
* @param string $ticket
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function scanTicketCheck($ticket)
{
$url = "https://api.weixin.qq.com/scan/scanticket/check?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['ticket' => $ticket]);
}
/**
* 清除扫码记录
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @param string $extinfo 调用“获取商品二维码接口”时传入的extinfo为标识参数
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function clearScanticket($keystandard, $keystr, $extinfo)
{
$data = ['keystandard' => $keystandard, 'keystr' => $keystr, 'extinfo' => $extinfo];
$url = "https://api.weixin.qq.com/scan/scanticket/check?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
}

View File

@ -0,0 +1,77 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 二维码管理
* Class Qrcode
* @package WeChat
*/
class Qrcode extends BasicWeChat
{
/**
* 创建二维码ticket
* @param string|integer $scene 场景
* @param int $expire_seconds 有效时间
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function create($scene, $expire_seconds = 0)
{
if (is_integer($scene)) { // 二维码场景类型
$data = ['action_info' => ['scene' => ['scene_id' => $scene]]];
} else {
$data = ['action_info' => ['scene' => ['scene_str' => $scene]]];
}
if ($expire_seconds > 0) { // 临时二维码
$data['expire_seconds'] = $expire_seconds;
$data['action_name'] = is_integer($scene) ? 'QR_SCENE' : 'QR_STR_SCENE';
} else { // 永久二维码
$data['action_name'] = is_integer($scene) ? 'QR_LIMIT_SCENE' : 'QR_LIMIT_STR_SCENE';
}
$url = "https://api.weixin.qq.com/cgi-bin/qrcode/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 通过ticket换取二维码
* @param string $ticket 获取的二维码ticket凭借此ticket可以在有效时间内换取二维码。
* @return string
*/
public function url($ticket)
{
return "https://mp.weixin.qq.com/cgi-bin/showqrcode?ticket={$ticket}";
}
/**
* 长链接转短链接接口
* @param string $longUrl 需要转换的长链接
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function shortUrl($longUrl)
{
$url = "https://api.weixin.qq.com/cgi-bin/shorturl?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['action' => 'long2short', 'long_url' => $longUrl]);
}
}

View File

@ -0,0 +1,164 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicPushEvent;
/**
* 公众号推送管理
* Class Receive
* @package WeChat
*/
class Receive extends BasicPushEvent
{
/**
* 转发多客服消息
* @param string $account
* @return $this
*/
public function transferCustomerService($account = '')
{
$this->message = [
'CreateTime' => time(),
'ToUserName' => $this->getOpenid(),
'FromUserName' => $this->getToOpenid(),
'MsgType' => 'transfer_customer_service',
];
empty($account) || $this->message['TransInfo'] = ['KfAccount' => $account];
return $this;
}
/**
* 设置文本消息
* @param string $content 文本内容
* @return $this
*/
public function text($content = '')
{
$this->message = [
'MsgType' => 'text',
'CreateTime' => time(),
'Content' => $content,
'ToUserName' => $this->getOpenid(),
'FromUserName' => $this->getToOpenid(),
];
return $this;
}
/**
* 设置回复图文
* @param array $newsData
* @return $this
*/
public function news($newsData = [])
{
$this->message = [
'CreateTime' => time(),
'MsgType' => 'news',
'Articles' => $newsData,
'ToUserName' => $this->getOpenid(),
'FromUserName' => $this->getToOpenid(),
'ArticleCount' => count($newsData),
];
return $this;
}
/**
* 设置图片消息
* @param string $mediaId 图片媒体ID
* @return $this
*/
public function image($mediaId = '')
{
$this->message = [
'MsgType' => 'image',
'CreateTime' => time(),
'ToUserName' => $this->getOpenid(),
'FromUserName' => $this->getToOpenid(),
'Image' => ['MediaId' => $mediaId],
];
return $this;
}
/**
* 设置语音回复消息
* @param string $mediaid 语音媒体ID
* @return $this
*/
public function voice($mediaid = '')
{
$this->message = [
'CreateTime' => time(),
'MsgType' => 'voice',
'ToUserName' => $this->getOpenid(),
'FromUserName' => $this->getToOpenid(),
'Voice' => ['MediaId' => $mediaid],
];
return $this;
}
/**
* 设置视频回复消息
* @param string $mediaid 视频媒体ID
* @param string $title 视频标题
* @param string $description 视频描述
* @return $this
*/
public function video($mediaid = '', $title = '', $description = '')
{
$this->message = [
'CreateTime' => time(),
'MsgType' => 'video',
'ToUserName' => $this->getOpenid(),
'FromUserName' => $this->getToOpenid(),
'Video' => [
'Title' => $title,
'MediaId' => $mediaid,
'Description' => $description,
],
];
return $this;
}
/**
* 设置音乐回复消息
* @param string $title 音乐标题
* @param string $desc 音乐描述
* @param string $musicurl 音乐地址
* @param string $hgmusicurl 高清音乐地址
* @param string $thumbmediaid 音乐图片缩略图的媒体id可选
* @return $this
*/
public function music($title, $desc, $musicurl, $hgmusicurl = '', $thumbmediaid = '')
{
$this->message = [
'CreateTime' => time(),
'MsgType' => 'music',
'ToUserName' => $this->getOpenid(),
'FromUserName' => $this->getToOpenid(),
'Music' => [
'Title' => $title,
'Description' => $desc,
'MusicUrl' => $musicurl,
'HQMusicUrl' => $hgmusicurl,
],
];
if ($thumbmediaid) {
$this->message['Music']['ThumbMediaId'] = $thumbmediaid;
}
return $this;
}
}

View File

@ -0,0 +1,199 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 扫一扫接入管理
* Class Scan
* @package WeChat
*/
class Scan extends BasicWeChat
{
/**
* 获取商户信息
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getMerchantInfo()
{
$url = "https://api.weixin.qq.com/scan/merchantinfo/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 创建商品
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addProduct(array $data)
{
$url = "https://api.weixin.qq.com/scan/product/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 商品发布
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @param string $status 设置发布状态。on为提交审核off为取消发布
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function modProduct($keystandard, $keystr, $status = 'on')
{
$data = ['keystandard' => $keystandard, 'keystr' => $keystr, 'status' => $status];
$url = "https://api.weixin.qq.com/scan/product/modstatus?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 设置测试人员白名单
* @param array $openids 测试人员的openid列表
* @param array $usernames 测试人员的微信号列表
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setTestWhiteList($openids = [], $usernames = [])
{
$data = ['openid' => $openids, 'username' => $usernames];
$url = "https://api.weixin.qq.com/scan/product/modstatus?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 获取商品二维码
* @param string $keystandard
* @param string $keystr
* @param null|string $extinfo
* @param integer $qrcode_size
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getQrc($keystandard, $keystr, $extinfo = null, $qrcode_size = 64)
{
$data = ['keystandard' => $keystandard, 'keystr' => $keystr, 'qrcode_size' => $qrcode_size];
is_null($extinfo) || $data['extinfo'] = $extinfo;
$url = "https://api.weixin.qq.com/scan/product/getqrcode?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询商品信息
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getProductInfo($keystandard, $keystr)
{
$url = "https://api.weixin.qq.com/scan/product/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['keystandard' => $keystandard, 'keystr' => $keystr]);
}
/**
* 批量查询商品信息
* @param integer $offset 批量查询的起始位置从0开始包含该起始位置。
* @param integer $limit 批量查询的数量。
* @param string $status 支持按状态拉取。on为发布状态off为未发布状态check为审核中状态reject为审核未通过状态all为所有状态。
* @param string $keystr 支持按部分编码内容拉取。填写该参数后,可将编码内容中包含所传参数的商品信息拉出。类似关键词搜索。
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getProductList($offset = 1, $limit = 10, $status = null, $keystr = null)
{
$data = ['offset' => $offset, 'limit' => $limit];
is_null($status) || $data['status'] = $status;
is_null($keystr) || $data['keystr'] = $keystr;
$url = "https://api.weixin.qq.com/scan/product/getlist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 更新商品信息
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateProduct(array $data)
{
$url = "https://api.weixin.qq.com/scan/product/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 清除商品信息
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function clearProduct($keystandard, $keystr)
{
$url = "https://api.weixin.qq.com/scan/product/clear?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['keystandard' => $keystandard, 'keystr' => $keystr]);
}
/**
* 检查wxticket参数
* @param string $ticket
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function checkTicket($ticket)
{
$url = "https://api.weixin.qq.com/scan/scanticket/check?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['ticket' => $ticket]);
}
/**
* 清除扫码记录
* @param string $keystandard 商品编码标准
* @param string $keystr 商品编码内容
* @param string $extinfo 调用“获取商品二维码接口”时传入的extinfo为标识参数
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function clearScanTicket($keystandard, $keystr, $extinfo)
{
$url = "https://api.weixin.qq.com/scan/scanticket/check?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['keystandard' => $keystandard, 'keystr' => $keystr, 'extinfo' => $extinfo]);
}
}

View File

@ -0,0 +1,113 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
use WeChat\Contracts\Tools;
use WeChat\Exceptions\InvalidResponseException;
/**
* 微信前端支持
* Class Script
* @package WeChat
*/
class Script extends BasicWeChat
{
/**
* 删除JSAPI授权TICKET
* @param string $type TICKET类型(wx_card|jsapi)
* @param string $appid 强制指定有效APPID
* @return void
*/
public function delTicket($type = 'jsapi', $appid = null)
{
is_null($appid) && $appid = $this->config->get('appid');
$cache_name = "{$appid}_ticket_{$type}";
Tools::delCache($cache_name);
}
/**
* 获取JSAPI_TICKET接口
* @param string $type TICKET类型(wx_card|jsapi)
* @param string $appid 强制指定有效APPID
* @return string
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getTicket($type = 'jsapi', $appid = null)
{
is_null($appid) && $appid = $this->config->get('appid');
$cache_name = "{$appid}_ticket_{$type}";
$ticket = Tools::getCache($cache_name);
if (empty($ticket)) {
$url = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=ACCESS_TOKEN&type={$type}";
$this->registerApi($url, __FUNCTION__, func_get_args());
$result = $this->httpGetForJson($url);
if (empty($result['ticket'])) {
throw new InvalidResponseException('Invalid Resoponse Ticket.', '0');
}
$ticket = $result['ticket'];
Tools::setCache($cache_name, $ticket, 5000);
}
return $ticket;
}
/**
* 获取JsApi使用签名
* @param string $url 网页的URL
* @param string $appid 用于多个appid时使用(可空)
* @param string $ticket 强制指定ticket
* @return array
* @throws Exceptions\LocalCacheException
* @throws InvalidResponseException
*/
public function getJsSign($url, $appid = null, $ticket = null)
{
list($url,) = explode('#', $url);
is_null($ticket) && $ticket = $this->getTicket('jsapi');
is_null($appid) && $appid = $this->config->get('appid');
$data = ["url" => $url, "timestamp" => '' . time(), "jsapi_ticket" => $ticket, "noncestr" => Tools::createNoncestr(16)];
return [
'debug' => false,
"appId" => $appid,
"nonceStr" => $data['noncestr'],
"timestamp" => $data['timestamp'],
"signature" => $this->getSignature($data, 'sha1'),
'jsApiList' => [
'updateAppMessageShareData', 'updateTimelineShareData', 'onMenuShareTimeline', 'onMenuShareAppMessage', 'onMenuShareQQ', 'onMenuShareWeibo', 'onMenuShareQZone',
'startRecord', 'stopRecord', 'onVoiceRecordEnd', 'playVoice', 'pauseVoice', 'stopVoice', 'onVoicePlayEnd', 'uploadVoice', 'downloadVoice',
'chooseImage', 'previewImage', 'uploadImage', 'downloadImage', 'translateVoice', 'getNetworkType', 'openLocation', 'getLocation',
'hideOptionMenu', 'showOptionMenu', 'hideMenuItems', 'showMenuItems', 'hideAllNonBaseMenuItem', 'showAllNonBaseMenuItem',
'closeWindow', 'scanQRCode', 'chooseWXPay', 'openProductSpecificView', 'addCard', 'chooseCard', 'openCard',
],
];
}
/**
* 数据生成签名
* @param array $data 签名数组
* @param string $method 签名方法
* @param array $params 签名参数
* @return bool|string 签名值
*/
protected function getSignature($data, $method = "sha1", $params = [])
{
ksort($data);
if (!function_exists($method)) return false;
foreach ($data as $k => $v) array_push($params, "{$k}={$v}");
return $method(join('&', $params));
}
}

View File

@ -0,0 +1,364 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\Tools;
use WeChat\Contracts\BasicWeChat;
/**
* 揺一揺周边
* Class Shake
* @package WeChat
*/
class Shake extends BasicWeChat
{
/**
* 申请开通功能
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function register(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/account/register?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询审核状态
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function auditStatus()
{
$url = "https://api.weixin.qq.com/shakearound/account/auditstatus?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 申请设备ID
* @param string $quantity 申请的设备ID的数量单次新增设备超过500个需走人工审核流程
* @param string $apply_reason 申请理由不超过100个汉字或200个英文字母
* @param null|string $comment 备注不超过15个汉字或30个英文字母
* @param null|string $poi_id 设备关联的门店ID关联门店后在门店1KM的范围内有优先摇出信息的机会。
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function createApply($quantity, $apply_reason, $comment = null, $poi_id = null)
{
$data = ['quantity' => $quantity, 'apply_reason' => $apply_reason];
is_null($poi_id) || $data['poi_id'] = $poi_id;
is_null($comment) || $data['comment'] = $comment;
$url = "https://api.weixin.qq.com/shakearound/device/applyid?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询设备ID申请审核状态
* @param integer $applyId 批次ID申请设备ID时所返回的批次ID
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getApplyStatus($applyId)
{
$url = "https://api.weixin.qq.com/shakearound/device/applyid?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['apply_id' => $applyId]);
}
/**
* 编辑设备信息
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateApply(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/device/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 配置设备与门店的关联关系
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function bindLocation(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/device/bindlocation?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询设备列表
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function search(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/device/search?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 页面管理
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function createPage(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/page/add?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 编辑页面信息
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updatePage(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/page/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询页面列表
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function searchPage(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/page/search?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 删除页面
* @param integer page_id 指定页面的id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function deletePage($page_id)
{
$url = "https://api.weixin.qq.com/shakearound/page/delete?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['page_id' => $page_id]);
}
/**
* 上传图片素材
* @param string $filename 图片名字
* @param string $type Icon摇一摇页面展示的icon图License申请开通摇一摇周边功能时需上传的资质文件若不传type则默认type=icon
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function upload($filename, $type = 'icon')
{
$url = "https://api.weixin.qq.com/shakearound/material/add?access_token=ACCESS_TOKEN&type={$type}";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['media' => Tools::createCurlFile($filename)]);
}
/**
* 配置设备与页面的关联关系
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function bindPage(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/device/bindpage?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询设备与页面的关联关系
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function queryPage(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/relation/search?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 以设备为维度的数据统计接口
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function totalDevice(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/statistics/device?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 批量查询设备统计数据接口
* @param integer $date 指定查询日期时间戳,单位为秒
* @param integer $page_index 指定查询的结果页序号返回结果按摇周边人数降序排序每50条记录为一页
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function totalDeviceList($date, $page_index = 1)
{
$url = "https://api.weixin.qq.com/shakearound/statistics/devicelist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['date' => $date, 'page_index' => $page_index]);
}
/**
* 以页面为维度的数据统计接口
* @param integer $page_id 指定页面的设备ID
* @param integer $begin_date 起始日期时间戳最长时间跨度为30天单位为秒
* @param integer $end_date 结束日期时间戳最长时间跨度为30天单位为秒
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function totalPage($page_id, $begin_date, $end_date)
{
$url = "https://api.weixin.qq.com/shakearound/statistics/page?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['page_id' => $page_id, 'begin_date' => $begin_date, 'end_date' => $end_date]);
}
/**
* 编辑分组信息
* @param integer $group_id 分组唯一标识,全局唯一
* @param string $group_name 分组名称不超过100汉字或200个英文字母
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateGroup($group_id, $group_name)
{
$url = "https://api.weixin.qq.com/shakearound/device/group/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['group_id' => $group_id, 'group_name' => $group_name]);
}
/**
* 删除分组
* @param integer $group_id 分组唯一标识,全局唯一
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function deleteGroup($group_id)
{
$url = "https://api.weixin.qq.com/shakearound/device/group/delete?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['group_id' => $group_id]);
}
/**
* 查询分组列表
* @param integer $begin 分组列表的起始索引值
* @param integer $count 待查询的分组数量不能超过1000个
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getGroupList($begin = 0, $count = 10)
{
$url = "https://api.weixin.qq.com/shakearound/device/group/getlist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['begin' => $begin, 'count' => $count]);
}
/**
* 查询分组详情
* @param integer $group_id 分组唯一标识,全局唯一
* @param integer $begin 分组里设备的起始索引值
* @param integer $count 待查询的分组里设备的数量不能超过1000个
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getGroupDetail($group_id, $begin = 0, $count = 100)
{
$url = "https://api.weixin.qq.com/shakearound/device/group/getdetail?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['group_id' => $group_id, 'begin' => $begin, 'count' => $count]);
}
/**
* 添加设备到分组
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addDeviceGroup(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/device/group/adddevice?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 从分组中移除设备
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function deleteDeviceGroup(array $data)
{
$url = "https://api.weixin.qq.com/shakearound/device/group/deletedevice?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
}

View File

@ -0,0 +1,124 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 用户标签管理
* Class Tags
* @package WeChat
*/
class Tags extends BasicWeChat
{
/**
* 获取粉丝标签列表
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getTags()
{
$url = "https://api.weixin.qq.com/cgi-bin/tags/get?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 创建粉丝标签
* @param string $name
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function createTags($name)
{
$url = "https://api.weixin.qq.com/cgi-bin/tags/create?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['tag' => ['name' => $name]]);
}
/**
* 更新粉丝标签
* @param integer $id 标签ID
* @param string $name 标签名称
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function updateTags($id, $name)
{
$url = "https://api.weixin.qq.com/cgi-bin/tags/update?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['tag' => ['name' => $name, 'id' => $id]]);
}
/**
* 删除粉丝标签
* @param int $tagId
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function deleteTags($tagId)
{
$url = 'https://api.weixin.qq.com/cgi-bin/tags/delete?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['tag' => ['id' => $tagId]]);
}
/**
* 批量为用户打标签
* @param array $openids
* @param integer $tagId
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function batchTagging(array $openids, $tagId)
{
$url = 'https://api.weixin.qq.com/cgi-bin/tags/members/batchtagging?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['openid_list' => $openids, 'tagid' => $tagId]);
}
/**
* 批量为用户取消标签
* @param array $openids
* @param integer $tagId
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function batchUntagging(array $openids, $tagId)
{
$url = 'https://api.weixin.qq.com/cgi-bin/tags/members/batchuntagging?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['openid_list' => $openids, 'tagid' => $tagId]);
}
/**
* 获取用户身上的标签列表
* @param string $openid
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getUserTagId($openid)
{
$url = 'https://api.weixin.qq.com/cgi-bin/tags/getidlist?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['openid' => $openid]);
}
}

View File

@ -0,0 +1,110 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 模板消息
* Class Template
* @package WeChat
*/
class Template extends BasicWeChat
{
/**
* 设置所属行业
* @param string $industry_id1 公众号模板消息所属行业编号
* @param string $industry_id2 公众号模板消息所属行业编号
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setIndustry($industry_id1, $industry_id2)
{
$url = "https://api.weixin.qq.com/cgi-bin/template/api_set_industry?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['industry_id1' => $industry_id1, 'industry_id2' => $industry_id2]);
}
/**
* 获取设置的行业信息
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getIndustry()
{
$url = "https://api.weixin.qq.com/cgi-bin/template/get_industry?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 获得模板ID
* @param string $tpl_id 板库中模板的编号有“TM**”和“OPENTMTM**”等形式
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addTemplate($tpl_id)
{
$url = "https://api.weixin.qq.com/cgi-bin/template/api_add_template?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['template_id_short' => $tpl_id]);
}
/**
* 获取模板列表
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getAllPrivateTemplate()
{
$url = "https://api.weixin.qq.com/cgi-bin/template/get_all_private_template?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 删除模板ID
* @param string $tpl_id 公众帐号下模板消息ID
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function delPrivateTemplate($tpl_id)
{
$url = "https://api.weixin.qq.com/cgi-bin/template/del_private_template?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['template_id' => $tpl_id]);
}
/**
* 发送模板消息
* @param array $data
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function send(array $data)
{
$url = "https://api.weixin.qq.com/cgi-bin/message/template/send?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
}

View File

@ -0,0 +1,147 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 微信粉丝管理
* Class User
* @package WeChat
*/
class User extends BasicWeChat
{
/**
* 设置用户备注名
* @param string $openid
* @param string $remark
* @return array
* @throws Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function updateMark($openid, $remark)
{
$url = 'https://api.weixin.qq.com/cgi-bin/user/info/updateremark?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['openid' => $openid, 'remark' => $remark]);
}
/**
* 获取用户基本信息包括UnionID机制
* @param string $openid
* @param string $lang
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getUserInfo($openid, $lang = 'zh_CN')
{
$url = "https://api.weixin.qq.com/cgi-bin/user/info?access_token=ACCESS_TOKEN&openid={$openid}&lang={$lang}";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 批量获取用户基本信息
* @param array $openids
* @param string $lang
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getBatchUserInfo(array $openids, $lang = 'zh_CN')
{
$url = 'https://api.weixin.qq.com/cgi-bin/user/info/batchget?access_token=ACCESS_TOKEN';
$data = ['user_list' => []];
foreach ($openids as $openid) {
$data['user_list'][] = ['openid' => $openid, 'lang' => $lang];
}
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 获取用户列表
* @param string $next_openid
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getUserList($next_openid = '')
{
$url = "https://api.weixin.qq.com/cgi-bin/user/get?access_token=ACCESS_TOKEN&next_openid={$next_openid}";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpGetForJson($url);
}
/**
* 获取标签下粉丝列表
* @param integer $tagid 标签ID
* @param string $next_openid 第一个拉取的OPENID
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getUserListByTag($tagid, $next_openid = '')
{
$url = 'https://api.weixin.qq.com/cgi-bin/user/tag/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['tagid' => $tagid, 'next_openid' => $next_openid]);
}
/**
* 获取公众号的黑名单列表
* @param string $begin_openid
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getBlackList($begin_openid = '')
{
$url = "https://api.weixin.qq.com/cgi-bin/tags/members/getblacklist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['begin_openid' => $begin_openid]);
}
/**
* 批量拉黑用户
* @param array $openids
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function batchBlackList(array $openids)
{
$url = "https://api.weixin.qq.com/cgi-bin/tags/members/batchblacklist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['openid_list' => $openids]);
}
/**
* 批量取消拉黑用户
* @param array $openids
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function batchUnblackList(array $openids)
{
$url = "https://api.weixin.qq.com/cgi-bin/tags/members/batchunblacklist?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['openid_list' => $openids]);
}
}

View File

@ -0,0 +1,284 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeChat;
use WeChat\Contracts\BasicWeChat;
/**
* 门店 WIFI 管理
* Class Wifi
* @package WeChat
*/
class Wifi extends BasicWeChat
{
/**
* 获取 Wi-Fi 门店列表
* @param integer $pageindex 分页下标默认从1开始
* @param integer $pagesize 每页的个数默认10个最大20个
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getShopList($pageindex = 1, $pagesize = 2)
{
$url = 'https://api.weixin.qq.com/bizwifi/shop/list?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['pageindex' => $pageindex, 'pagesize' => $pagesize]);
}
/**
* 查询门店Wi-Fi信息
* @param integer $shop_id 门店ID
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getShopWifi($shop_id)
{
$url = 'https://api.weixin.qq.com/bizwifi/shop/list?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id]);
}
/**
* 修改门店网络信息
* @param integer $shop_id 门店ID
* @param string $old_ssid 旧的无线网络设备的ssid
* @param string $ssid 新的无线网络设备的ssid
* @param string $password 无线网络设备的密码(可选)
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function upShopWifi($shop_id, $old_ssid, $ssid, $password = null)
{
$data = ['shop_id' => $shop_id, 'old_ssid' => $old_ssid, 'ssid' => $ssid];
is_null($password) || $data['password'] = $password;
$url = 'https://api.weixin.qq.com/bizwifi/shop/update?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 清空门店网络及设备
* @param integer $shop_id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function clearShopWifi($shop_id)
{
$url = 'https://api.weixin.qq.com/bizwifi/shop/clean?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id]);
}
/**
* 添加密码型设备
* @param integer $shop_id 门店ID
* @param string $ssid 无线网络设备的ssid
* @param null|string $password 无线网络设备的密码
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addShopWifi($shop_id, $ssid, $password = null)
{
$data = ['shop_id' => $shop_id, 'ssid' => $ssid, 'password' => $password];
$url = 'https://api.weixin.qq.com/bizwifi/device/add?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 添加portal型设备
* @param integer $shop_id 门店ID
* @param string $ssid 无线网络设备的ssid
* @param bool $reset 重置secretkeyfalse-不重置true-重置默认为false
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function addShopPortal($shop_id, $ssid, $reset = false)
{
$data = ['shop_id' => $shop_id, 'ssid' => $ssid, 'reset' => $reset];
$url = 'https://api.weixin.qq.com/bizwifi/apportal/register?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询设备
* @param null|integer $shop_id 根据门店id查询
* @param null|integer $pageindex 分页下标默认从1开始
* @param null|integer $pagesize 每页的个数默认10个最大20个
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function queryShopWifi($shop_id = null, $pageindex = null, $pagesize = null)
{
$data = [];
is_null($pagesize) || $data['pagesize'] = $pagesize;
is_null($pageindex) || $data['pageindex'] = $pageindex;
is_null($shop_id) || $data['shop_id'] = $shop_id;
$url = 'https://api.weixin.qq.com/bizwifi/device/list?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 删除设备
* @param string $bssid 需要删除的无线网络设备无线mac地址格式冒号分隔字符长度17个并且字母小写例如00:1f:7a:ad:5c:a8
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function delShopWifi($bssid)
{
$url = 'https://api.weixin.qq.com/bizwifi/device/delete?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['bssid' => $bssid]);
}
/**
* 获取物料二维码
* @param integer $shop_id 门店ID
* @param string $ssid 已添加到门店下的无线网络名称
* @param integer $img_id 物料样式编号0-纯二维码可用于自由设计宣传材料1-二维码物料155mm×215mm(宽×高),可直接张贴
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getQrc($shop_id, $ssid, $img_id = 1)
{
$url = 'https://api.weixin.qq.com/bizwifi/qrcode/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id, 'ssid' => $ssid, 'img_id' => $img_id]);
}
/**
* 设置商家主页
* @param integer $shop_id 门店ID
* @param integer $template_id 模板ID0-默认模板1-自定义url
* @param null|string $url 自定义链接当template_id为1时必填
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setHomePage($shop_id, $template_id, $url = null)
{
$data = ['shop_id' => $shop_id, 'template_id' => $template_id];
is_null($url) && $data['struct'] = ['url' => $url];
$url = 'https://api.weixin.qq.com/bizwifi/homepage/set?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询商家主页
* @param integer $shop_id 查询的门店id
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getHomePage($shop_id)
{
$url = 'https://api.weixin.qq.com/bizwifi/homepage/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id]);
}
/**
* 设置微信首页欢迎语
* @param integer $shop_id 门店ID
* @param integer $bar_type 微信首页欢迎语的文本内容0--欢迎光临+公众号名称1--欢迎光临+门店名称2--已连接+公众号名称+WiFi3--已连接+门店名称+Wi-Fi。
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setBar($shop_id, $bar_type = 1)
{
$url = 'https://api.weixin.qq.com/bizwifi/bar/set?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id, 'bar_type' => $bar_type]);
}
/**
* 设置连网完成页
* @param integer $shop_id 门店ID
* @param string $finishpage_url 连网完成页URL
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setFinishPage($shop_id, $finishpage_url)
{
$url = 'https://api.weixin.qq.com/bizwifi/finishpage/set?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id, 'finishpage_url' => $finishpage_url]);
}
/**
* Wi-Fi 数据统计
* @param string $begin_date 起始日期时间格式yyyy-mm-dd最长时间跨度为30天
* @param string $end_date 结束日期时间戳格式yyyy-mm-dd最长时间跨度为30天
* @param integer $shop_id 按门店ID搜索-1为总统计
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function staticList($begin_date, $end_date, $shop_id = -1)
{
$url = 'https://api.weixin.qq.com/bizwifi/statistics/list?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id, 'begin_date' => $begin_date, 'end_date' => $end_date]);
}
/**
* 设置门店卡券投放信息
* @param integer $shop_id 门店ID可设置为0表示所有门店
* @param integer $card_id 卡券ID
* @param string $card_describe 卡券描述不能超过18个字符
* @param string $start_time 卡券投放开始时间(单位是秒)
* @param string $end_time 卡券投放结束时间(单位是秒) 注:不能超过卡券的有效期时间
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function setCouponput($shop_id, $card_id, $card_describe, $start_time, $end_time)
{
$data = ['shop_id' => $shop_id, 'card_id' => $card_id, 'card_describe' => $card_describe, 'start_time' => $start_time, 'end_time' => $end_time];
$url = 'https://api.weixin.qq.com/bizwifi/couponput/set?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, $data);
}
/**
* 查询门店卡券投放信息
* @param integer $shop_id 门店ID可设置为0表示所有门店
* @return array
* @throws Exceptions\InvalidResponseException
* @throws Exceptions\LocalCacheException
*/
public function getCouponput($shop_id)
{
$url = 'https://api.weixin.qq.com/bizwifi/couponput/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->httpPostForJson($url, ['shop_id' => $shop_id]);
}
}

View File

@ -0,0 +1,105 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
use WeChat\Contracts\Tools;
use WeChat\Exceptions\InvalidDecryptException;
use WeChat\Exceptions\InvalidResponseException;
/**
* 数据加密处理
* Class Crypt
* @package WeMini
*/
class Crypt extends BasicWeChat
{
/**
* 数据签名校验
* @param string $iv
* @param string $sessionKey
* @param string $encryptedData
* @return bool
*/
public function decode($iv, $sessionKey, $encryptedData)
{
require_once __DIR__ . DIRECTORY_SEPARATOR . 'crypt' . DIRECTORY_SEPARATOR . 'wxBizDataCrypt.php';
$pc = new \WXBizDataCrypt($this->config->get('appid'), $sessionKey);
$errCode = $pc->decryptData($encryptedData, $iv, $data);
if ($errCode == 0) {
return json_decode($data, true);
}
return false;
}
/**
* 登录凭证校验
* @param string $code 登录时获取的 code
* @return array
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function session($code)
{
$appid = $this->config->get('appid');
$secret = $this->config->get('appsecret');
$url = "https://api.weixin.qq.com/sns/jscode2session?appid={$appid}&secret={$secret}&js_code={$code}&grant_type=authorization_code";
return json_decode(Tools::get($url), true);
}
/**
* 换取用户信息
* @param string $code 用户登录凭证(有效期五分钟)
* @param string $iv 加密算法的初始向量
* @param string $encryptedData 加密数据( encryptedData )
* @return array
* @throws InvalidDecryptException
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function userInfo($code, $iv, $encryptedData)
{
$result = $this->session($code);
if (empty($result['session_key'])) {
throw new InvalidResponseException('Code 换取 SessionKey 失败', 403);
}
$userinfo = $this->decode($iv, $result['session_key'], $encryptedData);
if (empty($userinfo)) {
throw new InvalidDecryptException('用户信息解析失败', 403);
}
return array_merge($result, $userinfo);
}
/**
* 用户支付完成后,获取该用户的 UnionId
* @param string $openid 支付用户唯一标识
* @param null|string $transaction_id 微信支付订单号
* @param null|string $mch_id 微信支付分配的商户号,和商户订单号配合使用
* @param null|string $out_trade_no 微信支付商户订单号,和商户号配合使用
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getPaidUnionId($openid, $transaction_id = null, $mch_id = null, $out_trade_no = null)
{
$url = "https://api.weixin.qq.com/wxa/getpaidunionid?access_token=ACCESS_TOKEN&openid={$openid}";
if (is_null($mch_id)) $url .= "&mch_id={$mch_id}";
if (is_null($out_trade_no)) $url .= "&out_trade_no={$out_trade_no}";
if (is_null($transaction_id)) $url .= "&transaction_id={$transaction_id}";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callGetApi($url);
}
}

View File

@ -0,0 +1,181 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 小程序即时配送
* Class Delivery
* @package WeMini
*/
class Delivery extends BasicWeChat
{
/**
* 异常件退回商家商家确认收货接口
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function abnormalConfirm($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/confirm_return?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 下配送单接口
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function addOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/add?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 可以对待接单状态的订单增加小费
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function addTip($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/addtips?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 取消配送单接口
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function cancelOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/cancel?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 获取已支持的配送公司列表接口
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getAllImmeDelivery($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/delivery/getall?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 拉取已绑定账号
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getBindAccount($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/shop/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 拉取配送单信息
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 模拟配送公司更新配送单状态
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function mockUpdateOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/test_update_order?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 预下配送单接口
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function preAddOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/pre_add?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 预取消配送单接口
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function preCancelOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/precancel?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 重新下单
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function reOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/local/business/order/readd?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
}

View File

@ -0,0 +1,72 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
use WeChat\Exceptions\InvalidResponseException;
/**
* 小程序图像处理
* Class Image
* @package WeMini
*/
class Image extends BasicWeChat
{
/**
* 本接口提供基于小程序的图片智能裁剪能力
* @param string $img_url 要检测的图片 url传这个则不用传 img 参数。
* @param string $img form-data 中媒体文件标识有filename、filelength、content-type等信息传这个则不用穿 img_url
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function aiCrop($img_url, $img)
{
$url = "https://api.weixin.qq.com/cv/img/aicrop?access_token=ACCESS_TOCKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['img_url' => $img_url, 'img' => $img], true);
}
/**
* 本接口提供基于小程序的条码/二维码识别的API
* @param string $img_url 要检测的图片 url传这个则不用传 img 参数。
* @param string $img form-data 中媒体文件标识有filename、filelength、content-type等信息传这个则不用穿 img_url
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function scanQRCode($img_url, $img)
{
$url = "https://api.weixin.qq.com/cv/img/qrcode?img_url=ENCODE_URL&access_token=ACCESS_TOCKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['img_url' => $img_url, 'img' => $img], true);
}
/**
* 本接口提供基于小程序的图片高清化能力
* @param string $img_url 要检测的图片 url传这个则不用传 img 参数
* @param string $img form-data 中媒体文件标识有filename、filelength、content-type等信息传这个则不用穿 img_url
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function superresolution($img_url, $img)
{
$url = "https://api.weixin.qq.com/cv/img/qrcode?img_url=ENCODE_URL&access_token=ACCESS_TOCKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['img_url' => $img_url, 'img' => $img], true);
}
}

View File

@ -0,0 +1,206 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 小程序物流助手
* Class Logistics
* @package WeMini
*/
class Logistics extends BasicWeChat
{
/**
* 生成运单
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function addOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/order/add?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 取消运单
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function cancelOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/order/cancel?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 获取支持的快递公司列表
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getAllDelivery()
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/delivery/getall?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callGetApi($url);
}
/**
* 获取运单数据
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/order/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 查询运单轨迹
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getPath($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/path/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 获取打印员。若需要使用微信打单 PC 软件,才需要调用
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getPrinter()
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/printer/getall?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callGetApi($url);
}
/**
* 获取电子面单余额。仅在使用加盟类快递公司时,才可以调用
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getQuota($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/path/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 模拟快递公司更新订单状态, 该接口只能用户测试
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function testUpdateOrder($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/test_update_order?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 配置面单打印员,若需要使用微信打单 PC 软件,才需要调用
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function updatePrinter($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/business/printer/update?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 获取面单联系人信息
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getContact($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/delivery/contact/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 预览面单模板。用于调试面单模板使用
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function previewTemplate($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/delivery/template/preview?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 更新商户审核结果
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function updateBusiness($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/delivery/service/business/update?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 更新运单轨迹
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function updatePath($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/express/delivery/path/update?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
}

View File

@ -0,0 +1,67 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 小程序动态消息
* Class Message
* @package WeMini
*/
class Message extends BasicWeChat
{
/**
* 动态消息,创建被分享动态消息的 activity_id
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function createActivityId($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/message/wxopen/activityid/create?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 动态消息,修改被分享的动态消息
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function setUpdatableMsg($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/message/wxopen/updatablemsg/send?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 下发小程序和公众号统一的服务消息
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function uniformSend($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/message/wxopen/template/uniform_send?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
}

View File

@ -0,0 +1,110 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 小程序ORC服务
* Class Ocr
* @package WeMini
*/
class Ocr extends BasicWeChat
{
/**
* 本接口提供基于小程序的银行卡 OCR 识别
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function bankcard($data)
{
$url = 'https://api.weixin.qq.com/cv/ocr/bankcard?access_token=ACCESS_TOCKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 本接口提供基于小程序的营业执照 OCR 识别
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function businessLicense($data)
{
$url = 'https://api.weixin.qq.com/cv/ocr/bizlicense?access_token=ACCESS_TOCKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 本接口提供基于小程序的驾驶证 OCR 识别
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function driverLicense($data)
{
$url = 'https://api.weixin.qq.com/cv/ocr/drivinglicense?access_token=ACCESS_TOCKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 本接口提供基于小程序的身份证 OCR 识别
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function idcard($data)
{
$url = 'https://api.weixin.qq.com/cv/ocr/idcard?access_token=ACCESS_TOCKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 本接口提供基于小程序的通用印刷体 OCR 识别
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function printedText($data)
{
$url = 'https://api.weixin.qq.com/cv/ocr/comm?access_token=ACCESS_TOCKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 本接口提供基于小程序的行驶证 OCR 识别
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function vehicleLicense($data)
{
$url = 'https://api.weixin.qq.com/cv/ocr/driving?access_token=ACCESS_TOCKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
}

View File

@ -0,0 +1,112 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 微信小程序插件管理
* Class Plugs
* @package WeMini
*/
class Plugs extends BasicWeChat
{
/**
* 1.申请使用插件
* @param string $plugin_appid 插件appid
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function apply($plugin_appid)
{
$url = 'https://api.weixin.qq.com/wxa/plugin?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['action' => 'apply', 'plugin_appid' => $plugin_appid], true);
}
/**
* 2.查询已添加的插件
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getList()
{
$url = 'https://api.weixin.qq.com/wxa/plugin?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['action' => 'list'], true);
}
/**
* 3.删除已添加的插件
* @param string $plugin_appid 插件appid
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function unbind($plugin_appid)
{
$url = 'https://api.weixin.qq.com/wxa/plugin?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['action' => 'unbind', 'plugin_appid' => $plugin_appid], true);
}
/**
* 获取当前所有插件使用方
* 修改插件使用申请的状态
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function devplugin($data)
{
$url = 'https://api.weixin.qq.com/wxa/devplugin?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
/**
* 4.获取当前所有插件使用方(供插件开发者调用)
* @param integer $page 拉取第page页的数据
* @param integer $num 表示每页num条记录
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function devApplyList($page = 1, $num = 10)
{
$url = 'https://api.weixin.qq.com/wxa/plugin?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
$data = ['action' => 'dev_apply_list', 'page' => $page, 'num' => $num];
return $this->callPostApi($url, $data, true);
}
/**
* 5.修改插件使用申请的状态(供插件开发者调用)
* @param string $action dev_agree同意申请dev_refuse拒绝申请dev_delete删除已拒绝的申请者
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function devAgree($action = 'dev_agree')
{
$url = 'https://api.weixin.qq.com/wxa/plugin?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['action' => $action], true);
}
}

View File

@ -0,0 +1,91 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 微信小程序地址管理
* Class Poi
* @package WeMini
*/
class Poi extends BasicWeChat
{
/**
* 添加地点
* @param string $related_name 经营资质主体
* @param string $related_credential 经营资质证件号
* @param string $related_address 经营资质地址
* @param string $related_proof_material 相关证明材料照片临时素材mediaid
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function addBearByPoi($related_name, $related_credential, $related_address, $related_proof_material)
{
$url = 'https://api.weixin.qq.com/wxa/addnearbypoi?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
$data = [
'related_name' => $related_name, 'related_credential' => $related_credential,
'related_address' => $related_address, 'related_proof_material' => $related_proof_material,
];
return $this->callPostApi($url, $data, true);
}
/**
* 查看地点列表
* @param integer $page 起始页id从1开始计数
* @param integer $page_rows 每页展示个数最多1000个
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getNearByPoiList($page = 1, $page_rows = 1000)
{
$url = "https://api.weixin.qq.com/wxa/getnearbypoilist?page={$page}&page_rows={$page_rows}&access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callGetApi($url);
}
/**
* 删除地点
* @param string $poi_id 附近地点ID
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function delNearByPoiList($poi_id)
{
$url = "https://api.weixin.qq.com/wxa/delnearbypoi?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['poi_id' => $poi_id], true);
}
/**
* 展示/取消展示附近小程序
* @param string $poi_id 附近地点ID
* @param string $status 0取消展示1展示
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function setNearByPoiShowStatus($poi_id, $status)
{
$url = "https://api.weixin.qq.com/wxa/setnearbypoishowstatus?access_token=ACCESS_TOKEN";
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['poi_id' => $poi_id, 'status' => $status], true);
}
}

View File

@ -0,0 +1,112 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
use WeChat\Contracts\Tools;
/**
* 微信小程序二维码管理
* Class Qrcode
* @package WeMini
*/
class Qrcode extends BasicWeChat
{
/**
* 获取小程序码(永久有效)
* 接口A: 适用于需要的码数量较少的业务场景
* @param string $path 不能为空,最大长度 128 字节
* @param integer $width 二维码的宽度
* @param bool $auto_color 自动配置线条颜色,如果颜色依然是黑色,则说明不建议配置主色调
* @param array $line_color auto_color false 时生效
* @param boolean $is_hyaline 是否需要透明底色
* @param null|string $outType 输出类型
* @return array|string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function createMiniPath($path, $width = 430, $auto_color = false, $line_color = ["r" => "0", "g" => "0", "b" => "0"], $is_hyaline = true, $outType = null)
{
$url = 'https://api.weixin.qq.com/wxa/getwxacode?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
$data = ['path' => $path, 'width' => $width, 'auto_color' => $auto_color, 'line_color' => $line_color, 'is_hyaline' => $is_hyaline];
$result = Tools::post($url, Tools::arr2json($data));
if (is_array($json = json_decode($result, true))) {
if (!$this->isTry && isset($json['errcode']) && in_array($json['errcode'], ['40014', '40001', '41001', '42001'])) {
[$this->delAccessToken(), $this->isTry = true];
return call_user_func_array([$this, $this->currentMethod['method']], $this->currentMethod['arguments']);
}
return Tools::json2arr($result);
}
return is_null($outType) ? $result : $outType($result);
}
/**
* 获取小程序码(永久有效)
* 接口B适用于需要的码数量极多的业务场景
* @param string $scene 最大32个可见字符只支持数字
* @param string $page 必须是已经发布的小程序存在的页面
* @param integer $width 二维码的宽度
* @param bool $auto_color 自动配置线条颜色,如果颜色依然是黑色,则说明不建议配置主色调
* @param array $line_color auto_color false 时生效
* @param boolean $is_hyaline 是否需要透明底色
* @param null|string $outType 输出类型
* @return array|string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function createMiniScene($scene, $page, $width = 430, $auto_color = false, $line_color = ["r" => "0", "g" => "0", "b" => "0"], $is_hyaline = true, $outType = null)
{
$url = 'https://api.weixin.qq.com/wxa/getwxacodeunlimit?access_token=ACCESS_TOKEN';
$data = ['scene' => $scene, 'width' => $width, 'auto_color' => $auto_color, 'page' => $page, 'line_color' => $line_color, 'is_hyaline' => $is_hyaline];
$this->registerApi($url, __FUNCTION__, func_get_args());
$result = Tools::post($url, Tools::arr2json($data));
if (is_array($json = json_decode($result, true))) {
if (!$this->isTry && isset($json['errcode']) && in_array($json['errcode'], ['40014', '40001', '41001', '42001'])) {
[$this->delAccessToken(), $this->isTry = true];
return call_user_func_array([$this, $this->currentMethod['method']], $this->currentMethod['arguments']);
}
return Tools::json2arr($result);
}
return is_null($outType) ? $result : $outType($result);
}
/**
* 获取小程序二维码(永久有效)
* 接口C适用于需要的码数量较少的业务场景
* @param string $path 不能为空,最大长度 128 字节
* @param integer $width 二维码的宽度
* @param null|string $outType 输出类型
* @return array|string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function createDefault($path, $width = 430, $outType = null)
{
$url = 'https://api.weixin.qq.com/cgi-bin/wxaapp/createwxaqrcode?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
$result = Tools::post($url, Tools::arr2json(['path' => $path, 'width' => $width]));
if (is_array($json = json_decode($result, true))) {
if (!$this->isTry && isset($json['errcode']) && in_array($json['errcode'], ['40014', '40001', '41001', '42001'])) {
[$this->delAccessToken(), $this->isTry = true];
return call_user_func_array([$this, $this->currentMethod['method']], $this->currentMethod['arguments']);
}
return Tools::json2arr($result);
}
return is_null($outType) ? $result : $outType($result);
}
}

View File

@ -0,0 +1,70 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
use WeChat\Exceptions\InvalidResponseException;
/**
* 小程序内容安全
* Class Security
* @package WeMini
*/
class Security extends BasicWeChat
{
/**
* 校验一张图片是否含有违法违规内容
* @param string $media 要检测的图片文件格式支持PNG、JPEG、JPG、GIF图片尺寸不超过 750px x 1334px
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function imgSecCheck($media)
{
$url = 'https://api.weixin.qq.com/wxa/img_sec_check?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['media' => $media], true);
}
/**
* 异步校验图片/音频是否含有违法违规内容
* @param string $media_url
* @param string $media_type
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function mediaCheckAsync($media_url, $media_type)
{
$url = 'https://api.weixin.qq.com/wxa/media_check_async?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['media_url' => $media_url, 'media_type' => $media_type], true);
}
/**
* 检查一段文本是否含有违法违规内容
* @param string $content
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function msgSecCheck($content)
{
$url = 'https://api.weixin.qq.com/wxa/msg_sec_check?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['content' => $content], true);
}
}

View File

@ -0,0 +1,40 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 小程序生物认证
* Class Soter
* @package WeMini
*/
class Soter extends BasicWeChat
{
/**
* SOTER 生物认证秘钥签名验证
* @param array $data
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function verifySignature($data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/soter/verify_signature?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
}

View File

@ -0,0 +1,110 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 公众号小程序模板消息支持
* Class Mini
* @package WeChat
*/
class Template extends BasicWeChat
{
/**
* 获取小程序模板库标题列表
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getTemplateLibraryList()
{
$url = 'https://api.weixin.qq.com/cgi-bin/wxopen/template/library/list?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['offset' => '0', 'count' => '20'], true);
}
/**
* 获取模板库某个模板标题下关键词库
* @param string $template_id 模板标题id可通过接口获取也可登录小程序后台查看获取
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getTemplateLibrary($template_id)
{
$url = 'https://api.weixin.qq.com/cgi-bin/wxopen/template/library/get?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['id' => $template_id], true);
}
/**
* 组合模板并添加至帐号下的个人模板库
* @param string $template_id 模板标题id可通过接口获取也可登录小程序后台查看获取
* @param array $keyword_id_list 开发者自行组合好的模板关键词列表,关键词顺序可以自由搭配(例如[3,5,4][4,5,3]最多支持10个关键词组合
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function addTemplate($template_id, array $keyword_id_list)
{
$url = 'https://api.weixin.qq.com/cgi-bin/wxopen/template/add?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['id' => $template_id, 'keyword_id_list' => $keyword_id_list], true);
}
/**
* 获取帐号下已存在的模板列表
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getTemplateList()
{
$url = 'https://api.weixin.qq.com/cgi-bin/wxopen/template/list?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['offset' => '0', 'count' => '20'], true);
}
/**
* 删除模板消息
* @param string $template_id 要删除的模板id
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function delTemplate($template_id)
{
$url = 'https://api.weixin.qq.com/cgi-bin/wxopen/template/del?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['template_id' => $template_id], true);
}
/**
* 发送模板消息
* @param array $data 发送的消息对象数组
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function send(array $data)
{
$url = 'https://api.weixin.qq.com/cgi-bin/message/wxopen/template/send?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, $data, true);
}
}

View File

@ -0,0 +1,176 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WeMini;
use WeChat\Contracts\BasicWeChat;
/**
* 微信小程序数据接口
* Class Total
* @package WeMini
*/
class Total extends BasicWeChat
{
/**
* 数据分析接口
* @param string $begin_date 开始日期
* @param string $end_date 结束日期限定查询1天数据end_date允许设置的最大值为昨日
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidDailySummarytrend($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappiddailysummarytrend?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 访问分析
* @param string $begin_date 开始日期
* @param string $end_date 结束日期限定查询1天数据end_date允许设置的最大值为昨日
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidDailyVisittrend($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappiddailyvisittrend?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 周趋势
* @param string $begin_date 开始日期,为周一日期
* @param string $end_date 结束日期,为周日日期,限定查询一周数据
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidWeeklyVisittrend($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappidweeklyvisittrend?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 月趋势
* @param string $begin_date 开始日期,为自然月第一天
* @param string $end_date 结束日期,为自然月最后一天,限定查询一个月数据
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidMonthlyVisittrend($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappidmonthlyvisittrend?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 访问分布
* @param string $begin_date 开始日期
* @param string $end_date 结束日期限定查询1天数据end_date允许设置的最大值为昨日
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidVisitdistribution($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappidvisitdistribution?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 日留存
* @param string $begin_date 开始日期
* @param string $end_date 结束日期限定查询1天数据end_date允许设置的最大值为昨日
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidDailyRetaininfo($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappiddailyretaininfo?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 周留存
* @param string $begin_date 开始日期,为周一日期
* @param string $end_date 结束日期,为周日日期,限定查询一周数据
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidWeeklyRetaininfo($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappidweeklyretaininfo?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 月留存
* @param string $begin_date 开始日期,为自然月第一天
* @param string $end_date 结束日期,为自然月最后一天,限定查询一个月数据
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidMonthlyRetaininfo($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappidmonthlyretaininfo?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 访问页面
* @param string $begin_date 开始日期
* @param string $end_date 结束日期限定查询1天数据end_date允许设置的最大值为昨日
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidVisitPage($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappidvisitpage?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
/**
* 用户画像
* @param string $begin_date 开始日期
* @param string $end_date 结束日期开始日期与结束日期相差的天数限定为0/6/29分别表示查询最近1/7/30天数据end_date允许设置的最大值为昨日
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function getWeanalysisAppidUserportrait($begin_date, $end_date)
{
$url = 'https://api.weixin.qq.com/datacube/getweanalysisappiduserportrait?access_token=ACCESS_TOKEN';
$this->registerApi($url, __FUNCTION__, func_get_args());
return $this->callPostApi($url, ['begin_date' => $begin_date, 'end_date' => $end_date], true);
}
}

View File

@ -0,0 +1,20 @@
<?php
/**
* error code 说明.
* <ul>
* <li>-41001: encodingAesKey 非法</li>
* <li>-41003: aes 解密失败</li>
* <li>-41004: 解密后得到的buffer非法</li>
* <li>-41005: base64加密失败</li>
* <li>-41016: base64解密失败</li>
* </ul>
*/
class ErrorCode
{
public static $OK = 0;
public static $IllegalAesKey = -41001;
public static $IllegalIv = -41002;
public static $IllegalBuffer = -41003;
public static $DecodeBase64Error = -41004;
}

View File

@ -0,0 +1,57 @@
<?php
/**
* 对微信小程序用户加密数据的解密示例代码
* Class WXBizDataCrypt
* @copyright Copyright (c) 1998-2014 Tencent Inc.
*/
class WXBizDataCrypt
{
private $appid;
private $sessionKey;
/**
* 构造函数
* @param $sessionKey string 用户在小程序登录后获取的会话密钥
* @param $appid string 小程序的appid
*/
public function __construct($appid, $sessionKey)
{
$this->appid = $appid;
$this->sessionKey = $sessionKey;
include_once __DIR__ . DIRECTORY_SEPARATOR . "errorCode.php";
}
/**
* 检验数据的真实性,并且获取解密后的明文.
* @param $encryptedData string 加密的用户数据
* @param $iv string 与用户数据一同返回的初始向量
* @param $data string 解密后的原文
*
* @return int 成功0失败返回对应的错误码
*/
public function decryptData($encryptedData, $iv, &$data)
{
if (strlen($this->sessionKey) != 24) {
return \ErrorCode::$IllegalAesKey;
}
$aesKey = base64_decode($this->sessionKey);
if (strlen($iv) != 24) {
return \ErrorCode::$IllegalIv;
}
$aesIV = base64_decode($iv);
$aesCipher = base64_decode($encryptedData);
$result = openssl_decrypt($aesCipher, "AES-128-CBC", $aesKey, 1, $aesIV);
$dataObj = json_decode($result);
if ($dataObj == null) {
return \ErrorCode::$IllegalBuffer;
}
if ($dataObj->watermark->appid != $this->appid) {
return \ErrorCode::$IllegalBuffer;
}
$data = $result;
return \ErrorCode::$OK;
}
}

View File

@ -0,0 +1,63 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WePay;
use WeChat\Contracts\BasicWePay;
use WeChat\Contracts\Tools;
use WeChat\Exceptions\InvalidResponseException;
/**
* 微信商户账单及评论
* Class Bill
* @package WePay
*/
class Bill extends BasicWePay
{
/**
* 下载对账单
* @param array $options 静音参数
* @param null|string $outType 输出类型
* @return bool|string
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function download(array $options, $outType = null)
{
$this->params->set('sign_type', 'MD5');
$params = $this->params->merge($options);
$params['sign'] = $this->getPaySign($params, 'MD5');
$result = Tools::post('https://api.mch.weixin.qq.com/pay/downloadbill', Tools::arr2xml($params));
if (($jsonData = Tools::xml2arr($result))) {
if ($jsonData['return_code'] !== 'SUCCESS') {
throw new InvalidResponseException($jsonData['return_msg'], '0');
}
}
return is_null($outType) ? $result : $outType($result);
}
/**
* 拉取订单评价数据
* @param array $options
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function comment(array $options)
{
$url = 'https://api.mch.weixin.qq.com/billcommentsp/batchquerycomment';
return $this->callPostApi($url, $options, true);
}
}

View File

@ -0,0 +1,65 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WePay;
use WeChat\Contracts\BasicWePay;
/**
* 微信商户代金券
* Class Coupon
* @package WePay
*/
class Coupon extends BasicWePay
{
/**
* 发放代金券
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function create(array $options)
{
$url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/send_coupon";
return $this->callPostApi($url, $options, true);
}
/**
* 查询代金券批次
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function queryStock(array $options)
{
$url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/query_coupon_stock";
return $this->callPostApi($url, $options, false);
}
/**
* 查询代金券信息
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function queryInfo(array $options)
{
$url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/query_coupon_stock";
return $this->callPostApi($url, $options, false);
}
}

View File

@ -0,0 +1,173 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WePay;
use WeChat\Contracts\BasicWePay;
use WeChat\Contracts\Tools;
/**
* 微信商户订单
* Class Order
* @package WePay
*/
class Order extends BasicWePay
{
/**
* 统一下单
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function create(array $options)
{
$url = 'https://api.mch.weixin.qq.com/pay/unifiedorder';
return $this->callPostApi($url, $options, false, 'MD5');
}
/**
* 刷卡支付
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function micropay(array $options)
{
$url = 'https://api.mch.weixin.qq.com/pay/micropay';
return $this->callPostApi($url, $options, false, 'MD5');
}
/**
* 查询订单
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function query(array $options)
{
$url = 'https://api.mch.weixin.qq.com/pay/orderquery';
return $this->callPostApi($url, $options);
}
/**
* 关闭订单
* @param string $outTradeNo 商户订单号
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function close($outTradeNo)
{
$url = 'https://api.mch.weixin.qq.com/pay/closeorder';
return $this->callPostApi($url, ['out_trade_no' => $outTradeNo]);
}
/**
* 创建JsApi及H5支付参数
* @param string $prepayId 统一下单预支付码
* @return array
*/
public function jsapiParams($prepayId)
{
$option = [];
$option["appId"] = $this->config->get('appid');
$option["timeStamp"] = (string)time();
$option["nonceStr"] = Tools::createNoncestr();
$option["package"] = "prepay_id={$prepayId}";
$option["signType"] = "MD5";
$option["paySign"] = $this->getPaySign($option, 'MD5');
$option['timestamp'] = $option['timeStamp'];
return $option;
}
/**
* 获取支付规则二维码
* @param string $productId 商户定义的商品id或者订单号
* @return string
*/
public function qrcParams($productId)
{
$data = [
'appid' => $this->config->get('appid'),
'mch_id' => $this->config->get('mch_id'),
'time_stamp' => (string)time(),
'nonce_str' => Tools::createNoncestr(),
'product_id' => (string)$productId,
];
$data['sign'] = $this->getPaySign($data, 'MD5');
return "weixin://wxpay/bizpayurl?" . http_build_query($data);
}
/**
* 获取微信App支付秘需参数
* @param string $prepayId 统一下单预支付码
* @return array
*/
public function appParams($prepayId)
{
$data = [
'appid' => $this->config->get('appid'),
'partnerid' => $this->config->get('mch_id'),
'prepayid' => (string)$prepayId,
'package' => 'Sign=WXPay',
'timestamp' => (string)time(),
'noncestr' => Tools::createNoncestr(),
];
$data['sign'] = $this->getPaySign($data, 'MD5');
return $data;
}
/**
* 刷卡支付 撤销订单
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function reverse(array $options)
{
$url = 'https://api.mch.weixin.qq.com/secapi/pay/reverse';
return $this->callPostApi($url, $options, true);
}
/**
* 刷卡支付 授权码查询openid
* @param string $authCode 扫码支付授权码,设备读取用户微信中的条码或者二维码信息
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function queryAuthCode($authCode)
{
$url = 'https://api.mch.weixin.qq.com/tools/authcodetoopenid';
return $this->callPostApi($url, ['auth_code' => $authCode]);
}
/**
* 刷卡支付 交易保障
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function report(array $options)
{
$url = 'https://api.mch.weixin.qq.com/payitil/report';
return $this->callPostApi($url, $options);
}
}

View File

@ -0,0 +1,72 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WePay;
use WeChat\Contracts\BasicWePay;
/**
* 微信红包支持
* Class Redpack
* @package WePay
*/
class Redpack extends BasicWePay
{
/**
* 发放普通红包
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function create(array $options)
{
$this->params->offsetUnset('appid');
$this->params->set('wxappid', $this->config->get('appid'));
$url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/sendredpack";
return $this->callPostApi($url, $options, true, 'MD5', false);
}
/**
* 发放裂变红包
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function groups(array $options)
{
$this->params->offsetUnset('appid');
$this->params->set('wxappid', $this->config->get('appid'));
$url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/sendgroupredpack";
return $this->callPostApi($url, $options, true, 'MD5', false);
}
/**
* 查询红包记录
* @param string $mchBillno 商户发放红包的商户订单号
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function query($mchBillno)
{
$this->params->offsetUnset('wxappid');
$this->params->set('appid', $this->config->get('appid'));
$url = "https://api.mch.weixin.qq.com/mmpaymkttransfers/gethbinfo";
return $this->callPostApi($url, ['mch_billno' => $mchBillno, 'bill_type' => 'MCHT'], true, 'MD5', false);
}
}

View File

@ -0,0 +1,78 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WePay;
use WeChat\Contracts\BasicWePay;
use WeChat\Contracts\Tools;
use WeChat\Exceptions\InvalidResponseException;
/**
* 微信商户退款
* Class Refund
* @package WePay
*/
class Refund extends BasicWePay
{
/**
* 创建退款订单
* @param array $options
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function create(array $options)
{
$url = 'https://api.mch.weixin.qq.com/secapi/pay/refund';
return $this->callPostApi($url, $options, true);
}
/**
* 查询退款
* @param array $options
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function query(array $options)
{
$url = 'https://api.mch.weixin.qq.com/pay/refundquery';
return $this->callPostApi($url, $options);
}
/**
* 获取退款通知
* @return array
* @throws InvalidResponseException
*/
public function getNotify()
{
$data = Tools::xml2arr(file_get_contents("php://input"));
if (!isset($data['return_code']) || $data['return_code'] !== 'SUCCESS') {
throw new InvalidResponseException('获取退款通知XML失败');
}
if (!class_exists('Prpcrypt', false)) {
include dirname(__DIR__) . '/WeChat/Contracts/Prpcrypt.php';
}
$pc = new \Prpcrypt(md5($this->config->get('mch_key')));
$array = $pc->decrypt(base64_decode($data['req_info']));
if (intval($array[0]) > 0) {
throw new InvalidResponseException($array[1], $array[0]);
}
$data['decode'] = $array[1];
return $data;
}
}

View File

@ -0,0 +1,61 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WePay;
use WeChat\Contracts\BasicWePay;
/**
* 微信商户打款到零钱
* Class Transfers
* @package WePay
*/
class Transfers extends BasicWePay
{
/**
* 企业付款到零钱
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function create(array $options)
{
$this->params->offsetUnset('appid');
$this->params->offsetUnset('mch_id');
$this->params->set('mchid', $this->config->get('mch_id'));
$this->params->set('mch_appid', $this->config->get('appid'));
$url = 'https://api.mch.weixin.qq.com/mmpaymkttransfers/promotion/transfers';
return $this->callPostApi($url, $options, true, 'MD5', false);
}
/**
* 查询企业付款到零钱
* @param string $partnerTradeNo 商户调用企业付款API时使用的商户订单号
* @return array
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function query($partnerTradeNo)
{
$this->params->offsetUnset('mchid');
$this->params->offsetUnset('mch_appid');
$this->params->set('appid', $this->config->get('appid'));
$this->params->set('mch_id', $this->config->get('mch_id'));
$url = 'https://api.mch.weixin.qq.com/mmpaymkttransfers/gettransferinfo';
return $this->callPostApi($url, ['partner_trade_no' => $partnerTradeNo], true, 'MD5', false);
}
}

View File

@ -0,0 +1,125 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
namespace WePay;
use WeChat\Contracts\BasicWePay;
use WeChat\Contracts\Tools;
use WeChat\Exceptions\InvalidArgumentException;
use WeChat\Exceptions\InvalidDecryptException;
use WeChat\Exceptions\InvalidResponseException;
/**
* 微信商户打款到银行卡
* Class TransfersBank
* @package WePay
*/
class TransfersBank extends BasicWePay
{
/**
* 企业付款到银行卡
* @param array $options
* @return array
* @throws \WeChat\Exceptions\InvalidDecryptException
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function create(array $options)
{
if (!isset($options['partner_trade_no'])) {
throw new InvalidArgumentException('Missing Options -- [partner_trade_no]');
}
if (!isset($options['enc_bank_no'])) {
throw new InvalidArgumentException('Missing Options -- [enc_bank_no]');
}
if (!isset($options['enc_true_name'])) {
throw new InvalidArgumentException('Missing Options -- [enc_true_name]');
}
if (!isset($options['bank_code'])) {
throw new InvalidArgumentException('Missing Options -- [bank_code]');
}
if (!isset($options['amount'])) {
throw new InvalidArgumentException('Missing Options -- [amount]');
}
$this->params->offsetUnset('appid');
return $this->callPostApi('https://api.mch.weixin.qq.com/mmpaysptrans/pay_bank', [
'amount' => $options['amount'],
'bank_code' => $options['bank_code'],
'partner_trade_no' => $options['partner_trade_no'],
'enc_bank_no' => $this->rsaEncode($options['enc_bank_no']),
'enc_true_name' => $this->rsaEncode($options['enc_true_name']),
'desc' => isset($options['desc']) ? $options['desc'] : '',
], true, 'MD5', false);
}
/**
* 商户企业付款到银行卡操作进行结果查询
* @param string $partnerTradeNo 商户订单号,需保持唯一
* @return array
* @throws InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
public function query($partnerTradeNo)
{
$this->params->offsetUnset('appid');
$url = 'https://api.mch.weixin.qq.com/mmpaysptrans/query_bank';
return $this->callPostApi($url, ['partner_trade_no' => $partnerTradeNo], true, 'MD5', false);
}
/**
* RSA加密处理
* @param string $string
* @param string $encrypted
* @return string
* @throws \WeChat\Exceptions\InvalidDecryptException
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
private function rsaEncode($string, $encrypted = '')
{
$search = ['-----BEGIN RSA PUBLIC KEY-----', '-----END RSA PUBLIC KEY-----', "\n", "\r"];
$pkc1 = str_replace($search, '', $this->getRsaContent());
$publicKey = '-----BEGIN PUBLIC KEY-----' . PHP_EOL .
wordwrap('MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A' . $pkc1, 64, PHP_EOL, true) . PHP_EOL .
'-----END PUBLIC KEY-----';
if (!openssl_public_encrypt("{$string}", $encrypted, $publicKey, OPENSSL_PKCS1_OAEP_PADDING)) {
throw new InvalidDecryptException('Rsa Encrypt Error.');
}
return base64_encode($encrypted);
}
/**
* 获取签名文件内容
* @return string
* @throws \WeChat\Exceptions\InvalidResponseException
* @throws \WeChat\Exceptions\LocalCacheException
*/
private function getRsaContent()
{
$cacheKey = "pub_ras_key_" . $this->config->get('mch_id');
if (($pub_key = Tools::getCache($cacheKey))) {
return $pub_key;
}
$data = $this->callPostApi('https://fraud.mch.weixin.qq.com/risk/getpublickey', [], true, 'MD5');
if (!isset($data['return_code']) || $data['return_code'] !== 'SUCCESS' || $data['result_code'] !== 'SUCCESS') {
$error = 'ResultError:' . $data['return_msg'];
$error .= isset($data['err_code_des']) ? ' - ' . $data['err_code_des'] : '';
throw new InvalidResponseException($error, 20000, $data);
}
Tools::setCache($cacheKey, $data['pub_key'], 600);
return $data['pub_key'];
}
}

View File

@ -0,0 +1,39 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
try {
// 实例支付对象
// $pay = \We::AliPayApp($config);
// $pay = new \AliPay\App($config);
$pay = \AliPay\App::instance($config);
// 请参考请求参数https://docs.open.alipay.com/api_1/alipay.trade.app.pay
$result = $pay->apply([
'out_trade_no' => time(), // 商户订单号
'total_amount' => '1', // 支付金额
'subject' => 'test subject', // 支付订单描述
]);
echo '<pre>';
var_export($result);
} catch (\Exception $e) {
echo $e->getMessage();
}

View File

@ -0,0 +1,36 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
try {
// 实例支付对象
// $pay = new \AliPay\Bill($config);
// $pay = \We::AliPayBill($config);
$pay = \AliPay\Bill::instance($config);
// 请参考请求参数https://docs.open.alipay.com/api_15/alipay.data.dataservice.bill.downloadurl.query
$result = $pay->apply([
'bill_date' => '2018-10-03', // 账单时间(日账单yyyy-MM-dd,月账单 yyyy-MM)
'bill_type' => 'signcustomer', // 账单类型(trade指商户基于支付宝交易收单的业务账单,signcustomer是指基于商户支付宝余额收入及支出等资金变动的帐务账单)
]);
echo '<pre>';
var_export($result);
} catch (Exception $e) {
echo $e->getMessage();
}

View File

@ -0,0 +1,39 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
try {
// 实例支付对象
// $pay = \We::AliPayApp($config);
// $pay = new \AliPay\App($config);
$pay = \AliPay\App::instance($config);
$data = $pay->notify();
if (in_array($data['trade_status'], ['TRADE_SUCCESS', 'TRADE_FINISHED'])) {
// @todo 更新订单状态,支付完成
file_put_contents('notify.txt', "收到来自支付宝的异步通知\r\n", FILE_APPEND);
file_put_contents('notify.txt', '订单号:' . $data['out_trade_no'] . "\r\n", FILE_APPEND);
file_put_contents('notify.txt', '订单金额:' . $data['total_amount'] . "\r\n\r\n", FILE_APPEND);
} else {
file_put_contents('notify.txt', "收到异步通知\r\n", FILE_APPEND);
}
} catch (\Exception $e) {
// 异常处理
echo $e->getMessage();
}

View File

@ -0,0 +1,41 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
try {
// 实例支付对象
// $pay = We::AliPayPos($config);
// $pay = new \AliPay\Pos($config);
$pay = \AliPay\Pos::instance($config);
// 参数链接https://docs.open.alipay.com/api_1/alipay.trade.pay
$result = $pay->apply([
'out_trade_no' => '4312412343', // 订单号
'total_amount' => '13', // 订单金额,单位:元
'subject' => '订单商品标题', // 订单商品标题
'auth_code' => '123456', // 授权码
]);
echo '<pre>';
var_export($result);
} catch (Exception $e) {
echo $e->getMessage();
}

View File

@ -0,0 +1,39 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
// 原商户订单号
$out_trade_no = '56737188841424';
// 申请退款金额
$refund_fee = '1.00';
try {
// 实例支付对象
// $pay = We::AliPayApp($config);
// $pay = new \AliPay\App($config);
$pay = \AliPay\App::instance($config);
// 参考链接https://docs.open.alipay.com/api_1/alipay.trade.refund
$result = $pay->refund($out_trade_no, $refund_fee);
echo '<pre>';
var_export($result);
} catch (Exception $e) {
echo $e->getMessage();
}

View File

@ -0,0 +1,40 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
try {
// 实例支付对象
// $pay = We::AliPayScan($config);
// $pay = new \AliPay\Scan($config);
$pay = \AliPay\Scan::instance($config);
// 参考链接https://docs.open.alipay.com/api_1/alipay.trade.precreate
$result = $pay->apply([
'out_trade_no' => '14321412', // 订单号
'total_amount' => '13', // 订单金额,单位:元
'subject' => '订单商品标题', // 订单商品标题
]);
echo '<pre>';
var_export($result);
} catch (Exception $e) {
echo $e->getMessage();
}

View File

@ -0,0 +1,43 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
try {
// 实例支付对象
// $pay = We::AliPayTransfer($config);
// $pay = new \AliPay\Transfer($config);
$pay = \AliPay\Transfer::instance($config);
// 参考链接https://docs.open.alipay.com/api_28/alipay.fund.trans.toaccount.transfer
$result = $pay->apply([
'out_biz_no' => time(), // 订单号
'payee_type' => 'ALIPAY_LOGONID', // 收款方账户类型(ALIPAY_LOGONID | ALIPAY_USERID)
'payee_account' => 'demo@sandbox.com', // 收款方账户
'amount' => '10', // 转账金额
'payer_show_name' => '未寒', // 付款方姓名
'payee_real_name' => '张三', // 收款方真实姓名
'remark' => '张三', // 转账备注
]);
echo '<pre>';
var_export($result);
} catch (Exception $e) {
echo $e->getMessage();
}

View File

@ -0,0 +1,42 @@
<?php
// +----------------------------------------------------------------------
// | WeChatDeveloper
// +----------------------------------------------------------------------
// | 版权所有 2014~2018 广州楚才信息科技有限公司 [ http://www.cuci.cc ]
// +----------------------------------------------------------------------
// | 官方网站: http://think.ctolog.com
// +----------------------------------------------------------------------
// | 开源协议 ( https://mit-license.org )
// +----------------------------------------------------------------------
// | github开源项目https://github.com/zoujingli/WeChatDeveloper
// +----------------------------------------------------------------------
// 1. 手动加载入口文件
include "../include.php";
// 2. 准备公众号配置参数
$config = include "./alipay.php";
// 参考公共参数 https://docs.open.alipay.com/203/107090/
$config['notify_url'] = 'http://pay.thinkadmin.top/test/alipay-notify.php';
$config['return_url'] = 'http://pay.thinkadmin.top/test/alipay-success.php';
try {
// 实例支付对象
// $pay = We::AliPayWap($config);
// $pay = new \AliPay\Wap($config);
$pay = \AliPay\Wap::instance($config);
// 参考链接https://docs.open.alipay.com/api_1/alipay.trade.wap.pay
$result = $pay->apply([
'out_trade_no' => time(), // 商户订单号
'total_amount' => '1', // 支付金额
'subject' => '支付订单描述', // 支付订单描述
]);
echo $result;
} catch (Exception $e) {
echo $e->getMessage();
}

Some files were not shown because too many files have changed in this diff Show More