Task.php 7.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241
  1. <?php
  2. namespace app\api\model\plus\bargain;
  3. use app\api\model\plus\bargain\Product as BargainProductModel;
  4. use app\api\model\plus\bargain\ProductSku as BargainSkuModel;
  5. use app\api\model\plus\bargain\Active as ActiveModel;
  6. use app\api\model\settings\Setting as SettingModel;
  7. use app\common\exception\BaseException;
  8. use app\common\model\plus\bargain\Task as TaskModel;
  9. use app\api\model\plus\bargain\TaskHelp as TaskHelpModel;
  10. use app\api\service\bargain\Amount as AmountService;
  11. use app\common\library\helper;
  12. /**
  13. * 砍价任务模型
  14. */
  15. class Task extends TaskModel
  16. {
  17. /**
  18. * 隐藏的字段
  19. * @var array
  20. */
  21. protected $hidden = [
  22. 'peoples',
  23. 'section',
  24. 'is_delete',
  25. 'app_id',
  26. 'update_time',
  27. ];
  28. /**
  29. * 我的砍价列表
  30. */
  31. public function getList($user_id, $params)
  32. {
  33. // 砍价活动列表
  34. return $this->where('user_id', '=', $user_id)->with(['file'])
  35. ->where('status', '=', $params['status'])
  36. ->where('is_delete', '=', 0)
  37. ->order(['create_time' => 'desc'])
  38. ->paginate($params);
  39. }
  40. /**
  41. * 获取砍价任务详情
  42. */
  43. public function getTaskDetail($bargain_task_id, $user = false)
  44. {
  45. // 砍价任务详情
  46. $task = static::detail($bargain_task_id, ['user']);
  47. if (empty($task)) {
  48. throw new BaseException(['msg' => '砍价任务不存在']);
  49. }
  50. // 砍价活动详情
  51. $active = ActiveModel::detail($task['bargain_activity_id']);
  52. // 获取商品详情
  53. $product = BargainProductModel::detail($task['bargain_product_id'], ['product.image.file']);
  54. // 好友助力榜
  55. $help_list = TaskHelpModel::getListByTaskId($bargain_task_id);
  56. // 当前是否为发起人
  57. $is_creater = $this->isCreater($task, $user);
  58. // 当前是否已砍
  59. $is_cut = $this->isCut($help_list, $user);
  60. // 砍价规则
  61. $setting = SettingModel::getBargain();
  62. return compact('task', 'is_creater', 'is_cut', 'active', 'product', 'help_list', 'setting');
  63. }
  64. /**
  65. * 新增砍价任务
  66. */
  67. public function add($user_id, $bargain_activity_id, $bargain_product_id, $bargain_product_sku_id, $product_sku_id)
  68. {
  69. // 获取活动详情
  70. $active = ActiveModel::detail($bargain_activity_id);
  71. // 获取商品详情
  72. $product = BargainProductModel::detail($bargain_product_id, ['product.image']);
  73. // 验证能否创建砍价任务
  74. if (!$this->onVerify($active, $user_id, $product)) {
  75. return false;
  76. }
  77. // 商品sku信息
  78. $product_sku = BargainSkuModel::detail($bargain_product_sku_id, ['productSku']);
  79. // 创建砍价任务
  80. return $this->addTask($user_id, $active, $product, $product_sku);
  81. }
  82. /**
  83. * 创建砍价任务记录
  84. */
  85. private function addTask($user_id, $active, $product, $product_sku)
  86. {
  87. // 分配砍价金额区间
  88. $section = $this->calcBargainSection(
  89. $product_sku['product_price'],
  90. $product_sku['bargain_price'],
  91. $product_sku['bargain_num']
  92. );
  93. // 新增记录
  94. return $this->save([
  95. 'bargain_activity_id' => $active['bargain_activity_id'],
  96. 'user_id' => $user_id,
  97. 'bargain_product_id' => $product['bargain_product_id'],
  98. 'bargain_product_sku_id' => $product_sku['bargain_product_sku_id'],
  99. 'product_price' => $product_sku['product_price'],
  100. 'bargain_price' => $product_sku['bargain_price'],
  101. 'actual_price' => $product_sku['product_price'],
  102. 'peoples' => $product_sku['bargain_num'],
  103. 'image_id' => $product['product']['image'][0]['image_id'],
  104. 'product_name' => $product['product']['product_name'],
  105. 'product_attr' => $product_sku['product_attr'],
  106. 'product_sku_id' => $product_sku['product_sku_id'],
  107. 'cut_people' => 0,
  108. 'section' => $section,
  109. 'cut_money' => 0.00,
  110. 'end_time' => time() + ($active['together_time'] * 3600),
  111. 'app_id' => self::$app_id,
  112. ]);
  113. //增加参与人数
  114. (new BargainProductModel)->where('bargain_product_id', '=', $product['bargain_product_id'])->inc('join_num')->update();
  115. }
  116. /**
  117. * 帮砍一刀
  118. */
  119. public function helpCut($user)
  120. {
  121. // 好友助力榜
  122. $helpList = TaskHelpModel::getListByTaskId($this['bargain_task_id']);
  123. // 当前是否已砍
  124. if ($this->isCut($helpList, $user)) {
  125. $this->error = '您已参与砍价,请不要重复操作';
  126. return false;
  127. }
  128. // 帮砍一刀事件
  129. return $this->transaction(function () use ($user) {
  130. return $this->onCutEvent($user['user_id'], $this->isCreater($this, $user));
  131. });
  132. }
  133. /**
  134. * 砍一刀的金额
  135. */
  136. public function getCutMoney()
  137. {
  138. return $this['section'][$this['cut_people']];
  139. }
  140. /**
  141. * 帮砍一刀事件
  142. */
  143. private function onCutEvent($userId, $isCreater = false)
  144. {
  145. // 砍价金额
  146. $cutMoney = $this->getCutMoney();
  147. // 砍价助力记录
  148. $model = new TaskHelpModel;
  149. $model->add($this, $userId, $cutMoney, $isCreater);
  150. // 实际购买金额
  151. $actualPrice = helper::bcsub($this['actual_price'], $cutMoney);
  152. // 更新砍价任务信息
  153. $this->save([
  154. 'cut_people' => ['inc', 1],
  155. 'cut_money' => ['inc', $cutMoney],
  156. 'actual_price' => $actualPrice,
  157. 'is_floor' => helper::bcequal($actualPrice, $this['bargain_price']),
  158. 'status' => helper::bcequal($actualPrice, $this['bargain_price']) == 0?0:1,
  159. ]);
  160. return true;
  161. }
  162. /**
  163. * 砍价任务标记为已购买
  164. */
  165. public function setIsBuy()
  166. {
  167. return $this->save(['is_buy' => 1]);
  168. }
  169. /**
  170. * 分配砍价金额区间
  171. */
  172. private function calcBargainSection($product_price, $bargain_price, $bargain_num)
  173. {
  174. $AmountService = new AmountService(helper::bcsub($product_price, $bargain_price), $bargain_num);
  175. return $AmountService->handle()['items'];
  176. }
  177. /**
  178. * 当前是否为发起人
  179. */
  180. private function isCreater($task, $user)
  181. {
  182. if ($user === false) return false;
  183. return $user['user_id'] == $task['user_id'];
  184. }
  185. /**
  186. * 当前是否已砍
  187. */
  188. private function isCut($helpList, $user)
  189. {
  190. if ($user === false) return false;
  191. foreach ($helpList as $item) {
  192. if ($item['user_id'] == $user['user_id']) return true;
  193. }
  194. return false;
  195. }
  196. /**
  197. * 验证能否创建砍价任务
  198. */
  199. private function onVerify($active, $userId, $product)
  200. {
  201. // 活动是否开始
  202. if ($active['start_time'] > time()) {
  203. $this->error = '很抱歉,当前砍价活动未开始';
  204. return false;
  205. }
  206. // 活动是否到期合法
  207. if ($active['end_time'] < time()) {
  208. $this->error = '很抱歉,当前砍价活动已结束';
  209. return false;
  210. }
  211. // 是否超过限购
  212. if($this->getUserTaskCount($userId, $product['bargain_product_id']) >= $product['limit_num']){
  213. $this->error = '已超过限购数量';
  214. return false;
  215. }
  216. return true;
  217. }
  218. private function getUserTaskCount($userId, $bargain_product_id){
  219. return (new self())->where('user_id', '=', $userId)
  220. ->where('bargain_product_id', '=', $bargain_product_id)
  221. ->count();
  222. }
  223. }