UserLevelOrder.php 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312
  1. <?php
  2. namespace app\models\user;
  3. use app\models\store\StoreBargain;
  4. use app\models\store\StoreCart;
  5. use app\models\store\StoreCombination;
  6. use app\models\store\StoreCouponUser;
  7. use app\models\store\StoreOrderCartInfo;
  8. use app\models\store\StoreOrderStatus;
  9. use app\models\store\StorePink;
  10. use app\models\store\StoreProduct;
  11. use app\models\store\StoreSeckill;
  12. use app\models\system\SystemStore;
  13. use app\models\system\SystemUserLevel;
  14. use app\models\system\SystemUserTask;
  15. use crmeb\basic\BaseModel;
  16. use crmeb\repositories\PaymentRepositories;
  17. use crmeb\repositories\UserRepository;
  18. use crmeb\traits\ModelTrait;
  19. use think\db\exception\DataNotFoundException;
  20. use think\db\exception\DbException;
  21. use think\db\exception\ModelNotFoundException;
  22. use think\Model;
  23. /**
  24. * TODO 会员等级Model
  25. * Class UserLevel
  26. * @package app\models\user
  27. */
  28. class UserLevelOrder extends BaseModel
  29. {
  30. /**
  31. * 数据表主键
  32. * @var string
  33. */
  34. protected $pk = 'id';
  35. /**
  36. * 模型名称
  37. * @var string
  38. */
  39. protected $name = 'user_level_order';
  40. use ModelTrait;
  41. /**
  42. * 获取用户等级人数
  43. * @param $uids
  44. * @return int
  45. */
  46. public static function setUserLevelOrderCount($uids)
  47. {
  48. $model = new self();
  49. if (is_array($uids)) $model = $model->where('uid', 'in', $uids);
  50. else $model = $model->where('uid', $uids);
  51. return $model->count();
  52. }
  53. /**
  54. * 设置查询初始化条件
  55. * @param string $alias 表别名
  56. * @param null $model 模型实例化对象
  57. * @return UserLevel
  58. */
  59. public static function valiWhere($alias = '', $model = null)
  60. {
  61. $model = is_null($model) ? new self() : $model;
  62. if ($alias) {
  63. $model = $model->alias($alias);
  64. $alias .= '.';
  65. }
  66. return $model->where("{$alias}status", 1)->where("{$alias}is_del", 0);
  67. }
  68. /**
  69. * 设置会员等级
  70. * @param int $uid 用户uid
  71. * @param int $level_id 等级id
  72. * @return UserLevel|bool|Model
  73. * @throws DataNotFoundException
  74. * @throws ModelNotFoundException
  75. * @throws \think\exception\DbException
  76. */
  77. public static function setUserLevel($uid, $level_id)
  78. {
  79. $vipinfo = SystemUserLevel::get($level_id);
  80. if (!$vipinfo) return false;
  81. $userinfo = User::find($uid);
  82. if (!$userinfo) return false;
  83. $add_valid_time = (int)$vipinfo->valid_date * 86400;
  84. $uservipinfo = self::valiWhere()->where('uid', $uid)->where('level_id', $level_id)->find();
  85. //检查是否购买过
  86. if ($uservipinfo) {
  87. $stay = 0;
  88. //剩余时间
  89. if (time() < $uservipinfo->valid_time) $stay = $uservipinfo->valid_time - time();
  90. //如果购买过当前等级的会员过期了.从当前时间开始计算
  91. //过期时效: 剩余时间+当前会员等级时间+当前time
  92. $add_valid_time = $stay + $add_valid_time + time();
  93. $data['is_forever'] = $vipinfo->is_forever;
  94. $data['valid_time'] = $add_valid_time;
  95. User::where('uid', $uid)->update(['level' => $level_id]);
  96. return self::where('uid', $uid)->where('level_id', $level_id)->update($data);
  97. } else {
  98. $data = [
  99. 'is_forever' => $vipinfo->is_forever,
  100. 'status' => 1,
  101. 'is_del' => 0,
  102. 'grade' => $vipinfo->grade,
  103. 'uid' => $uid,
  104. 'add_time' => time(),
  105. 'level_id' => $level_id,
  106. 'discount' => $vipinfo->discount,
  107. ];
  108. if ($data['is_forever'])
  109. $data['valid_time'] = 0;
  110. else
  111. $data['valid_time'] = $add_valid_time + time();
  112. $data['mark'] = '尊敬的用户' . $userinfo['nickname'] . '在' . date('Y-m-d H:i:s', time()) . '成为了' . $vipinfo['name'];
  113. $res = self::create($data);
  114. if (!$res) return false;
  115. User::where('uid', $uid)->update(['level' => $level_id]);
  116. return $res;
  117. }
  118. }
  119. /**
  120. * 获取当前用户会员等级返回当前用户等级id
  121. * @param int $uid 用户uid
  122. * @param int $grade 会员id
  123. * @return bool|mixed
  124. * @throws DataNotFoundException
  125. * @throws ModelNotFoundException
  126. * @throws \think\exception\DbException
  127. */
  128. public static function getUserLevel($uid, $grade = 0)
  129. {
  130. $model = self::valiWhere();
  131. if ($grade) $model = $model->where('grade', '<', $grade);
  132. $level = $model->where('uid', $uid)->order('grade desc')->field('level_id,is_forever,valid_time,id,status,grade')->find();
  133. if (!$level) return false;
  134. if ($level->is_forever) return $level->id;
  135. //会员已经过期
  136. if (time() > $level->valid_time) {
  137. if ($level->status == 1) {
  138. $level->status = 0;
  139. $level->save();
  140. }
  141. return self::getUserLevel($uid, $level->grade);
  142. } else
  143. //会员没有过期
  144. return $level->id;
  145. }
  146. /**
  147. * 获取会员详细信息
  148. * @param $id 会员记录id
  149. * @param string $keyName 字段名
  150. * @return array|mixed|string|Model|null
  151. * @throws DataNotFoundException
  152. * @throws ModelNotFoundException
  153. * @throws \think\exception\DbException
  154. */
  155. public static function getUserLevelInfo($id, $keyName = '')
  156. {
  157. $vipinfo = self::valiWhere('a')->where('a.id', $id)->field('l.id,a.add_time,l.discount,a.level_id,l.name,l.money,l.icon,l.is_pay,l.grade')
  158. ->join('system_user_level l', 'l.id=a.level_id')->find();
  159. if ($keyName) if (isset($vipinfo[$keyName])) return $vipinfo[$keyName]; else return '';
  160. return $vipinfo;
  161. }
  162. /**
  163. * 获取当前用户已成为的vip id
  164. * @param $uid 用户id
  165. * @return array
  166. */
  167. public static function getUserLevelIds($uid)
  168. {
  169. return self::valiWhere()->group('level_id')->where('uid', $uid)->order('grade asc')->column('level_id', 'level_id');
  170. }
  171. /**
  172. * 余额支付
  173. * @param $order_id
  174. * @param $uid
  175. * @param string $formId
  176. * @return bool
  177. * @throws \think\Exception
  178. * @throws DataNotFoundException
  179. * @throws ModelNotFoundException
  180. * @throws \think\exception\DbException
  181. */
  182. public static function yuePay($order_id, $uid, $formId = '')
  183. {
  184. $orderInfo = self::where('uid', $uid)->where('order_id', $order_id)->where('is_del', 0)->find();
  185. if (!$orderInfo) return self::setErrorInfo('订单不存在!');
  186. if ($orderInfo['paid']) return self::setErrorInfo('该订单已支付!');
  187. // if($orderInfo['pay_type'] != 'yue') return self::setErrorInfo('该订单不能使用余额支付!');
  188. $userInfo = User::getUserInfo($uid);
  189. if ($userInfo['now_money'] < $orderInfo['pay_price'])
  190. return self::setErrorInfo(['status' => 'pay_deficiency', 'msg' => '余额不足' . floatval($orderInfo['pay_price'])]);
  191. self::beginTrans();
  192. $res1 = false !== User::bcDec($uid, 'now_money', $orderInfo['pay_price'], 'uid');
  193. $res2 = UserBill::expend('购买商品', $uid, 'now_money', 'pay_product', $orderInfo['pay_price'], $orderInfo['id'], $userInfo['now_money'], '余额支付' . floatval($orderInfo['pay_price']) . '元购买商品');
  194. $res3 = self::paySuccess($order_id, 'yue', $formId);//余额支付成功
  195. try {
  196. PaymentRepositories::yuePayProduct($userInfo, $orderInfo);
  197. } catch (\Exception $e) {
  198. self::rollbackTrans();
  199. return self::setErrorInfo($e->getMessage());
  200. }
  201. $res = $res1 && $res2 && $res3;
  202. self::checkTrans($res);
  203. return $res;
  204. }
  205. /**
  206. * 微信支付 为 0元时
  207. * @param $order_id
  208. * @param $uid
  209. * @param string $formId
  210. * @return bool
  211. * @throws \think\Exception
  212. * @throws DataNotFoundException
  213. * @throws ModelNotFoundException
  214. * @throws \think\exception\DbException
  215. */
  216. public static function jsPayPrice($order_id, $uid, $formId = '')
  217. {
  218. $orderInfo = self::where('uid', $uid)->where('order_id', $order_id)->where('is_del', 0)->find();
  219. if (!$orderInfo) return self::setErrorInfo('订单不存在!');
  220. if ($orderInfo['paid']) return self::setErrorInfo('该订单已支付!');
  221. $userInfo = User::getUserInfo($uid);
  222. self::beginTrans();
  223. $res1 = UserBill::expend('购买商品', $uid, 'now_money', 'pay_product', $orderInfo['pay_price'], $orderInfo['id'], $userInfo['now_money'], '微信支付' . floatval($orderInfo['pay_price']) . '元购买商品');
  224. $res2 = self::paySuccess($order_id, 'weixin', $formId);//微信支付为0时
  225. $res = $res1 && $res2;
  226. self::checkTrans($res);
  227. return $res;
  228. }
  229. /**
  230. * //TODO 支付成功后
  231. * @param $orderId
  232. * @param string $paytype
  233. * @param string $formId
  234. * @return bool
  235. * @throws DataNotFoundException
  236. * @throws DbException
  237. * @throws ModelNotFoundException
  238. */
  239. public static function paySuccess($orderId, $paytype = 'weixin', $formId = '')
  240. {
  241. $order = self::where('order_id', $orderId)->find();
  242. $resPink = true;
  243. $res1 = self::where('order_id', $orderId)->update(['paid' => 1, 'pay_type' => $paytype, 'pay_time' => time(), 'is_del' => 0, 'is_system_del' => 0, 'mark' => '']);//订单改为支付
  244. if ($order->combination_id && $res1 && !$order->refund_status) $resPink = StorePink::createPink($order);//创建拼团
  245. $oid = self::where('order_id', $orderId)->value('id');
  246. StoreOrderStatus::status($oid, 'pay_success', '用户付款成功');
  247. $now_money = User::where('uid', $order['uid'])->value('now_money');
  248. UserBill::expend('购买商品', $order['uid'], 'now_money', 'pay_money', $order['pay_price'], $order['id'], $now_money, '支付' . floatval($order['pay_price']) . '元购买商品');
  249. //支付成功后
  250. event('OrderPaySuccess', [$order, $formId]);
  251. $res = $res1 && $resPink && UserSpread::setSpreadSure($order['uid']) && User::backOrderBrokerage($order);
  252. return false !== $res;
  253. }
  254. // 创建会员订单
  255. public static function CreateOrder($uid, $level_id)
  256. {
  257. self::beginTrans();
  258. try {
  259. $orderInfo = [
  260. 'uid' => $uid,
  261. 'order_id' => self::getNewOrderId(),
  262. // 'mer_id' =>
  263. ];
  264. if ($shipping_type === 2) {
  265. $orderInfo['verify_code'] = self::getStoreCode();
  266. $orderInfo['store_id'] = SystemStore::getStoreDispose($storeId, 'id');
  267. if (!$orderInfo['store_id']) return self::setErrorInfo('暂无门店无法选择门店自提!', true);
  268. }
  269. $order = self::create($orderInfo);
  270. if (!$order) return self::setErrorInfo('订单生成失败!', true);
  271. $res5 = true;
  272. foreach ($cartInfo as $cart) {
  273. //减库存加销量
  274. if ($combinationId) $res5 = $res5 && StoreCombination::decCombinationStock($cart['cart_num'], $combinationId, isset($cart['productInfo']['attrInfo']) ? $cart['productInfo']['attrInfo']['unique'] : '');
  275. else if ($seckill_id) $res5 = $res5 && StoreSeckill::decSeckillStock($cart['cart_num'], $seckill_id, isset($cart['productInfo']['attrInfo']) ? $cart['productInfo']['attrInfo']['unique'] : '');
  276. else if ($bargain_id) $res5 = $res5 && StoreBargain::decBargainStock($cart['cart_num'], $bargain_id, isset($cart['productInfo']['attrInfo']) ? $cart['productInfo']['attrInfo']['unique'] : '');
  277. else $res5 = $res5 && StoreProduct::decProductStock($cart['cart_num'], $cart['productInfo']['id'], isset($cart['productInfo']['attrInfo']) ? $cart['productInfo']['attrInfo']['unique'] : '');
  278. }
  279. //保存购物车商品信息
  280. $res4 = false !== StoreOrderCartInfo::setCartInfo($order['id'], $cartInfo);
  281. //购物车状态修改
  282. $res6 = false !== StoreCart::where('id', 'IN', $cartIds)->update(['is_pay' => 1]);
  283. if (!$res4 || !$res5 || !$res6) return self::setErrorInfo('订单生成失败!', true);
  284. //自动设置默认地址
  285. UserRepository::storeProductOrderCreateEbApi($order, compact('cartInfo', 'addressId'));
  286. self::clearCacheOrderInfo($uid, $key);
  287. self::commitTrans();
  288. StoreOrderStatus::status($order['id'], 'cache_key_create_order', '订单生成');
  289. return $order;
  290. } catch (\PDOException $e) {
  291. self::rollbackTrans();
  292. return self::setErrorInfo('生成订单时SQL执行错误错误原因:' . $e->getMessage());
  293. } catch (\Exception $e) {
  294. self::rollbackTrans();
  295. return self::setErrorInfo('生成订单时系统错误错误原因:' . $e->getMessage());
  296. }
  297. }
  298. }