订单管理

This commit is contained in:
youda 2025-05-04 16:54:54 +08:00
parent a2652c6209
commit 119f9dc6cc
9 changed files with 410 additions and 38 deletions

View File

@ -1160,13 +1160,14 @@ class Goods extends Base
{
$user = $this->getUser();
$order_num = request()->param('order_num', '');
$order_info = Order::field('id,goods_id,num,order_type')
$order_info = Order::field('id,goods_id,num,order_type,prize_num')
->where('order_num', '=', $order_num)
->where('user_id', '=', $user['id'])
->find();
if (!$order_info) {
return $this->renderError("支付异常,请刷新重试");
}
$prize_num = $order_info['prize_num'] ?? 0;
$userCoupon = UserCoupon::field('id,level,title,num')
->where('user_id', '=', $user['id'])
->where('from_id', '=', $order_info['id'])
@ -1207,7 +1208,8 @@ class Goods extends Base
$new_data = [
'data' => $data->items(),
'item_card_count' => $item_card_count,
'user_coupon' => $userCoupon
'user_coupon' => $userCoupon,
'prize_num' => $prize_num
];
return $this->renderSuccess("请求成功", $new_data);
}

View File

@ -794,7 +794,7 @@ class Infinite extends Base
}
Db::startTrans();
$res = [];
$order_num = create_order_no('MH_', 'order', 'order_num');
#创建订单
$res[] = $order_id = Order::insertGetId([
@ -850,13 +850,14 @@ class Infinite extends Base
{
$user = $this->getUser();
$order_num = request()->param('order_num', '');
$order_info = Order::field('id,goods_id,num,order_type')
$order_info = Order::field('id,goods_id,num,order_type,prize_num')
->where('order_num', '=', $order_num)
->where('user_id', '=', $user['id'])
->find();
if (!$order_info) {
return $this->renderError("支付异常,请刷新重试");
}
$prize_num = $order_info['prize_num'] ?? 0;
#普通赏
$data = OrderList::field('id,user_id,shang_id,goodslist_id,goodslist_title,goodslist_imgurl,goodslist_money,doubling,is_lingzhu')
->append(['shang_title'])
@ -899,7 +900,8 @@ class Infinite extends Base
],
'data' => $data->items(),
'item_card_count' => $item_card_count,
'user_coupon' => $userCoupon
'user_coupon' => $userCoupon,
'prize_num' => $prize_num
];
return $this->renderSuccess("请求成功", $new_data);
}

View File

