[self::INTEGRAL_SUBMIT, self::INTEGRAL_PAY]], ['pay_price', 'number', 'on' => [self::INTEGRAL_SUBMIT]], [['pay_price', 'pay_type', 'integral'], 'required', 'on' => [self::INTEGRAL_SUBMIT]], [['order_no', 'pay_code'], 'required', 'on' => [self::INTEGRAL_PAY]], [['store_id', 'integral', 'user_id', 'pay_type'], 'integer', 'on' => [self::INTEGRAL_SUBMIT]], [['order_no', 'pay_code'], 'string', 'on' => [self::INTEGRAL_PAY]] ]; } public function attributeLabels(): array { return [ 'store_id' => '商城ID', 'user_id' => '用户ID', 'integral' => '购买积分', 'order_no' => '积分购买订单', 'pay_price' => '积分充值支付金额', 'pay_type' => '支付方式', 'pay_code' => '支付二维码信息' ]; } /** * 创建积分充值订单 * @return array * @author: hankaige * @Time: 2024/12/3 上午10:45 */ public function submitIntegral(): array { try { if (!$this->validate()) { return ['code' => 1, 'msg' => $this->getErrorSummary(FALSE)[0]]; } $user = User::findOne($this->user_id); if (empty($user)) { throw new Exception('用户不存在'); } $setting = Option::get(OptionSetting::STORE_INTEGRAL, $this->store_id, 'gift', Option::get(OptionSetting::STORE_INTEGRAL, $this->store_id, 'store')['value']); // 计算积分支付金额 $realPayPrice = bcdiv($this->integral, $setting['value'], 2); if ($realPayPrice !== sprintf('%.2f', $this->pay_price)) { throw new Exception('实际支付金额不一致'); } $order = new IntegralRechargeOrder(); $order->store_id = $this->store_id; $order->user_id = $this->user_id; $order->order_no = OrderNo::getOrderNo(OrderNo::INTEGRAL_RECHARGE); $order->pay_price = $realPayPrice; $order->is_pay = 0; $order->pay_type = $this->pay_type; $order->is_delete = 0; $order->created_at = time(); $order->is_cashier = 1; $order->send_integral = $this->integral; $order->create_user_id = get_user_id(); if (!$order->save()) { throw new Exception('订单创建失败'); } if ($this->pay_type == self::CASH_PAY) { $this->payConfirm($order, $user); return [ 'code' => 0, 'msg' => '订单创建成功', 'data' => [ 'need_pay' => 0, 'order_no' => $order->order_no ] ]; } else { return [ 'code' => 0, 'msg' => '订单创建成功', 'data' => [ 'need_pay' => 1, 'order_no' => $order->order_no ] ]; } } catch (\Exception $e) { return ['code' => 1, 'msg' => $e->getMessage()]; } } /** * 充值积分订单微信支付 * @return array * @author: hankaige * @Time: 2024/12/3 上午10:45 */ public function pay(): array { try { if (!$this->validate()) { throw new \Exception($this->getErrorSummary(FALSE)[0]); } $order = IntegralRechargeOrder::find()->where(['order_no' => $this->order_no, 'is_pay' => IntegralRechargeOrder::NOT_PAY, 'is_delete' => IntegralRechargeOrder::NOT_DELETE])->one(); if (empty($order)) { throw new \Exception('订单不存在'); } $user = User::findOne($order->user_id); if ($order->pay_type == self::WECHAT_PAY) { debug_log(is_profit_pay(), 'cashier.log'); if (is_profit_pay()) { $result = WechatNewPay::micropay($order, OrderNo::ORDER_MALL, '积分充值', $order->pay_price, 0, $this->pay_code); } else { $result = WechatPay::micropay($order, OrderNo::ORDER_MALL, '积分充值', $order->pay_price, 0, $this->pay_code); } if ($result['return_code'] == 'SUCCESS') { if ($result['result_code'] === 'FAIL') { // 如果返回结果不是 等待用户输入密码 则直接返回 if ($result['err_code'] == 'USERPAYING') { $result = $this->checkOrderPay($order, 0); } else { return [ 'code' => 1, 'msg' => '微信支付参数错误', 'data' => $result ]; } } if ($result['result_code'] == 'SUCCESS' && $result['result_code'] == 'SUCCESS' && $result['trade_type'] == 'MICROPAY') { $t = \Yii::$app->db->beginTransaction(); $order->transaction_id = $result['transaction_id']; $order->is_pay = 1; $order->pay_time = time(); if (!$order->save()) { $t->rollBack(); throw new \Exception('订单状态更新失败'); } self::payConfirm($user, $order); $t->commit(); return ['code' => 0, 'msg' => '余额充值成功']; } return [ 'code' => 1, 'msg' => '微信支付错误', 'data' => $result ]; } else { throw new \Exception('微信支付失败' . $result['return_msg']); } } else { throw new \Exception('暂不支持该支付方式'); } } catch (\Exception $e) { return ['code' => 1, 'msg' => $e->getMessage()]; } } /** * 校验扫码付款结果 * @param $order * @param $num * @return array|string[]|void * @author: hankaige * @Time: 2024/12/3 上午10:46 */ public function checkOrderPay($order, $num = 0) { sleep(5); if ($num >= 45) { return ['result_code' => 'FAIL', 'data' => '支付超时']; } $num += 5; if (is_profit_pay()) { $result = WechatNewPay::orderQuery($order); } else { $result = WechatPay::orderQuery($order); } if ($result['return_code'] == 'SUCCESS') { if ($result['trade_state'] == 'USERPAYING') { return $this->checkOrderPay($order, $num); } else { return $result; } } } /** * 支付成功后操作 * @param $user * @param $order * @author: hankaige * @Time: 2024/12/3 上午10:46 */ private static function payConfirm($user, $order): void { try { $t = \Yii::$app->db->beginTransaction(); $old_integral = $user->integral; $user->integral += $order->send_integral; $user->total_integral += $order->send_integral; if (!$user->save()) { $t->rollBack(); return; } // 添加积分变动记录 $log = new AccountLog(); $log->store_id = get_store_id(); $log->user_id = $user->id; $log->type = AccountLog::TYPE_INTEGRAL; $log->log_type = AccountLog::LOG_TYPE_INCOME; $log->amount = $order->send_integral; $log->desc = "充值积分, 订单号:{$order->order_no}"; $log->before = $old_integral; $log->after = $user->integral; $log->operator = 'system'; $log->operator_id = 0; $log->operator_type = AccountLog::TYPE_OPERATOR_NORMAL; $log->created_at = time(); $log->order_id = $order->id; $log->order_type = AccountLog::TYPE_PLATFORM_ORDER; $log->save(); // 生成操作记录 $user = User::findOne($order->user_id); CashierActionLog::setLog($order->store_id,get_user_id(),CashierActionLog::RECHARGE_INTEGRAL,'给'.$user->nickname.'用户充值积分'); $t->commit(); return; } catch (\Exception $e) { \Yii::warning('积分充值失败' . $e->getMessage()); } } }