DistributionRewardTrait.php 8.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201
  1. <?php
  2. namespace addons\Distribution\common\traits;
  3. use addons\Distribution\common\enums\ComputingEnum;
  4. use addons\Distribution\common\enums\DistributionEnum;
  5. use addons\Distribution\common\models\Distribution;
  6. use common\enums\AddonsEnum;
  7. use common\enums\StatusEnum;
  8. use common\helpers\FormatHelper;
  9. use common\models\mall\MallAddons;
  10. use common\models\order\OrderDetail;
  11. use services\common\UserWalletService;
  12. use yii\helpers\Json;
  13. trait DistributionRewardTrait
  14. {
  15. /**
  16. * @param array $order
  17. * @return bool
  18. */
  19. public function repurchaseReward(array $order)
  20. {
  21. // 判断插件有没有安装
  22. try {
  23. $mall_id = $order['mall_id'];
  24. $order_id = $order['id'];
  25. $user_id = $order['user_id'];
  26. if (MallAddons::isInstall($mall_id, DistributionEnum::ADDONS_NAME) == 0) return false;
  27. $setting = \Yii::$app->services->setting->addons->get($mall_id, DistributionEnum::ADDONS_NAME, 'basic');
  28. if (empty($setting['level'])) throw new \Exception('没开启经销商');
  29. if (empty($setting['enable_repurchase_reward'])) return false;
  30. if (MallAddons::isInstall($mall_id, AddonsEnum::ADDONS_NAME_AGENT) == 0) return false;
  31. $agent_setting = \Yii::$app->services->setting->addons->get($mall_id, AddonsEnum::ADDONS_NAME_AGENT, 'basic');
  32. if (empty($agent_setting['is_enable'])) throw new \Exception('没开启团队分红');
  33. // 判断自己是否为经销商,如果是经销商,那么自己买了后需要给自己奖励一个一级经销商的奖励金额
  34. $params['where'] = [['order_id' => $order_id], ['user_id' => $user_id], ['mall_id' => $mall_id]];
  35. $order_detail_list = OrderDetail::lists($params);
  36. if (empty($order_detail_list)) throw new \Exception('订单详情不存在');
  37. // 判断自己是否为经销商
  38. $distribution = Distribution::getOne([
  39. 'mall_id' => $mall_id,
  40. 'user_id' => $user_id,
  41. 'status' => StatusEnum::ENABLED
  42. ]);
  43. if (empty($distribution)) throw new \Exception("当前用户非经销商");
  44. $commission_setting = Json::decode($setting['commission']);
  45. $score_setting = Json::decode($setting['score']);
  46. $insert_wallet = [];
  47. $reward_key = 'first_prize';
  48. $is_frozen = $setting['compute_type'] ==ComputingEnum::ORDER_FINISH;
  49. foreach ($order_detail_list as $orderDetail) {
  50. // 奖金
  51. // 需要判断是否独立设置
  52. $reward_amount = $commission_setting[$reward_key];
  53. $reward_score = $score_setting[$reward_key];
  54. if($orderDetail['is_virtual'] == StatusEnum::ENABLED){
  55. //虚拟商品,支付后-直接订单完成,所以直接结算
  56. $is_frozen = false;
  57. }
  58. switch ($setting['computing_method']) {
  59. case 0: // 实际支付金额
  60. if ($commission_setting['is_percent'] == StatusEnum::DISABLED) { // 百分比
  61. $reward_amount = $this->calcByPayAmount($orderDetail['goods_price'], $commission_setting[$reward_key] * 0.01);
  62. }
  63. if ($score_setting['is_percent'] == StatusEnum::DISABLED) { // 百分比
  64. $reward_score = $this->calcByPayAmount($orderDetail['goods_price'], $score_setting[$reward_key] * 0.01);
  65. }
  66. break;
  67. case 1: // 商品售价
  68. if ($commission_setting['is_percent'] == StatusEnum::DISABLED) {
  69. $reward_amount = $this->calcByGoodsSalePrice($orderDetail['price'], $orderDetail['num'], $commission_setting[$reward_key] * 0.01);
  70. }
  71. if ($score_setting['is_percent'] == StatusEnum::DISABLED) { // 百分比
  72. $reward_score = $this->calcByGoodsSalePrice($orderDetail['price'], $orderDetail['num'], $score_setting[$reward_key] * 0.01);
  73. }
  74. break;
  75. case 2: // 商品利润
  76. if ($commission_setting['is_percent'] == StatusEnum::DISABLED) { // 百分比
  77. $reward_amount = $this->calcByGoodsProfit($orderDetail['price'], $orderDetail['cost_price'],
  78. $orderDetail['num'], $commission_setting[$reward_key] * 0.01);
  79. }
  80. if ($score_setting['is_percent'] == StatusEnum::DISABLED) { // 百分比
  81. $reward_score = $this->calcByGoodsProfit($orderDetail['price'], $orderDetail['cost_price'],
  82. $orderDetail['num'], $score_setting[$reward_key] * 0.01);
  83. }
  84. break;
  85. }
  86. if ($reward_amount > 0) {
  87. $insert_wallet[] = $this->pack($user_id, $orderDetail['mall_id'],
  88. UserWalletService::WALLET_TYPE_COMMISSION, $reward_amount, ComputingEnum::DISTRIBUTION_FIRST_PRIZE,
  89. $order['order_no'], $orderDetail['id'], $orderDetail['order_id'], ComputingEnum::DISTRIBUTION_FIRST_PRIZE_REWARD_TYPE, $is_frozen);
  90. }
  91. if ($reward_score > 0) {
  92. $insert_wallet[] = $this->pack($user_id, $orderDetail['mall_id'],
  93. UserWalletService::WALLET_TYPE_SCORE, $reward_amount, ComputingEnum::DISTRIBUTION_FIRST_PRIZE,
  94. $order['order_no'], $orderDetail['id'], $orderDetail['order_id'], ComputingEnum::DISTRIBUTION_FIRST_PRIZE_REWARD_TYPE, $is_frozen);
  95. }
  96. }
  97. if (!empty($insert_wallet)) {
  98. $res = UserWalletService::batchHandleByQueue($insert_wallet);
  99. if (empty($res)) {
  100. throw new \Exception(UserWalletService::getStaticError());
  101. }
  102. }
  103. } catch (\Exception $e) {
  104. \Yii::error(FormatHelper::exception($e, __CLASS__ . "->" . __METHOD__));
  105. }
  106. return true;
  107. }
  108. /**
  109. * @param int $user_id
  110. * @param int $mall_id
  111. * @param string $commission_type
  112. * @param string $amount
  113. * @param string $capital_type
  114. * @param string $order_no
  115. * @param int $source_table_id
  116. * @param int $order_id
  117. * @param string $reward_type
  118. * @param bool $is_frozen
  119. * @return array
  120. */
  121. protected function pack(int $user_id, int $mall_id, string $commission_type, string $amount,
  122. string $capital_type, string $order_no, int $source_table_id, int $order_id, string $reward_type, bool $is_frozen)
  123. {
  124. $commission_name = \Yii::$app->services->setting->mall->get($mall_id, "{$commission_type}.{$commission_type}_name");
  125. if (empty($commission_name)) {
  126. switch ($commission_type) {
  127. case UserWalletService::WALLET_TYPE_COMMISSION:
  128. $commission_name = '佣金';
  129. break;
  130. default:
  131. $commission_name = '';
  132. }
  133. }
  134. $desc = "用户($user_id),获得复购订单($order_id)奖励, 奖励类型: $reward_type, 奖励: $amount $commission_name";
  135. return [
  136. 'mall_id' => $mall_id,
  137. 'user_id' => $user_id,
  138. 'is_frozen' => $is_frozen,
  139. 'wallet_type' => $commission_type,
  140. 'money' => $amount,
  141. 'desc' => $desc,
  142. 'source_table' => OrderDetail::tableName(),
  143. 'source_table_id' => $source_table_id, // 取出订单ID?
  144. 'from_type' => DistributionEnum::ADDONS_NAME,
  145. 'capital_type' => $capital_type,
  146. 'contributor_name' => '',
  147. 'order_no' => $order_no, // 这里需要订单号
  148. ];
  149. }
  150. /**
  151. * @param $goods_price
  152. * @param $cardinality
  153. * @return string
  154. */
  155. protected function calcByPayAmount($goods_price, $cardinality)
  156. {
  157. return bcmul($goods_price, $cardinality, 2);
  158. }
  159. /**
  160. * @param $goods_price
  161. * @param $num
  162. * @param $cardinality
  163. * @return string
  164. */
  165. protected function calcByGoodsSalePrice($goods_price, $num, $cardinality)
  166. {
  167. return bcmul(bcmul($goods_price, $num, 2), $cardinality, 2);
  168. }
  169. /**
  170. * @param $goods_price
  171. * @param $goods_const_price
  172. * @param $num
  173. * @param $cardinality
  174. * @return string
  175. */
  176. protected function calcByGoodsProfit($goods_price, $goods_const_price, $num, $cardinality)
  177. {
  178. return bcmul(bcmul(bcsub($goods_price, $goods_const_price, 2), $num, 2),
  179. $cardinality, 2);
  180. }
  181. }