<?php
namespace app\modules\api\controllers;
use app\dato\ApiResponse;
use app\extensions\TencentSms;
use app\models\QyxClassification;
use app\models\QyxClassificationConfig;
use app\models\QyxMember;
use app\models\QyxUserMember;
use app\models\UserCardvip;
use app\models\UserCardvipList;
use app\modules\api\models\wxbdc\WXBizDataCrypt;
use Yii;
class ClassificationController extends Controller
{
private $unifiedOrder;
public function init()
{
parent::init();
$this->unifiedOrder = 'https://api.mch.weixin.qq.com/pay/unifiedorder';
}
/**
* 對比愛學堂數據並同步
*/
public function actionSyncData()
{
$aixuetang = QyxClassificationConfig::find()
->select('name,type,sort,if_open,if_delete,subject_if_displays,classification_id')
->where(['store_id' => 8])
->asArray()
->all();
$weike = QyxClassificationConfig::find()
->select('name,type,sort,if_open,if_delete,subject_if_displays,classification_id')
->where(['store_id' => 9])
->asArray()
->all();
$install = $aixuetang;
//更新不同數據,並拿出沒有的數據
foreach ($aixuetang as $k => $v) {
foreach ($weike as $i => $j) {
if ($v['classification_id'] == $j['classification_id']) {
unset($install[$k]);
if ($v != $j) {
$diff = array_diff_assoc($v, $j);
foreach ($diff as $k => $v) {
QyxClassificationConfig::updateAll([$k => $v], ['classification_id' => $j['classification_id'], 'store_id' => 9]);
}
}
}
}
}
//批量插入新紀錄
$field = ['name', 'type', 'sort', 'if_open', 'if_delete', 'subject_if_displays', 'store_id', 'classification_id'];
foreach ($install as $k => $v) {
$insertData[] = [$v['name'], $v['type'], $v['sort'], $v['if_open'], $v['if_delete'], $v['subject_if_displays'], 9, $v['classification_id']];
}
Yii::$app->db->createCommand()->batchInsert(QyxClassificationConfig::tableName(), $field, $insertData)->execute();
}
/**
* 數據去重
*/
public function actionRemove()
{
$sql = 'SELECT id,classification_id, COUNT(*) AS sumCount FROM szdato_qyx_classification_config where store_id = 9 GROUP BY classification_id HAVING sumCount > 1';
$command = Yii::$app->db->createCommand($sql);
$data = $command->queryAll();
foreach ($data as $k => $v) {
$ids[$k] = $v['id'];
}
$ids = implode(",", $ids);
$sql2 = 'delete from szdato_qyx_classification_config where id in(' . $ids . ')';
$command = Yii::$app->db->createCommand($sql2);
$data = $command->execute();
return $data;
}
/**
* 獲取科目,年級,版本
* @return \app\dato\ApiResponse
*/
public function actionIndex()
{
$form = $_POST;
if (!$form['store_id']) {
return new ApiResponse(400, '獲取失敗,缺少參數store_id');
}
$res = QyxClassification::find()
->from(QyxClassification::tableName() . 'a')
->select('a.id,a.name,a.type,a.sort,a.if_open,a.img_src,a.subject_if_displays')
->leftJoin(QyxclassificationConfig::tableName() . 'b', 'a.id = b.classification_id and b.if_delete = 0 and b.if_open = 1 and b.store_id =' . $form['store_id'])
->andWhere(['a.if_delete' => 0, 'a.if_open' => 1, 'b.if_delete' => 0, 'b.if_open' => 1])
->orderBy('b.sort asc,a.sort asc,a.id asc')
->asArray()
->all();
$data = QyxclassificationConfig::find()->where(['if_delete' => 0, 'store_id' => $form['store_id']])->asArray()->all();
foreach ($res as $k => $value) {
foreach ($data as $j => $item) {
if ($value['id'] == $item['classification_id']) {
if (!empty($item['name'])) {
$res[$k]['name'] = $item['name'];
}
if (!empty($item['img_src'])) {
$res[$k]['img_src'] = $item['img_src'];
}
if (!empty($item['subject_if_displays']) || $item['subject_if_displays'] == 0) {
$res[$k]['subject_if_displays'] = $item['subject_if_displays'];
}
if (!empty($item['sort'])) {
$res[$k]['sort'] = $item['sort'];
} else {
$res[$k]['sort'] = 5;
}
}
}
}
/*foreach ($res as $k => $v) {
if ($v['subject_if_displays'] != 1 &&$v['type'] == 'subject') {
unset($res[$k]);
}
}*/
/*foreach ($res as $k => $v) {
$arr[$v['sort']][] = $v;
}
ksort($arr);
$arr_res = [];
foreach ($arr as $k => $v) {
foreach ($v as $k1 => $v2) {
$arr_res[] = $v2;
}
}*/
$result['grade'][] = [
'id' => '0',
'name' => '全部',
'type' => 'grade',
'sort' => '5',
'if_open' => '1',
'img_src' => null,
'subject_if_displays' => '1'
];
$result['version'][] = [
'id' => '0',
'name' => '全部',
'type' => 'version',
'sort' => '5',
'if_open' => '1',
'img_src' => null,
'subject_if_displays' => '1'
];
if ($form['store_id'] == 9 || $form['store_id'] == 8) {
switch ($form['store_id']) {
case '9':
$result['subject'][] = [
'id' => '0',
'name' => '全部',
'type' => 'subject',
'sort' => '5',
'if_open' => '1',
'img_src' => 'https://app.2019edu.com/web/uploads/image/imgs/whole.png',
'subject_if_displays' => '1'
];
break;
case '8':
$result['subject'][] = [
'id' => '0',
'name' => '全部',
'type' => 'subject',
'sort' => '5',
'if_open' => '1',
'img_src' => 'https://app.2019edu.com/web/uploads/image/imgs/whole.bak.png',
'subject_if_displays' => '1'
];
break;
}
}
foreach ($res as $key => $value) {
if ($value['type'] == 'grade') {
$result['grade'][] = $value;
}
if ($value['type'] == 'subject') {
$result['subject'][] = $value;
}
//關閉了全部版本
/*if ($value['type'] == 'version') {
$result['version'][] = $value;
}*/
}
return new \app\dato\ApiResponse(200, 'success', $result);
}
/**
* 統一下單,準備支付各項參數
* @return \app\dato\ApiResponse
*/
public function actionJoinvip()
{
$params = Yii::$app->request->post();
//判斷前端是否傳入必要參數 ,以下4個參數爲必要參數,缺失一個將導致支付失敗
if (empty($params['store_id']) || empty($params['user_id']) || empty($params['total_fee']) || empty($params['open_id'])) {
return new \app\dato\ApiResponse(400, '前端參數傳入錯誤,請稍後支付', []);
}
$moneys = !empty($params['total_fee']) ? ($params['total_fee'] * 1000) / 10 : 1;//前端插入金額以分爲單位,小數位decimal(10,2)
$open_id = !empty($params['open_id']) ? $params['open_id'] : 'oo9kN5EQfseaIaTpKfv_7CqQLs4c';//前端獲取全局openid
$post = [];
$input = new \WxPayUnifiedOrder();
$input->SetBody("會員購買");
$input->SetOut_trade_no("hexie" . date("YmdHis") . '_' . substr($open_id, 0, 9));
$input->SetTotal_fee($moneys);
$input->SetNotify_url("https://app.2019edu.com/web/paymentresult.php");
$input->SetTrade_type("JSAPI");
$input->SetOpenid($open_id);
$data = $params;
$user_id = $data['user_id'];
$pay_time = time();
$store_id = $data['store_id'];
$order_no = $input->GetOut_trade_no();
$pay_price = $params['total_fee'];
$pay_type = 1;
$is_pay = 0;
$pid = !empty($data['pid']) ? $data['pid'] : ' ';
$member_id = $data['member_id'];
$vip_end_time = $data['end_time'];
$opening_time = $data['opening_name'];
//查詢是否已購買過該年級下會員
$vip = $this->selectThisVipInfo($user_id, $store_id, $member_id, $vip_end_time, $opening_time);
if ($vip) {
$local_time = date('Y-m-d', time());
if ($local_time < $vip['vip_end_time']) {
return new \app\dato\ApiResponse(401, '您已購買過當前年級下的會員,到期時間爲:' . $vip_end_time . '請勿重複購買', []);
}
}
//創建未支付訂單
$last_id = $this->insertLevelOrder($store_id, $order_no, $user_id, $pay_price, $pay_type, $is_pay, $pay_time, $pid, $member_id, $vip_end_time, $opening_time);
if (!$last_id) {
return new \app\dato\ApiResponse(402, '初始訂單創建失敗,請稍後支付', []);
}
$post['appid'] = $appid = $this->getAppid($store_id)['app_id'];
$post['attach'] = $attach = $last_id;//商家數據包,附加數據
$post['body'] = $body = $input->GetBody(); //交易標識簽名
$post['mch_id'] = $mch_id = $this->getAppid($store_id)['mch_id']; //商戶ID
$post['nonce_str'] = $nonce_str = $this->getARandomString();//隨機字符串
$post['notify_url'] = $notify_url = $input->GetNotify_url(); //回調地址
$post['openid'] = $openid = $input->GetOpenid();//openid 小程序:去預習 oo9kN5EQfseaIaTpKfv_7CqQLs4c
$post['out_trade_no'] = $out_trade_no = $input->GetOut_trade_no();//商戶訂單號
$post['spbill_create_ip'] = $spbill_create_ip = $this->getIp();//終端的ip
$post['total_fee'] = $total_fee = $input->GetTotal_fee();//總金額 最低爲一分錢 必須是整數
$post['trade_type'] = $trade_type = $input->GetTrade_type();//交易類型,默認
$sign = $this->getCryptographicSignature($post, $store_id);//簽名
$post_xml = $this->assemTheDataInXmlFormatToTheWeChatServer($appid, $attach, $body, $mch_id, $nonce_str, $notify_url, $openid, $out_trade_no, $spbill_create_ip, $total_fee, $trade_type, $sign);
$url = $this->unifiedOrder;
//微信服務器返回xml字符串
$xml = $this->httpRequestGetTheXmlReturned($url, $post_xml);
if (!$xml) {
return new \app\dato\ApiResponse(403, '支付錯誤,請檢查請求參數是否通過post方法提交,請稍後支付', []);
}
//轉義xml字符串至數組,轉義後數組的鍵全部是大寫
$array = $this->getTheEscapedXml($xml);
//將統一下單接口獲取的PREPAY_ID保存到數據庫中供後期模板消息調用,PREPAY_ID將作爲模板消息的重要參數之一
$sql = "UPDATE szdato_level_order SET
prepay_id='{$array['PREPAY_ID']}'
WHERE id={$last_id}";
$command = Yii::$app->db->createCommand($sql);
$prepay = $command->execute();
if (!$prepay) {
return new \app\dato\ApiResponse(403, 'prepay_id保存失敗,請重試或稍後支付', []);
}
if ($array['RETURN_CODE'] == 'SUCCESS' && $array['RESULT_CODE'] == 'SUCCESS') {
$time = time();
$tmp = [];//臨時數組用於簽名
$tmp['appId'] = $appid;
$tmp['nonceStr'] = $nonce_str;
$tmp['package'] = 'prepay_id=' . $array['PREPAY_ID'];
$tmp['signType'] = 'MD5';
$tmp['timeStamp'] = "$time";
$datas = $this->getPaymentParameters($time, $nonce_str, $array, $tmp, $out_trade_no, $store_id);
return new \app\dato\ApiResponse(200, 'success', $datas);
} else {
$datas['state'] = 0;
$datas['text'] = "參數錯誤";
$datas['ERR_CODE'] = $array['ERR_CODE'];
$datas['RESULT_CODE'] = $array['RESULT_CODE'];
$datas['RETURN_CODE'] = $array['RETURN_CODE'];
$datas['RETURN_MSG'] = $array['RETURN_MSG'];
$datas['ERR_CODE_DES'] = $array['ERR_CODE_DES'];
return new \app\dato\ApiResponse(404, '支付參數錯誤,請稍後支付', $datas);
}
}
/**
* 提供微信支付參數
* @param $time
* @param $nonce_str
* @param $array
* @param $tmp
* @param $out_trade_no
* @param $store_id
* @return array
*/
private function getPaymentParameters($time, $nonce_str, $array, $tmp, $out_trade_no, $store_id)
{
$data = [];
$data['state'] = 1;
$data['timeStamp'] = "$time";//時間戳
$data['nonceStr'] = $nonce_str;//隨機字符串
$data['signType'] = 'MD5';//簽名算法
$data['package'] = 'prepay_id=' . $array['PREPAY_ID'];//統一下單接口返回的 prepay_id 參數值,提交格式如:prepay_id=*
$data['paySign'] = $this->getCryptographicSignature($tmp, $store_id);//簽名,具體簽名方案參見微信公衆號支付幫助文檔;
$data['out_trade_no'] = $out_trade_no;
return $data;
}
/**
* 獲取小程序基本信息
* @param $store_id
* @return array|false
*/
private function getAppid($store_id)
{
$command = Yii::$app->db->createCommand("SELECT * FROM szdato_wechat_app where store_id={$store_id}");
$data = $command->queryOne();
if (!$data) {
return false;
}
return $data;
}
/**
* 獲取是否存在vip信息
* @param $user_id
* @param $store_id
* @param $member_id
* @param $vip_end_time
* @param $opening_time
* @return array|false
*/
private function selectThisVipInfo($user_id, $store_id, $member_id, $vip_end_time, $opening_time)
{
$command = Yii::$app->db->createCommand("SELECT * FROM szdato_level_order
where user_id=$user_id
AND store_id=$store_id
AND member_id=$member_id
AND is_pay=1
AND vip_end_time='{$vip_end_time}'
AND opening_time='{$opening_time}'");
$data = $command->queryOne();
return $data;
}
/**
* 插入初始會員訂單
* @param $store_id
* @param $order_no
* @param $user_id
* @param $pay_price
* @param $pay_type
* @param $is_pay
* @param $pay_time
* @param $pid
* @param $member_id
* @param $vip_end_time
* @param $opening_time
* @return string
*/
private function insertLevelOrder($store_id, $order_no, $user_id, $pay_price, $pay_type, $is_pay, $pay_time, $pid, $member_id, $vip_end_time, $opening_time)
{
$sql = "INSERT INTO szdato_level_order(
store_id,
order_no,
user_id,
pay_price,
pay_type,
is_pay,
pay_time,
pid,
member_id,
vip_end_time,
opening_time)
VALUES(
'{$store_id}',
'{$order_no}',
'{$user_id}',
'{$pay_price}',
'{$pay_type}',
'{$is_pay}',
'{$pay_time}',
'{$pid}',
'{$member_id}',
'{$vip_end_time}',
'{$opening_time}')";
$command = Yii::$app->db->createCommand($sql);
$command->execute();
$last_id = Yii::$app->db->getLastInsertID();
return $last_id;
}
/**
* 隨機字符串 ,最多32位
* @return string
*/
private function getARandomString()
{
$result = '';
$str = 'QWERTYUIOPASDFGHJKLZXCVBNMabcdefghijklmnopqrstuvwxyz';//自定義大小寫字母
for ($i = 0; $i < 32; $i++) {
$result .= $str[rand(0, 51)];
}
return $result;
}
/**
* 傳入微信需要的參數
* @param $appid
* @param $attach
* @param $body
* @param $mch_id
* @param $nonce_str
* @param $notify_url
* @param $openid
* @param $out_trade_no
* @param $spbill_create_ip
* @param $total_fee
* @param $trade_type
* @param $sign
* @return string
*/
private function assemTheDataInXmlFormatToTheWeChatServer($appid, $attach, $body, $mch_id, $nonce_str, $notify_url, $openid, $out_trade_no, $spbill_create_ip, $total_fee, $trade_type, $sign)
{
$string = '<xml>
<appid>' . $appid . '</appid>
<attach>' . $attach . '</attach>
<body>' . $body . '</body>
<mch_id>' . $mch_id . '</mch_id>
<nonce_str>' . $nonce_str . '</nonce_str>
<notify_url>' . $notify_url . '</notify_url>
<openid>' . $openid . '</openid>
<out_trade_no>' . $out_trade_no . '</out_trade_no>
<spbill_create_ip>' . $spbill_create_ip . '</spbill_create_ip>
<total_fee>' . $total_fee . '</total_fee>
<trade_type>' . $trade_type . '</trade_type>
<sign>' . $sign . '</sign>
</xml> ';
return $string;
}
/**簽名函數
* @param $data
* @param $store_id
* @return string
*/
private function getCryptographicSignature($data, $store_id)
{
$stringA = '';
foreach ($data as $key => $value) {
if (!$value) continue;
if ($stringA) {
$stringA .= '&' . $key . "=" . $value;
} else {
$stringA = $key . "=" . $value;
}
}
$wx_key = $this->getAppid($store_id)['key'];//申請支付後有給予一個商戶賬號和密碼,登陸後自己設置key
$stringSignTemp = $stringA . '&key=' . $wx_key;
return strtoupper(md5($stringSignTemp));
}
/**
* 獲取IP
* @return string
*/
public function getIp()
{
if (!empty($_SERVER['HTTP_CLIENT_IP'])) {
$cip = $_SERVER['HTTP_CLIENT_IP'];
} else if (!empty($_SERVER['HTTP_X_FORWARDED_FOR'])) {
$cip = $_SERVER["HTTP_X_FORWARDED_FOR"];
} else if (!empty($_SERVER["REMOTE_ADDR"])) {
$cip = $_SERVER["REMOTE_ADDR"];
} else {
$cip = '';
}
preg_match("/[\d\.]{7,15}/", $cip, $cips);
$cip = isset($cips[0]) ? $cips[0] : 'unknown';
unset($cips);
return $cip;
}
/**
* curl請求
* @param $url
* @param null $data
* @param array $headers
* @return mixed
*/
private function httpRequestGetTheXmlReturned($url, $data = null, $headers = array())
{
$curl = curl_init();
if (count($headers) >= 1) {
curl_setopt($curl, CURLOPT_HTTPHEADER, $headers);
}
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE);
if (!empty($data)) {
curl_setopt($curl, CURLOPT_POST, 1);
curl_setopt($curl, CURLOPT_POSTFIELDS, $data);
}
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$output = curl_exec($curl);
curl_close($curl);
return $output;
}
/**
* 解義xml
* @param $xml
* @return string
*/
private function getTheEscapedXml($xml)
{
$p = xml_parser_create();//創建 XML 解析器
xml_parse_into_struct($p, $xml, $vals, $index);
xml_parser_free($p);
$data = "";
foreach ($index as $key => $value) {
if ($key == 'xml' || $key == 'XML') continue;
$tag = $vals[$value[0]]['tag'];
$value = $vals[$value[0]]['value'];
$data[$tag] = $value;
}
return $data;
}
/**
* 獲取加密信息
* @return \app\dato\ApiResponse
*/
public function actionJm()
{
$appid = 'wx4f4bc4dec97d474b';
$sessionKey = 'tiihtNczf5v6AKRyjwEUhQ==';
$iv = 'r7BXXKkLb8qrSNn05n0qiA==';//前端傳入
$encryptedData = "CiyLU1Aw2KjvrjMdj8YKliAjtP4gsMZM
QmRzooG2xrDcvSnxIMXFufNstNGTyaGS
9uT5geRa0W4oTOb1WT7fJlAC+oNPdbB+
3hVbJSRgv+4lGOETKUQz6OYStslQ142d
NCuabNPGBzlooOmB231qMM85d2/fV6Ch
evvXvQP8Hkue1poOFtnEtpyxVLW1zAo6
/1Xx1COxFvrc2d7UL/lmHInNlxuacJXw
u0fjpXfz/YqYzBIBzD6WUfTIF9GRHpOn
/Hz7saL8xz+W//FRAUid1OksQaQx4CMs
8LOddcQhULW4ucetDf96JcR3g0gfRK4P
C7E/r7Z6xNrXd2UIeorGj5Ef7b1pJAYB
6Y5anaHqZ9J6nKEBvB4DnNLIVWSgARns
/8wR2SiRS7MNACwTyrGvt9ts8p12PKFd
lqYTopNHR1Vf7XjfhQlVsAJdNiKdYmYV
oKlaRv85IfVunYzO0IKXsyl7JCUjCpoG
20f0a04COwfneQAGGwd5oa+T8yO5hzuy
Db/XcxxmK01EpqOyuxINew==";
$pc = new WXBizDataCrypt($appid, $sessionKey);
$errCode = $pc->decryptData($encryptedData, $iv, $data);
if ($errCode == 0) {
return new \app\dato\ApiResponse(200, 'success', $data . "\n");
} else {
return new \app\dato\ApiResponse(400, 'error', $errCode . "\n");
}
}
/**
* 回調 函數 回調方法參見:統一下單接口中回調地址url
*/
public function actionPaymentresult()
{
$post = file_get_contents("php://input");
/**支付成功返回示例 詳見 https://pay.weixin.qq.com/wiki/doc/api/H5.php?chapter=9_7&index=7**
* $post = '<xml>
* <appid><![CDATA[wx2421b1c4370ec43b]]></appid>
* <attach><![CDATA[支付測試]]></attach>
* <bank_type><![CDATA[CFT]]></bank_type>
* <fee_type><![CDATA[CNY]]></fee_type>
* <is_subscribe><![CDATA[Y]]></is_subscribe>
* <mch_id><![CDATA[10000100]]></mch_id>
* <nonce_str><![CDATA[5d2b6c2a8db53831f7eda20af46e531c]]></nonce_str>
* <openid><![CDATA[oUpF8uMEb4qRXf22hE3X68TekukE]]></openid>
* <out_trade_no><![CDATA[1409811653]]></out_trade_no>
* <result_code><![CDATA[SUCCESS]]></result_code>
* <return_code><![CDATA[SUCCESS]]></return_code>
* <sign><![CDATA[B552ED6B279343CB493C5DD0D78AB241]]></sign>
* <sub_mch_id><![CDATA[10000100]]></sub_mch_id>
* <time_end><![CDATA[20140903131540]]></time_end>
* <total_fee>1</total_fee>
* <coupon_fee_0><![CDATA[10]]></coupon_fee_0>
* <coupon_count><![CDATA[1]]></coupon_count>
* <coupon_type><![CDATA[CASH]]></coupon_type>
* <coupon_id><![CDATA[10000]]></coupon_id>
* <trade_type><![CDATA[JSAPI]]></trade_type>
* <transaction_id><![CDATA[1004400740201409030005092168]]></transaction_id>
* </xml>';
**支付成功返回示例**/
// $post = '<xml>
// <appid><![CDATA[wx2421b1c4370ec43b]]></appid>
// <attach><![CDATA[支付測試]]></attach>
// <bank_type><![CDATA[CFT]]></bank_type>
// <fee_type><![CDATA[CNY]]></fee_type>
// <is_subscribe><![CDATA[Y]]></is_subscribe>
// <mch_id><![CDATA[10000100]]></mch_id>
// <nonce_str><![CDATA[5d2b6c2a8db53831f7eda20af46e531c]]></nonce_str>
// <openid><![CDATA[oUpF8uMEb4qRXf22hE3X68TekukE]]></openid>
// <out_trade_no><![CDATA[1409811653]]></out_trade_no>
// <result_code><![CDATA[SUCCESS]]></result_code>
// <return_code><![CDATA[SUCCESS]]></return_code>
// <sign><![CDATA[B552ED6B279343CB493C5DD0D78AB241]]></sign>
// <sub_mch_id><![CDATA[10000100]]></sub_mch_id>
// <time_end><![CDATA[20140903131540]]></time_end>
// <total_fee>1</total_fee>
// <coupon_fee_0><![CDATA[10]]></coupon_fee_0>
// <coupon_count><![CDATA[1]]></coupon_count>
// <coupon_type><![CDATA[CASH]]></coupon_type>
// <coupon_id><![CDATA[10000]]></coupon_id>
// <trade_type><![CDATA[JSAPI]]></trade_type>
// <transaction_id><![CDATA[1004400740201409030005092168]]></transaction_id>
// </xml>';
if ($post) {
$data = $this->getTheEscapedXml($post);
if ($data['RETURN_CODE'] == 'SUCCESS') {//此時返回了正確的數據,可以保存到數據庫了
$result = json_encode($data);
$this->savePaymentInformation($result);
}
$str = '<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';
echo $str;
} else {
exit('<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[Callback error]]></return_msg></xml>');
}
}
/**
*保存回調數據
* @param $result
* @return int
*/
private function savePaymentInformation($result)
{
$res = Yii::$app->db->createCommand()->insert('szdato_qyx_wxpay_callback',
['pay_info' => $result, 'add_time' => time(), 'create_date' => time()])->execute();
return $res;
}
public function sendTemplateInfo($prepay_id, $out_trade_no, $openid)
{
$formid = $prepay_id;
$template_id = 'KlrWgWw0nB6IUDgOR4Dh3_MDQDJM3PtfMOSk5700b94';//模板ID
$page = 'pages/index/index';
$open_id = $openid;
if (!$openid || !$formid) die('failed!');
$key1 = $out_trade_no;//訂單號
$key2 = '0.01';//支付金額
$key3 = date('Y-m-d H:i:s');//下單時間
$key4 = 'VIP會員';//物品名稱
$access_token = $this->returnAssKey();
$url = 'https://api.weixin.qq.com/cgi-bin/message/wxopen/template/send?access_token=' . $access_token;
$data = array(//這裏一定要按照微信給的格式
"touser" => $open_id,
"template_id" => $template_id,
"page" => $page,
"form_id" => $formid,
"data" => array(
"keyword1" => array(
"value" => $key1,
),
"keyword2" => array(
"value" => $key2,
),
"keyword3" => array(
"value" => $key3,
),
"keyword4" => array(
"value" => $key4,
)
),
"emphasis_keyword" => "keyword2.DATA",//需要進行加大的消息
);
$res = $this->postCurl($url, $data, 'json');//將data數組轉換爲json數據
return json_decode($res);
}
private function returnAsskey()
{
$url = 'https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=wxdda3d40e074e4e7d&secret=f50fb02c140c4fcfe11b8279f6217863';
$ass_key = $this->curl_get($url);
$a1 = $ass_key->access_token;
return $a1;
}
private function curl_get($url)
{
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$data = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
return json_decode($data);//對數據進行json解碼
}
private function postCurl($url, $data, $type)
{
if ($type == 'json') {
$data = json_encode($data);//對數組進行json編碼
$header = array("Content-type: application/json;charset=UTF-8", "Accept: application/json", "Cache-Control: no-cache", "Pragma: no-cache");
}
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url);
curl_setopt($curl, CURLOPT_POST, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
if (!empty($data)) {
curl_setopt($curl, CURLOPT_POSTFIELDS, $data);
}
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_HTTPHEADER, $header);
$res = curl_exec($curl);
if (curl_errno($curl)) {
echo 'Error+' . curl_error($curl);
}
curl_close($curl);
return $res;
}
/**
* 兌換碼接口
* @return ApiResponse
* @throws \yii\db\Exception
*/
public function actionSaveredeemcode()
{
if (\Yii::$app->request->isPost) {
$data = \Yii::$app->request->post();
$redeemCode = !empty($data['code']) ? strtoupper($data['code']) : ' ';
$store_id = !empty($data['store_id']) ? $data['store_id'] : ' ';
$user_id = !empty($data['user_id']) ? $data['user_id'] : null; //綁定者
$bindtime = time(); //綁定時間
$member_id = !empty($data['member_id']) ? $data['member_id'] : null;//套餐id
if (!$redeemCode || !$user_id || !$member_id) {
return new \app\dato\ApiResponse(400, '參數錯誤 , 請稍後再試!', []);
}
//修改綁定人,綁定時間
if ($redeemCode && $store_id && $member_id) {
$UserCardvipList = new UserCardvipList();
$datas = $UserCardvipList::find()->where(['redeem_code' => $redeemCode, 'store_id' => $store_id])->asArray()->one();
if (!$datas || $datas['status'] || $datas['user_id'] || $datas['bindingtime'] || $datas['bind_member_id']) {
return new \app\dato\ApiResponse(401, '該兌換碼不存在或已使用', []);
}
$UserCardvipInfo = UserCardvip::find()->where(['id' => $datas['redeem_code_id']])->asArray()->one();
$starttime = $UserCardvipInfo['starttime'];
$endtime = $UserCardvipInfo['endtime'];
$localtime = date('Y-m-d H:i:s', time());
if ($localtime < $starttime || $localtime > $endtime) {
if ($localtime < $starttime) {
$mgs = '請在開始時間' . $starttime . '後開始兌換';
}
$is_show = 1;
}
if (!$UserCardvipInfo['status'] || $is_show == 1) {
if (!empty($mgs)) {
return new \app\dato\ApiResponse(406, $mgs, []);
}
return new \app\dato\ApiResponse(402, '該兌換碼已失效或活動已結束', []);
}
//該兌換碼是免費時 is_free=0
if (!$UserCardvipInfo['is_free']) {
//查詢是否有使用過免費兌換碼
$code_list = UserCardvipList::find()->where(['user_id' => $user_id, 'store_id' => $store_id])->asArray()->all();
if (!empty($code_list)) {
$ids = [];
foreach ($code_list as $v) {
$ids[] = $v['redeem_code_id'];
}
if (!empty($ids)) {
$ids = implode(',', $ids);
$where = [
'and',
'id in (' . $ids . ')',
'is_free=0'
];
$code = UserCardvip::find()->where($where)->asArray()->one();
if (!empty($code)) {
return new \app\dato\ApiResponse(407, '您已經參加過此類活動了', []);
}
}
}
}
$arrcode = $UserCardvipList::find()->where(['redeem_code' => $redeemCode])->one();
$arrcode->status = 1;
$arrcode->bindingtime = $bindtime;
$arrcode->user_id = $user_id;
$arrcode->bind_member_id = $member_id;
$res = $arrcode->save();
if (!$res) {
return new \app\dato\ApiResponse(403, '綁定失敗', []);
}
$UserCardvipInfo = QyxUserMember::find()
->where(['user_id' => $user_id, 'member_id' => $member_id])
->andWhere(['>','endtime',strtotime(date('Y-m-d', time()))])
->orderBy('id desc')
->asArray()
->all();
//該情況爲沒有買過vip會員或者會員過期的情況,首次參與兌換碼活動
if (!$UserCardvipInfo) {
$endtime = $datas['usetime'] * 3600 * 24 + strtotime(date('Y-m-d', time()));
$vip_end_time = date('Y-m-d', $endtime);
} else {
//已買過會員,使用兌換碼時發生以下:延長(或增加)會員時間。
$endtime = $UserCardvipInfo[0]['endtime'] + $datas['usetime'] * 3600 * 24;
$vip_end_time = date('Y-m-d', $endtime);
}
$codeArrays = [[$user_id, time(), $endtime, $member_id, $vip_end_time, '兌換碼兌換會員']];
$resultUserMenber = \Yii::$app->db->createCommand()
->batchInsert('szdato_qyx_user_member',
['user_id', 'addtime', 'endtime', 'member_id', 'vip_end_time', 'remarks'], $codeArrays)
->execute();
if (!$resultUserMenber) {
return new \app\dato\ApiResponse(404, '會員延長時間保存失敗', []);
}
$memberInfo = QyxMember::find()->where(['id' => $member_id])->asArray()->one();
$classification_config_id = $memberInfo['classification_config_id'];
$sql = "SELECT group_concat(name) as classification_config_info
FROM szdato_qyx_classification_config
WHERE id in($classification_config_id)";
$command = Yii::$app->db->createCommand($sql);
$classificationConfigInfo = $command->queryAll();
$resultArrayInfo = [
'vip_end_time' => $vip_end_time,
'add_vip_time' => $datas['usetime'] . '天',
'gradeInfo' => $classificationConfigInfo[0]
];
return new \app\dato\ApiResponse(200, '綁定成功', $resultArrayInfo);
}
} else {
return new \app\dato\ApiResponse(405, 'ajax請求錯誤', []);
}
}
/**
* curl 定時任務 :發送短信提醒會員到期時間
* @return string
* @throws \yii\db\Exception
*/
public function actionServicenotice()
{
$sql = "select m.* , max(m.endtime) as maxtime ,u.wechat_open_id ,u.nickname,u.binding
from szdato_qyx_user_member as m
join szdato_user as u on m.user_id=u.id
group by m.user_id";
$command = Yii::$app->db->createCommand($sql);
$user_member_info = $command->queryAll();
date_default_timezone_set("PRC");
$local_time = strtotime(date('Y-m-d', time()));
$user_member_infos = [];
foreach ($user_member_info as $k => $value) {
if (1 * 3600 * 24 >= $value['endtime'] - $local_time) {//小於1天自動提醒
$user_member_infos[] = $value;
}
}
if (!$user_member_infos) {
return new \app\dato\ApiResponse(404, '暫時沒有發送短信的對象。', []);
}
$resultphones = [];
foreach ($user_member_infos as $n => $info) {
if (!empty($info['binding'])) {
$resultphones[] = $info['binding'];
}
}
//如果有需要發送的對象,則執行發送短信:
$tencentSms = new TencentSms();
$sms_id = 3;//短信id
$sms = 1;//天數
$result = $tencentSms->qunfaSms($sms, $resultphones, $sms_id);
$result = json_decode($result);
$send_phones = [];
$no_send_phones = [];
foreach ($result->detail as $i => $node) {
if (!$node->result) {
$send_phones[$i] = $node->mobile;
} else {
$no_send_phones[$i] = $node->mobile;
}
}
$send_total = count($send_phones);
$no_send_total = count($no_send_phones);
$sms_info = "被騷擾對象:" . json_encode($send_phones) . ";發送失敗:" . json_encode($no_send_phones);
$tips = "總髮送數:" . count($result->detail) . ",成功條數:" . $send_total . ";失敗條數:" . $no_send_total;
$create_date = time();
$sql = "INSERT INTO szdato_sms_callback(
sms_info,
tips,
create_date)
VALUES(
'{$sms_info}',
'{$tips}',
'{$create_date}')";
$command = Yii::$app->db->createCommand($sql);
$command->execute();
//記錄定時任務是否執行
if($send_phones){
file_put_contents('sms_send_callback.log', date('Y-m-d H:i:s', time()) . '執行了一次定時任務,並且騷擾了' . json_encode($send_phones), FILE_APPEND);
}
$string = $tips . '<br>' . $sms_info;
return new \app\dato\ApiResponse(200, $string, []);
}
}
微信支付全套流程輸出
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.