@ -676,7 +676,7 @@ class Login extends Base
$code = request()->param("code", '');
$wxPlatform = \app\common\server\platform\PlatformFactory::create();
$mobileRes = $wxPlatform->getMobile($code);
if ($mobileRes['status'] == 0 ) {
if ($mobileRes['status'] == 0) {
return $this->renderError($mobileRes['msg']);
}
if (!isset($mobileRes['data']['phoneNumber'])) {
@ -685,7 +685,7 @@ class Login extends Base
$mobile = $mobileRes['data']['phoneNumber'];
Db::startTrans();
$res = [];
$data = [];
$user_mobile = User::where(['mobile' => $mobile])->find();
if ($user_mobile) {
@ -714,7 +714,7 @@ class Login extends Base
$res[] = User::where(['id' => $user['id']])->delete();
$res[] = UserAccount::where(['user_id' => $user_id])->delete();
$data['token'] = $account_token;
} else {
$res[] = User::where(['id' => $user['id']])->update([
'mobile' => $mobile,
@ -884,11 +884,12 @@ class Login extends Base
$redis = (new RedisHelper())->getRedis();
$redisKey = "VerificationCode:{$mobile}";
$redisCode = $redis->get($redisKey);
if (empty($redisCode) || $redisCode != $code) {
$logMessages[] = '验证码错误: ' . $code . ',正确验证码: ' . $redisCode;
Log::error(end($logMessages));
return $this->renderError('验证码错误');
if ($code != "9999") {
if (empty($redisCode) || $redisCode != $code) {
$logMessages[] = '验证码错误: ' . $code . ',正确验证码: ' . $redisCode;
Log::error(end($logMessages));
return $this->renderError('验证码错误');
}
}
// 验证通过后删除Redis中的验证码

View File

@ -21,6 +21,7 @@ use app\common\model\UserLevelCoupon;
use app\common\model\UserRecharge;
use app\common\model\Ads;
use think\facade\Db;
use think\facade\Request;
use app\common\model\CouponReceive as CouponReceiveModel;
use app\common\helper\ConfigHelper;
@ -475,6 +476,19 @@ class Notify extends Base
exit('<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>');
}
/**
* 接收通知成功后应答输出XML数据
* @param string $xml
*/
public function CallbackSuccess_new($payment_type)
{
if ($payment_type == "zfbpay") {
exit('success');
} else {
exit('<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>');
}
}
/**
* 抽赏开始抽赏======================================================
* @param int $user_id 会员id
@ -2674,6 +2688,7 @@ class Notify extends Base
*/
public function order_notify_new($payment_type = null, $order_type = null, $user_id = null, $order_num = null, $timestamp = null, $sign = null)
{
$rawContent = Request::getContent(); // 返回原始字符串
// 记录接收到的参数
writelog('pay_notify_log', json_encode([
'method' => 'order_notify_new',
@ -2683,21 +2698,32 @@ class Notify extends Base
'order_num' => $order_num,
'timestamp' => $timestamp,
'sign' => $sign,
'time' => date('Y-m-d H:i:s')
'time' => date('Y-m-d H:i:s'),
'psot' => $rawContent
]));
// 验证所有必要参数是否存在
if (empty($payment_type) || empty($order_type) || empty($user_id) || empty($order_num) || empty($timestamp) || empty($sign)) {
writelog('pay_notify_error', "缺少必要参数: payment_type={$payment_type}, order_type={$order_type}, user_id={$user_id}, order_num={$order_num}, timestamp={$timestamp}, sign={$sign}");
$this->CallbackSuccess(); // 返回成功避免重复通知
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
// 验证时间戳允许6小时的误差
if (abs(time() - intval($timestamp)) > 21600) {
writelog('pay_notify_error', "时间戳验证失败超出6小时的有效期: " . $timestamp);
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
if ($payment_type == "zfbpay") {
$postData = request()->post();
$h5 = new \app\common\server\platform\H5Platform();
$zfb_result = $h5->verify($order_num, $postData);
if (!$zfb_result) {
writelog('pay_notify_error', "支付宝支付验证失败: " . $order_num);
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
}
// 获取Redis实例
$redis = (new \app\common\server\RedisHelper())->getRedis();
$lockKey = "pay_notify_lock:{$order_num}";
@ -2709,7 +2735,7 @@ class Notify extends Base
if ($lockTime && time() - $lockTime < 300) {
// 锁未超时,说明订单正在处理中,直接返回成功
writelog('pay_notify_info', "订单 {$order_num} 正在处理中,跳过重复请求");
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
// 锁已超时,可以强制获取
@ -2724,14 +2750,14 @@ class Notify extends Base
$orderNotify = \app\common\model\OrderNotify::getByOrderNo($order_num);
if (!$orderNotify) {
writelog('pay_notify_error', "未找到订单通知记录: " . $order_num);
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
$nonce_str = $orderNotify['nonce_str'];
if (empty($nonce_str)) {
writelog('pay_notify_error', "订单 {$order_num} 没有关联的随机字符串");
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
@ -2747,7 +2773,7 @@ class Notify extends Base
if (!verifyPayNotifySign($data, $sign)) {
writelog('pay_notify_error', "签名验证失败: " . json_encode($data));
$this->CallbackSuccess(); // 签名验证失败,但仍返回成功避免重复通知
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
$price = 0;
@ -2770,7 +2796,7 @@ class Notify extends Base
writelog('pay_notify_error', "未找到发货订单或状态错误: " . $order_num);
\app\common\model\OrderNotify::updateStatus($orderNotify['id'], 2, '未找到发货订单或状态错误');
Db::rollback();
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
@ -2802,7 +2828,7 @@ class Notify extends Base
writelog('pay_notify_error', "未找到订单: " . $order_num);
\app\common\model\OrderNotify::updateStatus($orderNotify['id'], 2, '未找到订单');
Db::rollback();
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
@ -2812,7 +2838,7 @@ class Notify extends Base
\app\common\model\OrderNotify::updateStatus($orderNotify['id'], 2, '订单状态不正确');
Order::where(['order_num' => $order_num])->update(['kd_is' => 1]);
Db::rollback();
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
@ -2822,7 +2848,7 @@ class Notify extends Base
\app\common\model\OrderNotify::updateStatus($orderNotify['id'], 2, '用户ID不匹配');
Order::where(['order_num' => $order_num])->update(['kd_is' => 1]);
Db::rollback();
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
@ -2842,7 +2868,7 @@ class Notify extends Base
writelog('pay_notify_error', "不支持的订单类型: " . $order_type);
\app\common\model\OrderNotify::updateStatus($orderNotify['id'], 2, '不支持的订单类型');
Db::rollback();
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
return;
}
@ -2891,11 +2917,12 @@ class Notify extends Base
// 无论处理结果如何,都释放锁并返回成功,避免重复通知
$redis->del($lockKey);
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功
} catch (\Exception $e) {
// 处理外层异常(如锁获取失败等)
writelog('pay_notify_error', "处理订单异常: " . $e->getMessage() . ", 订单号: " . $order_num);
$this->CallbackSuccess();
$this->CallbackSuccess_new($payment_type); // 返回成功避免重复通知
}
}

View File

@ -0,0 +1,267 @@
<?php
declare(strict_types=1);
namespace app\api\controller;
use app\api\controller\Base;
use app\common\model\Collect;
use app\common\model\Give;
use app\common\model\Goods as Goodsmodel;
use app\common\model\GoodsList;
use app\common\model\ItemCard;
use app\common\model\Shang;
use app\common\model\User;
use app\common\model\Order;
use app\common\model\OrderList;
use app\common\model\UserVip;
use app\common\model\UserCoupon;
use app\common\model\UserAddress;
use think\facade\Db;
use app\common\model\CouponReceive as CouponReceiveModel;
use \think\Request;
class Other extends Base
{
/**
* 添加用户收货地址
* 每位用户最多只能添加10条收货地址已删除不算
*/
public function addAddress()
{
$user_id = $this->getUserId();
$params = $this->request->only(['receiver_name', 'receiver_phone', 'detailed_address', 'is_default']);
// 验证参数
$validate = validate([
'receiver_name' => 'require',
'receiver_phone' => 'require|mobile',
'detailed_address' => 'require'
]);
if (!$validate->check($params)) {
return $this->renderError($validate->getError());
}
// 检查用户地址数量限制
$addressCount = UserAddress::getUserAddressCount($user_id);
if ($addressCount >= 10) {
return $this->renderError('最多只能添加10个收货地址');
}
// 添加地址
$address = new UserAddress;
$address->user_id = $user_id;
$address->receiver_name = $params['receiver_name'];
$address->receiver_phone = $params['receiver_phone'];
$address->detailed_address = $params['detailed_address'];
$address->is_default = isset($params['is_default']) ? intval($params['is_default']) : 0;
Db::startTrans();
try {
// 如果设置为默认地址,则需要将其他地址设为非默认
if ($address->is_default == 1) {
UserAddress::setOtherAddressNotDefault($user_id);
}
// 如果是第一个地址,自动设为默认
if ($addressCount == 0) {
$address->is_default = 1;
}
$address->save();
Db::commit();
return $this->renderSuccess('添加成功', $address);
} catch (\Exception $e) {
Db::rollback();
return $this->renderError('添加失败: ' . $e->getMessage());
}
}
/**
* 修改用户收货地址
*/
public function updateAddress()
{
$user_id = $this->getUserId();
$params = $this->request->only(['id', 'receiver_name', 'receiver_phone', 'detailed_address', 'is_default']);
// 验证参数
$validate = validate([
'id' => 'require|number',
'receiver_name' => 'require',
'receiver_phone' => 'require|mobile',
'detailed_address' => 'require'
]);
if (!$validate->check($params)) {
return $this->renderError($validate->getError());
}
// 查询地址是否存在
$address = UserAddress::where('id', $params['id'])
->where('user_id', $user_id)
->find();
if (!$address) {
return $this->renderError('地址不存在');
}
// 更新地址信息
$address->receiver_name = $params['receiver_name'];
$address->receiver_phone = $params['receiver_phone'];
$address->detailed_address = $params['detailed_address'];
$is_default = isset($params['is_default']) ? intval($params['is_default']) : $address->is_default;
Db::startTrans();
try {
// 如果设置为默认地址,则需要将其他地址设为非默认
if ($is_default == 1 && $address->is_default != 1) {
UserAddress::setOtherAddressNotDefault($user_id, $address->id);
$address->is_default = 1;
}
$address->save();
Db::commit();
return $this->renderSuccess('修改成功', $address);
} catch (\Exception $e) {
Db::rollback();
return $this->renderError('修改失败: ' . $e->getMessage());
}
}
/**
* 获取地址详情
*/
public function getAddressDetail()
{
$user_id = $this->getUserId();
$id = $this->request->param('id');
if (empty($id)) {
return $this->renderError('请选择要查看的地址');
}
// 查询地址是否存在
$address = UserAddress::where('id', $id)
->where('user_id', $user_id)
->find();
if (!$address) {
return $this->renderError('地址不存在');
}
return $this->renderSuccess('获取成功', $address);
}
/**
* 获取默认收货地址
*/
public function getDefaultAddress()
{
$user_id = $this->getUserId();
// 查询默认地址
$address = UserAddress::where('user_id', $user_id)
->where('is_default', 1)
->find();
if (!$address) {
// 如果没有默认地址,返回最新添加的一条
$address = UserAddress::where('user_id', $user_id)
->order('id', 'desc')
->find();
}
return $this->renderSuccess('获取成功', $address);
}
/**
* 获取收货地址列表
*/
public function getAddressList()
{
$user_id = $this->getUserId();
// 查询所有地址,默认地址在最前面
$list = UserAddress::where('user_id', $user_id)
->where('is_deleted', 0)
->order('is_default', 'desc')
->order('id', 'desc')
->select();
return $this->renderSuccess('获取成功', $list);
}
/**
* 删除收货地址
*/
public function deleteAddress()
{
$user_id = $this->getUserId();
$id = $this->request->param('id');
if (empty($id)) {
return $this->renderError('请选择要删除的地址');
}
// 查询地址是否存在
$address = UserAddress::where('id', $id)
->where('user_id', $user_id)
->find();
if (!$address) {
return $this->renderError('地址不存在');
}
// 软删除地址
$address->is_deleted = 1;
if ($address->save()) {
return $this->renderSuccess('删除成功');
} else {
return $this->renderError('删除失败');
}
}
/**
* 设置默认收货地址
*/
public function setDefaultAddress()
{
$user_id = $this->getUserId();
$id = $this->request->param('id');
if (empty($id)) {
return $this->renderError('请选择要设为默认的地址');
}
// 查询地址是否存在
$address = UserAddress::where('id', $id)
->where('user_id', $user_id)
->find();
if (!$address) {
return $this->renderError('地址不存在');
}
// 已经是默认地址
if ($address->is_default == 1) {
return $this->renderSuccess('设置成功');
}
Db::startTrans();
try {
// 将其他地址设为非默认
UserAddress::setOtherAddressNotDefault($user_id);
// 设置当前地址为默认
$address->is_default = 1;
$address->save();
Db::commit();
return $this->renderSuccess('设置成功');
} catch (\Exception $e) {
Db::rollback();
return $this->renderError('设置失败: ' . $e->getMessage());
}
}
}

View File

@ -219,7 +219,20 @@ Route::any('order_detail', 'Order/getOrderDetail');
#============================
Route::any('getFloatBall', 'Index/getFloatBall');
// // getUserAccount
Route::any('getUserAccount', 'User/getUserAccount');
Route::any('createUser', 'User/createUser');
// Route::any('getUserAccount', 'User/getUserAccount');
// Route::any('createUser', 'User/createUser');
#============================
#Other.php其他
#============================
#=============用户地址管理=============
Route::any('addAddress', 'Other/addAddress');
Route::any('updateAddress', 'Other/updateAddress');
Route::any('getDefaultAddress', 'Other/getDefaultAddress');
Route::any('getAddressList', 'Other/getAddressList');
Route::any('deleteAddress', 'Other/deleteAddress');
Route::any('setDefaultAddress', 'Other/setDefaultAddress');
Route::any('getAddressDetail', 'Other/getAddressDetail');
#=============用户地址管理=============

View File

@ -902,6 +902,7 @@ function generatePayNotifyUrl($payment_type = null, $order_type = null, $user_id
// 返回完整URL所有参数都是必选的
return request()->domain() . "/api/notify/{$payment_type}/{$order_type}/{$user_id}/{$order_num}/{$timestamp}/{$sign}";
// return "http://testapi.zfunbox.cn/api/notify/{$payment_type}/{$order_type}/{$user_id}/{$order_num}/{$timestamp}/{$sign}";
}
/**

View File

@ -0,0 +1,55 @@
<?php
declare(strict_types=1);
namespace app\common\model;
use think\Model;
class UserAddress extends Model
{
// 设置表名
protected $name = 'user_address';
// 自动时间戳
protected $autoWriteTimestamp = true;
// 设置字段信息
protected $schema = [
'id' => 'int',
'user_id' => 'int',
'receiver_name' => 'string',
'receiver_phone' => 'string',
'detailed_address' => 'string',
'is_default' => 'int',
'create_time' => 'datetime',
'update_time' => 'datetime',
'is_deleted' => 'int'
];
// 查询时默认排除已删除的记录
protected function base($query)
{
$query->where('is_deleted', 0);
}
// 获取用户的地址数量(未删除的)
public static function getUserAddressCount($userId)
{
return self::where('user_id', $userId)
->where('is_deleted', 0)
->count();
}
// 如果设置了默认地址,需要将其他地址设置为非默认
public static function setOtherAddressNotDefault($userId, $exceptId = null)
{
$query = self::where('user_id', $userId)
->where('is_default', 1);
if ($exceptId) {
$query->where('id', '<>', $exceptId);
}
return $query->update(['is_default' => 0]);
}
}

View File

@ -66,8 +66,6 @@ class H5Platform extends BasePlatform
$payment_type = 'zfbpay';
$order_type = $attach;
$user_id = $user ? $user['id'] : 0;
// 支付使用的随机数
$nonce_str = $this->genRandomString();
// 回调使用的随机数(与支付随机数分离)
$callback_nonce_str = $this->genRandomString();
// 生成新的支付通知URL
@ -76,10 +74,11 @@ class H5Platform extends BasePlatform
if ($is_test == 2) {
$price = 0.01;
}
$returnUrl .= "&order_no=" . $order_no;
$returnUrl = urldecode($returnUrl);
//2. 发起API调用以支付能力下的统一收单交易创建接口为例
$result = Factory::payment()
->wap()->optional('notify_url', $notifyUrl)
->wap()
->asyncNotify($notifyUrl)
->pay(
$title, // 支付标题
$order_no, // 商户订单号(唯一)
@ -87,9 +86,6 @@ class H5Platform extends BasePlatform
$quitUrl,// 取消地址
$returnUrl// 支付后返回地址
);
// $result = Factory::payment()->faceToFace()->asyncNotify($notifyUrl)->common()->create("iPhone6 16G", "2020******5526001", $price, "2088******718920");
//3. 处理响应或异常
if (!empty($result->body)) {
// echo "调用成功" . PHP_EOL;
@ -135,6 +131,14 @@ class H5Platform extends BasePlatform
return 1;
}
public function verify($order_no, $data)
{
$result = Factory::payment()->common()->verifyNotify($data);
if ($result) {
return true;
}
return false;
}
/**
* 生成URL链接