AliPayServices.php 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304
  1. <?php
  2. /**
  3. * 支付宝支付
  4. */
  5. namespace app\api\services;
  6. use think\console\command\optimize\Schema;
  7. use think\Exception;
  8. use think\facade\Db;
  9. use utils\AliPay;
  10. /**
  11. * Class AliPayServices
  12. * @package app\services
  13. * @method $this data($data)
  14. * @method $this type(int $type)
  15. * @method $this trade_type(string $trade_type)
  16. * @method $this uid(int $uid)
  17. */
  18. class AliPayServices extends BasePayServices
  19. {
  20. /**
  21. * 用户id
  22. * @var
  23. */
  24. protected $uid;
  25. /**
  26. * 数据体
  27. * @var
  28. */
  29. protected $data;
  30. /**
  31. * 支付类型 app jsapi
  32. * @var string
  33. */
  34. protected $trade_type;
  35. protected static $instance = null;
  36. public static function instance ()
  37. {
  38. if (is_null(self::$instance)) {
  39. self::$instance = new static();
  40. }
  41. return self::$instance;
  42. }
  43. /**
  44. * 统一下单
  45. * @return mixed
  46. */
  47. public function getUnifiedOrder ()
  48. {
  49. $uid = $this->uid;
  50. if (!$uid || !$this->data)
  51. return api_error_return('下单失败');
  52. list($body, $total_amount, $order_type, $remarks, $trade_type, $pay_way, $voucher_img) = $this->_payConf($uid, $this->data);
  53. // 如果是会员订单
  54. $out_trade_no = rand(1000000000, 9999999999) . (string)date('ymdhis', time()) . (int)microtime(true); // 订单号
  55. /** @var AliPay $pay */
  56. $pay = app()->make(AliPay::class);
  57. if ($pay->pay_v == 1) {
  58. $rpm = $pay->unifiedOrder(compact('uid', 'body', 'out_trade_no', 'total_amount'));
  59. } else {
  60. $rpm = $pay->easyUnifiedOrder(compact('uid', 'body', 'out_trade_no', 'total_amount'));
  61. }
  62. if (!$rpm['flag']) {
  63. return api_error_return($rpm['msg']);
  64. }
  65. $this->setPaymentOrder(compact('body', 'out_trade_no', 'total_amount', 'remarks', 'uid', 'trade_type', 'order_type', 'pay_way', 'voucher_img'), 2);
  66. return api_succ_return(['msg'=>'支付宝统一下单成功', 'data'=>['alipay'=>$rpm['data']['result']]]);
  67. }
  68. /**
  69. * 支付回调
  70. * @return $this
  71. */
  72. public function getNotifyInfo ()
  73. {
  74. $pay = new AliPay();
  75. if ($pay->checkSign($this->data)) {
  76. if ($this->data['trade_status'] == 'TRADE_SUCCESS') {
  77. $this->notify_info = $this->data;
  78. $this->pay_status = true;
  79. $this->pay_way = 2;
  80. }
  81. }
  82. sr_log('签名错误');
  83. return $this;
  84. }
  85. /**
  86. * 提现
  87. * @return mixed
  88. * @throws \think\db\exception\DataNotFoundException
  89. * @throws \think\db\exception\DbException
  90. * @throws \think\db\exception\ModelNotFoundException
  91. */
  92. public function withdrawal ()
  93. {
  94. if (empty($this->data['money'])){
  95. throw new Exception('参数错误');
  96. }
  97. if (!preg_match("/^[1-9][0-9]*$/" ,$this->data['money'])){
  98. throw new Exception('提现金额不能有小数点,不能是负数');
  99. }
  100. $uid = $this->uid;
  101. if (!$uid || !$this->data)
  102. throw new Exception('提现失败');
  103. $money = $this->data['money'];
  104. $user = Db::name('user')->alias('a')->join('user_data b', 'a.id=b.uid')->field('money,status,alipay,real_name,is_auth,level')->where('a.id', $uid)->find();
  105. if ($user['status'] != 1)
  106. throw new Exception('账号已被禁用');
  107. if ($user['is_auth'] != 1)
  108. throw new Exception('你还未实名认证');
  109. if (empty($user['alipay']) || empty($user['real_name']))
  110. throw new Exception('你还未绑定支付宝');
  111. if ($money <= env('WITHDRAW.ONE_COUNT_MONEY'))
  112. throw new Exception('单次提现金额要大于'.env('WITHDRAW.ONE_COUNT_MONEY'));
  113. if ($money > $user['money'])
  114. throw new Exception('余额不足');
  115. // $pay_configs = get_config(2); // 获取支付设置
  116. // if (empty($pay_configs))
  117. // return api_error_return('后台配置错误');
  118. //$service = $pay_configs['TRANSFERSERVICE'] ?? 0;
  119. // $service = $user['vip'] ? 0 : ($user['level'] ? 1 : 3); // vip手续费0,星级达人手续费1%,普通用户3%
  120. $service_money = $money * (env('WITHDRAW.APP_WITHDRAW_SCALE')) / 100 + env('WITHDRAW.APP_WITHDRAW_BEGIN');
  121. $practical_money = $money - $service_money; // 最终金额
  122. // if ($money < $pay_configs['AGENT_REFLECT_MONEY'])
  123. // return api_error_return('单笔提现金额小于' . $pay_configs['AGENT_REFLECT_MONEY'] . '元');
  124. // if ($money > $pay_configs['TRANSFERMAX'])
  125. // return api_error_return('单笔提现金额大于' . $pay_configs['TRANSFERMAX'] . '元');
  126. $today = Db::name('withdraw_log')
  127. ->field("
  128. CASE WHEN id>0 THEN count(id) ELSE 0 END count,
  129. CASE WHEN id>0 THEN sum(apply_money) ELSE 0 END money
  130. ")
  131. ->where('uid', $uid)
  132. ->where('status', 1)
  133. ->whereTime('create_at', 'today')
  134. ->find();
  135. if ($today['count'] >= env('WITHDRAW.ONE_DAY_MAX_COUNT'))
  136. throw new Exception('超出今日提现次数');
  137. if ($today['money'] + $money > env('WITHDRAW.ONE_DAY_MAX_MONEY'))
  138. throw new Exception('超过今日最大转账金额' . env('WITHDRAW.ONE_DAY_MAX_MONEY') . '元');
  139. $moth = Db::name('withdraw_log')
  140. ->field("
  141. CASE WHEN id>0 THEN count(id) ELSE 0 END count,
  142. CASE WHEN id>0 THEN sum(apply_money) ELSE 0 END money
  143. ")
  144. ->where('uid', $uid)
  145. ->where('status', 1)
  146. ->whereTime('create_at', 'moth')
  147. ->find();
  148. if ($moth['count'] >= env('WITHDRAW.ONE_MONTH_MAX_COUNT'))
  149. throw new Exception('超出本月提现次数');
  150. if ($moth['money'] + $money > env('WITHDRAW.ONE_MONTH_MAX_MONEY'))
  151. throw new Exception('超过本月最大提现金额' . env('WITHDRAW.ONE_MONTH_MAX_MONEY') . '元');
  152. $insert_log = [ // 提现流水
  153. 'uid' => $this->uid,
  154. 'apply_money' => $money,
  155. 'status' => 0,
  156. 'zfb_number' => $user['alipay'],
  157. 'zfb_name' => $user['real_name'],
  158. 'channel' => 1,
  159. 'service_money' => $service_money,
  160. 'transfer_type' => 1,
  161. 'practical_money' => $practical_money,
  162. 'ip' => app('request')->ip(),
  163. 'mchid' => Db::name('pay_config')->where('channel', 1)->where('status', 1)->value('mchid'), // 商户号
  164. ];
  165. edit_user_money(2, $uid, $money);
  166. $log_id = Db::name('withdraw_log')->insertGetId($insert_log);
  167. }
  168. /**
  169. * 后台提现
  170. * @return mixed
  171. * @throws \think\db\exception\DataNotFoundException
  172. * @throws \think\db\exception\DbException
  173. * @throws \think\db\exception\ModelNotFoundException
  174. */
  175. public function adminWithdrawal ()
  176. {
  177. $uid = $this->uid;
  178. if (!$uid || !$this->data)
  179. return api_error_return('提现失败');
  180. $money = $this->data['apply_money']; // 申请的金额
  181. $practical_money = $this->data['practical_money']; // 最终金额
  182. if ($practical_money <= 0)
  183. return api_error_return('提现金额必须大于0');
  184. $user = Db::name('user')->field('money,status,is_auth')->where('id', $uid)->find();
  185. if ($user['status'] != 1)
  186. return api_error_return('账号已被禁用');
  187. // if ($user['is_auth'] != 1)
  188. // api_error_return->json_error('你还未实名认证');
  189. if ($money <= 0)
  190. return api_error_return('提现金额要大于0');
  191. // if ($money > $user['money'])
  192. // return api_error_return('余额不足');
  193. // $pay_configs = get_config(2); // 获取支付设置
  194. // if (empty($pay_configs))
  195. // return api_error_return('后台配置错误');
  196. // if ($money < $pay_configs['AGENT_REFLECT_MONEY'])
  197. // return api_error_return('单笔提现金额小于' . $pay_configs['AGENT_REFLECT_MONEY'] . '元');
  198. // if ($money > $pay_configs['TRANSFERMAX'])
  199. // return api_error_return('单笔提现金额大于' . $pay_configs['AGENT_REFLECT_MONEY'] . '元');
  200. // $today = Db::name('withdraw_log')
  201. // ->field("
  202. // CASE WHEN id>0 THEN count(id) ELSE 0 END count,
  203. // CASE WHEN id>0 THEN sum(apply_money) ELSE 0 END money
  204. // ")
  205. // ->where('uid', $uid)
  206. // ->where('status', 1)
  207. // ->whereTime('create_at', 'today')
  208. // ->find();
  209. // if ($today['count'] >= $pay_configs['TRANSFERMAXDAYNUM'])
  210. // return api_error_return('超出今日提现次数');
  211. // if ($today['money'] + $money > $pay_configs['TRANSFERMAXTODAY'])
  212. // return api_error_return('超过今日最大转账金额' . $pay_configs['TRANSFERMAXTODAY'] . '元');
  213. // $moth = Db::name('withdraw_log')
  214. // ->field("
  215. // CASE WHEN id>0 THEN count(id) ELSE 0 END count,
  216. // CASE WHEN id>0 THEN sum(apply_money) ELSE 0 END money
  217. // ")
  218. // ->where('uid', $uid)
  219. // ->where('status', 1)
  220. // ->whereTime('create_at', 'moth')
  221. // ->find();
  222. // if ($moth['count'] >= $pay_configs['PERFORMANCE_UPPER'])
  223. // return api_error_return('超出本月提现次数');
  224. // if ($moth['money'] + $money > $pay_configs['TRANSFERMAXMONTH'])
  225. // return api_error_return('超过本月最大转账金额' . $pay_configs['TRANSFERMAXMONTH'] . '元');
  226. try {
  227. /** @var AliPay $pay */
  228. $pay = app()->make(AliPay::class);
  229. // $pay = new AliPay();
  230. $para = ['practical_money'=>$this->data['practical_money'],
  231. 'zfb_name'=>$this->data['zfb_name'],
  232. 'zfb_number'=>$this->data['zfb_number'],
  233. 'uid'=>$this->data['uid'],
  234. 'type'=>'pay'
  235. ];
  236. // $para {"practical_money":"7.50","real_name":"王红力","alipay":"18280066008","uid":"7493314"}
  237. $rpm = $pay->withdrawal($para);
  238. sr_log('rpm'.json_encode($rpm));
  239. if ($rpm['flag']) {
  240. Db::name('withdraw_log')->where('id', $this->data['id'])->update(['status' => 1, 'out_biz_no' => $rpm['data']['out_biz_no'], 'update_at' => date('Y-m-d H:i:s', time()), 'final_transfer_type' => 1]);
  241. return api_succ_return('提现成功');
  242. } else {
  243. Db::name('withdraw_log')->where('id', $this->data['id'])->update(['fail_log' => $rpm['msg'], 'status' => 2]);
  244. return api_error_return('提现失败');
  245. }
  246. } catch (\Exception $e) {
  247. sr_log('eeee'.$e->getMessage());
  248. return api_error_return($e->getMessage());
  249. return api_error_return('提现失败');
  250. }
  251. }
  252. /**
  253. * 魔术方法
  254. * @param $name
  255. * @param $arguments
  256. * @return $this
  257. */
  258. public function __call ($name, $arguments)
  259. {
  260. // TODO: Implement __call() method.
  261. if ($name == 'data') {
  262. $this->{$name} = $arguments[0];
  263. } else {
  264. $this->{$name} = $arguments[0];
  265. }
  266. return $this;
  267. }
  268. }