AchievementLogic.php 30 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735
  1. <?php
  2. namespace addons\Achievement\common\logic;
  3. use addons\Achievement\common\enums\AchievementEnum;
  4. use addons\Achievement\common\models\AchievementAwardLog;
  5. use addons\Achievement\common\models\AchievementAwardLogExtra;
  6. use addons\Achievement\common\models\AchievementGrantLog;
  7. use addons\Achievement\common\models\AchievementUser;
  8. use common\enums\AddonsEnum;
  9. use common\enums\StatusEnum;
  10. use common\enums\UserWalletEnum;
  11. use common\models\mall\MallAddons;
  12. use common\models\user\UserPartitionRelationship;
  13. use common\models\user\UserRelationshipLog;
  14. use common\traits\ErrorTrait;
  15. use services\common\UserWalletService;
  16. use Exception;
  17. class AchievementLogic
  18. {
  19. use ErrorTrait;
  20. /**
  21. * @desc:业绩进入待结算
  22. * @Author: hua
  23. * @Date: 2022/3/8
  24. * @Time: 16:45
  25. * @Copyright: copyright (c) 2021 广东七件事集团
  26. * @param $grant_id
  27. * @return bool
  28. * @throws \Exception
  29. */
  30. public static function toBeSettled($grant_id)
  31. {
  32. $t = \Yii::$app->db->beginTransaction();
  33. try {
  34. $grant = AchievementGrantLog::findOne(['id' => $grant_id, 'status' => StatusEnum::ENABLED, 'is_wait' => 0]);
  35. if (empty($grant)) throw new \Exception("规则不存在");
  36. //判断业绩奖励是否开启
  37. $configs = \Yii::$app->services->setting->addons->get($grant['mall_id'], AddonsEnum::ADDONS_NAME_ACHIEVEMENT, 'basic');
  38. if (empty($configs['status'])) throw new \Exception("业绩奖励没开启");
  39. $list = AchievementAwardLog::findAll(['grant_id' => $grant_id, 'mall_id' => $grant['mall_id'], 'status' => StatusEnum::ENABLED]);
  40. $user_id_arr = array_column($list, 'user_id');
  41. $sum_list = AchievementAwardLog::lists([
  42. 'where' => [
  43. ['user_id' => $user_id_arr],
  44. ['mall_id' => $grant['mall_id']],
  45. ['status' => StatusEnum::ENABLED],
  46. ['is_end' => 1]
  47. ],
  48. 'index' => 'user_id',
  49. 'group' => 'user_id',
  50. 'select' => 'sum(award_money) as money,user_id'
  51. ]);
  52. $total = 0;//总业绩
  53. $user_num = 0;
  54. $sum_award = 0;
  55. //计算奖励
  56. foreach ($list as $k => $v) {
  57. //统计团队业绩
  58. $user_id = $v['user_id'];
  59. $money = 0;
  60. $offset = 1;
  61. $limit = 1000;
  62. $params['select'] = 'user_id,deep';
  63. list($tree, $deep, $all_tree, $all_tree_arr) = UserPartitionRelationship::getTree($user_id);
  64. while ($child_list = UserPartitionRelationship::batchGetTeamData($offset, $limit, $tree, $params)) {
  65. $user_ids = array_column($child_list, 'user_id');
  66. $team_achievement_user_list = AchievementUser::lists(['where' => [['user_id' => $user_ids], ['status' => StatusEnum::ENABLED]]]);
  67. $team_ids = array_column($team_achievement_user_list, 'user_id');
  68. //获取到下级的所有业绩
  69. $personal_achievement = AchievementAwardLog::find()->where(['mall_id' => $v['mall_id'], 'status' => StatusEnum::ENABLED, 'grant_id' => $grant['id']])
  70. ->andWhere(['in', 'user_id', $team_ids])->sum('personal_achievement');
  71. if (!empty($personal_achievement)) $money += $personal_achievement;
  72. $offset++;
  73. }
  74. $v->team_achievement += $money;
  75. $v->achievement_sum += $money;
  76. $award = self::confirmProportion($grant['award_proportion'], $v['achievement_sum'], $v['personal_achievement'], $grant['settlement_mode']);
  77. $v->award_proportion = $award['proportion'];
  78. if ($grant['settlement_mode'] == 0) {
  79. //不含极差
  80. $v->award_money = $award['money'];
  81. $v->is_end = 1;
  82. //总计
  83. $sum_money = 0;
  84. if (isset($sum_list[$v['user_id']])) $sum_money = $sum_list[$v['user_id']]['money'];
  85. $sum_money = $sum_money + $award['money'];
  86. $v->award_sum = $sum_money;
  87. } else {
  88. $v->parent_team = self::getParentAchievementUser($user_id);
  89. $v->proportion_money = $award['money'];
  90. }
  91. if (!$v->save()) throw new \Exception("业绩修改奖励日志失败");
  92. $total += $v->personal_achievement;
  93. $user_num++;
  94. $sum_award += $award['money'];
  95. }
  96. if ($grant->settlement_mode == 1) $sum_award = self::planB($grant, $list, $user_id_arr);//极差
  97. //平级奖励
  98. $grant->total_performance = $total;
  99. $grant->user_num = $user_num;
  100. $grant->award_money = $sum_award;
  101. $grant->is_wait = 1;
  102. if (!$grant->save()) throw new \Exception("业绩修改规则日志失败");
  103. $t->commit();
  104. return true;
  105. } catch (Exception $e) {
  106. $t->rollBack();
  107. \Yii::error('业绩待结算失败' . PHP_EOL . $e->getFile() . '(' . $e->getLine() . ')' . PHP_EOL . "message:" . $e->getMessage());
  108. self::$static_error = '业绩待结算失败' . PHP_EOL . $e->getFile() . '(' . $e->getLine() . ')' . PHP_EOL . "message:" . $e->getMessage();
  109. return true;
  110. }
  111. }
  112. /**
  113. * @desc:极差的结算方案
  114. * @Author: hua
  115. * @Date: 2022/3/8
  116. * @Time: 16:44
  117. * @Copyright: copyright (c) 2021 广东七件事集团
  118. * @param $grant
  119. * @param $list
  120. * @param $user_id_arr
  121. * @return int|mixed
  122. * @throws \Exception
  123. */
  124. public static function planB($grant, $list, $user_id_arr)
  125. {
  126. $sum_award = 0;
  127. $achievement_award_log_list = AchievementAwardLog::lists([
  128. 'where' => [
  129. ['parent_team' => $user_id_arr],
  130. ['mall_id' => $grant['mall_id']],
  131. ['grant_id' => $grant['id']],
  132. ['status' => StatusEnum::ENABLED],
  133. ],
  134. 'index' => 'parent_team',
  135. 'group' => 'parent_team',
  136. 'select' => 'sum(proportion_money) as money,parent_team',
  137. ]);
  138. $achievement_award_log_list_end = AchievementAwardLog::lists([
  139. 'where' => [
  140. ['parent_team' => $user_id_arr],
  141. ['mall_id' => $grant['mall_id']],
  142. ['status' => StatusEnum::ENABLED],
  143. ['is_end' => 1],
  144. ],
  145. 'index' => 'user_id',
  146. 'group' => 'user_id',
  147. 'select' => 'sum(proportion_money) as money,user_id',
  148. ]);
  149. foreach ($list as $k => $v) {
  150. //查看所有下级的结算金额
  151. $money = 0;
  152. if (isset($achievement_award_log_list[$v['user_id']])) $money = $achievement_award_log_list[$v['user_id']]['money'];
  153. $award_money = $v['proportion_money'] - $money > 0 ? $v['proportion_money'] - $money : 0;
  154. $v->award_money = $award_money;
  155. $v->is_end = 1;
  156. //总计
  157. $sum_money = 0;
  158. $sum_money += $award_money;
  159. if (isset($achievement_award_log_list_end[$v['user_id']])) $sum_money += $achievement_award_log_list_end[$v['user_id']]['money'];
  160. $v->award_sum = $sum_money;
  161. if (!$v->save()) throw new \Exception("业绩修改奖励日志失败");
  162. $sum_award += $v->award_money;
  163. }
  164. return $sum_award;
  165. }
  166. /**
  167. * @desc:计算奖励金额
  168. * @Author: hua
  169. * @Date: 2022/3/8
  170. * @Time: 16:46
  171. * @Copyright: copyright (c) 2021 广东七件事集团
  172. * @param $list
  173. * @param $sum
  174. * @param $personal
  175. * @param $settlement_mode
  176. * @return array
  177. */
  178. public static function confirmProportion($list, $sum, $personal, $settlement_mode, $is_team_achievement = false)
  179. {
  180. $list = json_decode($list, true);
  181. $column = array_column($list, 'money');
  182. array_multisort($column, SORT_ASC, $list);//升序
  183. $proportion = 0;//比例
  184. $money = 0;//奖励金额
  185. foreach ($list as $k => $v) {
  186. if ($sum >= $v['money']) {
  187. $proportion = $v['proportion'];
  188. if ($settlement_mode == 0) {
  189. $money = $v['proportion'] * $personal / 100;
  190. } else {
  191. $money = ($sum * $proportion) / 100;
  192. if ($is_team_achievement == 1) {
  193. $money = (($sum - $personal) * $proportion) / 100;
  194. }
  195. }
  196. }
  197. }
  198. return ['proportion' => $proportion, 'money' => $money];
  199. }
  200. /**
  201. * @desc:获取上级团长user_id
  202. * @Author: hua
  203. * @Date: 2022/3/8
  204. * @Time: 16:46
  205. * @Copyright: copyright (c) 2021 广东七件事集团
  206. * @param $user_id
  207. * @return int|mixed
  208. */
  209. public static function getParentAchievementUser($user_id)
  210. {
  211. //订单付款者不是团长身份,就往他的上级找
  212. $id = 0;
  213. $parent_id_arr = UserPartitionRelationship::getParentIdArr($user_id);
  214. $parent_id_arr = array_reverse($parent_id_arr);
  215. $parent_achievement_user_list = AchievementUser::lists(['where' => [['user_id' => $parent_id_arr], ['status' => StatusEnum::ENABLED]], 'index' => 'user_id']);
  216. foreach ($parent_id_arr as $user_id) {
  217. if (isset($parent_achievement_user_list[$user_id])) {
  218. $achievement_user = $parent_achievement_user_list[$user_id];
  219. $id = $achievement_user['user_id'];
  220. break;
  221. }
  222. }
  223. return $id;
  224. }
  225. /**
  226. * @desc:结算业绩
  227. * @Author: hua
  228. * @Date: 2022/3/8
  229. * @Time: 16:47
  230. * @Copyright: copyright (c) 2021 广东七件事集团
  231. * @param $id
  232. * @return bool
  233. * @throws \Exception
  234. */
  235. public static function grantAchievement($id)
  236. {
  237. if (is_array($id)) {
  238. $id = $id['id'];
  239. }
  240. $grant = AchievementGrantLog::findOne(['id' => $id, 'status' => StatusEnum::ENABLED, 'is_settlement' => 0]);
  241. if (empty($grant)) return true;
  242. //判断业绩奖励是否开启
  243. $configs = \Yii::$app->services->setting->addons->get($grant['mall_id'], AddonsEnum::ADDONS_NAME_ACHIEVEMENT, 'basic');
  244. if (empty($configs['status'])) return true;
  245. $t = \Yii::$app->db->beginTransaction();
  246. try {
  247. $list = AchievementAwardLog::findAll(['grant_id' => $id, 'mall_id' => $grant['mall_id'], 'status' => StatusEnum::ENABLED, 'is_settlement' => 0]);
  248. $beg_time = date('Y.m.d', $grant['created_at']);
  249. $end_time = date('Y.m.d', $grant['end_time'] - 1);
  250. $remark = $beg_time . '-' . $end_time;
  251. $insert_wallet = [];
  252. $award_log_ids = [];
  253. foreach ($list as $item) {
  254. //统计团队业绩
  255. $award_money = $item['award_money'] + $item['equal_money'];
  256. //新增不结算判断
  257. if ($award_money > 0 && $item['is_skip_settlement'] == 0) {
  258. //发送佣金队列
  259. $award_money = bcmul($award_money, 1, 2);
  260. $desc = '用户(' . $item['user_id'] . '),获得业绩奖励,金额:' . $award_money;
  261. // echo $desc.PHP_EOL;
  262. $insert_wallet [] = ['mall_id' => $item['mall_id'], 'user_id' => $item['user_id'],
  263. 'is_frozen' => false, 'wallet_type' => 'commission', 'money' => $award_money,
  264. 'desc' => $desc,
  265. 'source_table' => AchievementAwardLog::tableName(),
  266. 'source_table_id' => $item['id'],
  267. 'from_type' => AddonsEnum::ADDONS_NAME_ACHIEVEMENT,
  268. 'capital_type' => UserWalletEnum::ACHIEVEMENT_REWARD,
  269. ];
  270. //todo 微信推送,暂时不做推送,看后期规划
  271. if (!empty($configs['is_notice'])) {
  272. }
  273. }
  274. $award_log_ids[] = $item['id'];
  275. }
  276. AchievementAwardLog::updateAll(['is_settlement' => 1, 'is_end' => 1], ['id' => $award_log_ids]);
  277. $grant->is_settlement = 1;
  278. if (!$grant->save()) throw new \Exception("业绩结算修改规则日志失败");
  279. // 批量插入数据
  280. try {
  281. //投递到资产队列
  282. if ($insert_wallet) {
  283. $res = UserWalletService::batchHandleByQueue($insert_wallet);
  284. if (empty($res)) throw new \Exception(UserWalletService::getStaticError());
  285. foreach ($insert_wallet as $k => $user) {
  286. $achievement = AchievementUser::findOne(['user_id' => $user['user_id']]);
  287. $achievement->total_commission += $user['money'];
  288. $res = $achievement->save();
  289. if (empty($res)) throw new \Exception(AchievementUser::getStaticError());
  290. }
  291. }
  292. } catch (\Exception $e) {
  293. \Yii::error('DistributionBase:addFrozenCommission' . $e->getMessage());
  294. }
  295. $t->commit();
  296. return true;
  297. } catch (Exception $e) {
  298. $t->rollBack();
  299. \Yii::error('业绩结算失败' . PHP_EOL . $e->getFile() . '(' . $e->getLine() . ')' . PHP_EOL . "message:" . $e->getMessage());
  300. self::$static_error = '业绩结算失败' . PHP_EOL . $e->getFile() . '(' . $e->getLine() . ')' . PHP_EOL . "message:" . $e->getMessage();
  301. return true;
  302. }
  303. }
  304. /**
  305. * @desc:整点添加规则
  306. * @Author: hua
  307. * @Date: 2022/3/8
  308. * @Time: 17:12
  309. * @Copyright: copyright (c) 2021 广东七件事集团
  310. * @param $mall_id
  311. * @param int $type 0,正常生成,1:更新配置后重新生成
  312. * @return bool
  313. * @throws \Exception
  314. */
  315. public static function addGrantLog($mall_id, $type = 0)
  316. {
  317. $time = time();
  318. // $time = '1647219869';//调测使用
  319. $is_install = MallAddons::isInstall($mall_id, AchievementEnum::ADDONS_NAME);
  320. if ($is_install == false) return true;
  321. //判断业绩奖励是否开启
  322. $configs = \Yii::$app->services->setting->addons->get($mall_id, AddonsEnum::ADDONS_NAME_ACHIEVEMENT, 'basic');
  323. if (empty($configs['status'])) return true;
  324. //查看最新一期是否存在
  325. $status = AchievementGrantLog::find()->where(['mall_id' => $mall_id, 'status' => StatusEnum::ENABLED, 'is_create' => 0])
  326. ->andWhere(['>', 'end_time', $time])->one();
  327. if (!empty($status)) return true;
  328. $t = \Yii::$app->db->beginTransaction();
  329. try {
  330. //0,正常生成,1:更新配置后重新生成
  331. if ($type == 0) {
  332. AchievementGrantLog::updateAll(['is_create' => 1], ['mall_id' => $mall_id, 'status' => StatusEnum::ENABLED, 'is_create' => 0]);
  333. } else {
  334. AchievementGrantLog::updateAll(['status' => StatusEnum::DELETE], ['mall_id' => $mall_id, 'is_wait' => 0, 'status' => StatusEnum::ENABLED, 'is_create' => 0]);
  335. }
  336. // $time = $configs['settlement_cycle'] == 0 ? strtotime('next monday') : strtotime(date("Y-m-d H:i:s", mktime(0, 0, 0, date("m") + 1, 1, date("Y"))));
  337. if ($configs['settlement_cycle'] == 0) {
  338. $time = strtotime('next monday');
  339. } elseif ($configs['settlement_cycle'] == 1) {
  340. $time = mktime(0, 0, 0, date("m") + 1, 1, date("Y"));
  341. } elseif ($configs['settlement_cycle'] == 2) {
  342. $current_month = date('n');
  343. $current_year = date('Y');
  344. // 计算当前季度起始月份 (1,4,7,10)
  345. $current_quarter_start = floor(($current_month - 1) / 3) * 3 + 1;
  346. // 计算下个季度起始月份
  347. $next_quarter_month = $current_quarter_start + 3;
  348. $next_year = $current_year;
  349. if ($next_quarter_month > 12) {
  350. $next_quarter_month -= 12;
  351. $next_year++;
  352. }
  353. $time = mktime(0, 0, 0, $next_quarter_month, 1, $next_year);
  354. }
  355. $cycle_time = $configs['settlement_time'];
  356. $award_proportion = $configs['award_proportion'];
  357. $settlement_cycle = $configs['settlement_cycle'];
  358. $delay_time = $configs['delay_time'];
  359. $statistical_methods = $configs['statistical_methods'];
  360. $settlement_mode = $configs['settlement_mode'];
  361. $grantLog = new AchievementGrantLog();
  362. $grantLog->mall_id = $mall_id;
  363. $grantLog->award_proportion = $award_proportion;
  364. $grantLog->cycle = $settlement_cycle;
  365. $grantLog->cycle_time = $cycle_time;
  366. $grantLog->wait_settlement_time = strtotime(date('Y-m-d ' . $cycle_time, $time));
  367. $grantLog->settlement_time = strtotime(date('Y-m-d ' . $cycle_time, $time)) + $delay_time * 86400;
  368. $grantLog->statistical_methods = $statistical_methods;
  369. $grantLog->end_time = $time;
  370. $grantLog->settlement_mode = $settlement_mode;
  371. $grantLog->is_equal = $configs['is_equal'] ?? 0;
  372. $grantLog->equal_percent = $configs['equal_percent'] ?? 0;
  373. $grantLog->equal_price_first = $configs['equal_price_first'] ?? 0;
  374. $grantLog->equal_price_second = $configs['equal_price_second'] ?? 0;
  375. $grantLog->is_team_achievement = $configs['team_achievement'] ?? 0;
  376. $grantLog->is_award_need_confirm = $configs['is_award_need_confirm'] ?? 0;
  377. $grantLog->is_leader_first_month_no_award = $configs['is_leader_first_month_no_award'] ?? 0;
  378. if (!$grantLog->save()) throw new \Exception("创建下一期规则日志失败");
  379. $t->commit();
  380. return true;
  381. } catch (Exception $e) {
  382. $t->rollBack();
  383. \Yii::error('创建下一期规则日志失败' . PHP_EOL . $e->getFile() . '(' . $e->getLine() . ')' . PHP_EOL . "message:" . $e->getMessage());
  384. self::$static_error = '创建下一期规则日志失败' . PHP_EOL . $e->getFile() . '(' . $e->getLine() . ')' . PHP_EOL . "message:" . $e->getMessage();
  385. return true;
  386. }
  387. }
  388. /**
  389. * @desc:编辑日志
  390. * @Author: hua
  391. * @Date: 2022/3/8
  392. * @Time: 17:12
  393. * @Copyright: copyright (c) 2021 广东七件事集团
  394. * @param $mall_id
  395. * @return bool
  396. */
  397. public function setLogStatus($mall_id)
  398. {
  399. try {
  400. $res = AchievementGrantLog::updateAll(['status' => StatusEnum::DELETE], ['mall_id' => $mall_id, 'is_settlement' => 0]);
  401. \Yii::$app->custom->logs('setLogStatus->AchievementGrantLog:update_count' . $res);
  402. $res = AchievementAwardLog::updateAll(['status' => StatusEnum::DELETE], ['mall_id' => $mall_id, 'is_settlement' => 0]);
  403. \Yii::$app->custom->logs('setLogStatus->AchievementAwardLog:update_count' . $res);
  404. return true;
  405. } catch (Exception $e) {
  406. return false;
  407. }
  408. }
  409. /**
  410. * 填充上级
  411. * @param $data
  412. * @return void
  413. */
  414. public static function fillParentTeam($data)
  415. {
  416. $mall_id = $data['mall_id'];
  417. $user_id = $data['user_id'];
  418. $grant = AchievementGrantLog::findOne(['mall_id' => $mall_id, 'status' => 1, 'is_wait' => 0, 'is_create' => 0]);
  419. if (!empty($grant)) {
  420. AchievementOrderLogic::fillParentTeamByEmpty($mall_id, $grant['id'], $grant['settlement_mode']);
  421. AchievementOrderLogic::updateParentTeam($mall_id, $grant['id'], $user_id);
  422. }
  423. $grant->award_proportion = json_decode($grant['award_proportion'], true);
  424. self::fixParentAchievement($grant, $user_id);
  425. $grant['award_proportion'] = json_encode($grant['award_proportion']);
  426. AchievementOrderLogic::updateGrant($grant);
  427. }
  428. /**
  429. * 修正上级的业绩
  430. *
  431. * @param $grant
  432. * @param $user_id
  433. * @return void
  434. * @throws Exception
  435. */
  436. public static function fixParentAchievement($grant, $user_id)
  437. {
  438. $mall_id = $grant['mall_id'];
  439. $parent_id_arr = UserPartitionRelationship::getParentIdArr($user_id);
  440. $parent_id_arr[] = $user_id;
  441. $parent_id_arr = array_reverse($parent_id_arr);
  442. $achievement_user_map = self::getAchievementUserMap($mall_id, $parent_id_arr);
  443. if (!empty($parent_id_arr)) {
  444. $new_parent_achievement_award_log_map = self::getParentAchievementAwardLogMap($grant['id'], $parent_id_arr);
  445. $new_parent_achievement_award_log_list_sort = [];
  446. foreach ($parent_id_arr as $pid) {
  447. if (!isset($new_parent_achievement_award_log_map[$pid])) {
  448. if (isset($achievement_user_map[$pid])) {
  449. $new_parent_achievement_award_log_list_sort[] = self::getTempModel($mall_id, $pid, $grant['id']);
  450. }
  451. } else {
  452. $new_parent_achievement_award_log_list_sort[] = $new_parent_achievement_award_log_map[$pid];
  453. }
  454. }
  455. if (!empty($new_parent_achievement_award_log_list_sort)) {
  456. self::handleAchievement($grant, $new_parent_achievement_award_log_list_sort);
  457. }
  458. }
  459. }
  460. /**
  461. * 获取团长map
  462. *
  463. * @param $mall_id
  464. * @param $parent_id_arr
  465. * @return false|mixed
  466. */
  467. public static function getAchievementUserMap($mall_id, $parent_id_arr)
  468. {
  469. return AchievementUser::lists([
  470. 'where' => [
  471. ['user_id' => $parent_id_arr],
  472. ['mall_id' => $mall_id],
  473. ['status' => StatusEnum::ENABLED]
  474. ],
  475. 'index' => 'user_id'
  476. ]);
  477. }
  478. public static function getParentAchievementAwardLogMap($grant_id, $parent_id_arr)
  479. {
  480. $achievement_award_log_list = AchievementAwardLog::lists([
  481. 'where' => [
  482. ['user_id' => $parent_id_arr],
  483. ['grant_id' => $grant_id],
  484. ['status' => StatusEnum::ENABLED]
  485. ],
  486. 'index' => 'user_id'
  487. ], false);
  488. if (empty($achievement_award_log_list)) {
  489. return []; //旧上级没有本周期的业绩奖励记录
  490. }
  491. return $achievement_award_log_list;
  492. }
  493. /**
  494. * 获取临时模型
  495. *
  496. * @param $mall_id
  497. * @param $user_id
  498. * @param $grant_id
  499. * @return AchievementAwardLog
  500. */
  501. public static function getTempModel($mall_id, $user_id, $grant_id)
  502. {
  503. $model = new AchievementAwardLog();
  504. $model->parent_team =
  505. $model->user_id = $user_id;
  506. $model->grant_id = $grant_id;
  507. $model->mall_id = $mall_id;
  508. $model->parent_team = AchievementLogic::getParentAchievementUser($user_id);
  509. $model->sub_personal_achievement = 0;
  510. return $model;
  511. }
  512. /**
  513. * 处理团队业绩
  514. *
  515. * @param $grant
  516. * @param $new_parent_achievement_award_log_list_sort
  517. * @return void
  518. * @throws Exception
  519. */
  520. public static function handleAchievement($grant, $new_parent_achievement_award_log_list_sort)
  521. {
  522. $settlement_mode = $grant['settlement_mode'];
  523. $grant_id = $grant['id'];
  524. $award_proportion = $grant['award_proportion'];
  525. $list = $user_id_arr = [];
  526. foreach ($new_parent_achievement_award_log_list_sort as $log) {
  527. $log->parent_team = AchievementLogic::getParentAchievementUser($log->user_id);
  528. $log->save();
  529. if ($settlement_mode == 2) {
  530. self::planC($log, $grant_id, $award_proportion, $settlement_mode);
  531. } else {
  532. $team_achievement = $log->team_achievement;
  533. $child_achievement_sum = self::handleAchievementExtra($log);
  534. if (empty($child_achievement_sum)) {
  535. $child_achievement_sum = 0;
  536. }
  537. if ($team_achievement == $child_achievement_sum) {
  538. //团队业绩无变化
  539. continue;
  540. }
  541. $log->team_achievement = $child_achievement_sum;
  542. $log->achievement_sum = $child_achievement_sum + $log->personal_achievement;
  543. if (!empty($log->achievement_sum)) {
  544. $log->save();
  545. }
  546. $award = AchievementLogic::confirmProportion($award_proportion, $log->achievement_sum, $log->personal_achievement, $settlement_mode);
  547. $log->award_proportion = $award['proportion'];
  548. if ($settlement_mode == 0) {
  549. $log->award_money = $award['money'];
  550. } else {
  551. $log->proportion_money = $award['money'];
  552. }
  553. if (!$log->save()) {
  554. var_dump('处理个人业绩日志时失败');
  555. }
  556. if ($settlement_mode == 1) {
  557. $list[] = $log;
  558. $user_id_arr[] = $log->user_id;
  559. }
  560. }
  561. }
  562. if ($settlement_mode == 1 && !empty($list)) {
  563. AchievementOrderLogic::planB($grant, $list, $user_id_arr);//极差
  564. }
  565. }
  566. /**
  567. * 处理扩展表的团队业绩,同时返回会员的下级们的总业绩
  568. * @param $log
  569. * @return bool|float|int|mixed|string
  570. */
  571. public static function handleAchievementExtra($log)
  572. {
  573. $user_id = $log->user_id;
  574. $grant_id = $log->grant_id;
  575. $child_achievement_award_log_list = self::getAchievementAwardLogListByParentTeam($user_id, $grant_id);
  576. $child_user_ids = array_column($child_achievement_award_log_list, 'user_id');
  577. $child_team_achievement = AchievementAwardLogExtra::find()->where(['user_id' => $child_user_ids, 'grant_id' => $grant_id])
  578. ->sum('team_achievement');
  579. $total_personal_achievement = array_sum(array_column($child_achievement_award_log_list, 'personal_achievement'));
  580. $team_achievement = 0;
  581. if ($child_team_achievement) {
  582. $team_achievement = $child_team_achievement;
  583. }
  584. if ($total_personal_achievement) {
  585. $team_achievement = $team_achievement + $total_personal_achievement;
  586. }
  587. AchievementAwardLogExtra::updateAll(['team_achievement' => $team_achievement], ['user_id' => $user_id, 'grant_id' => $grant_id]);
  588. return $team_achievement;
  589. }
  590. /**
  591. * 业绩极差
  592. *
  593. * @param $log
  594. * @param $grant_id
  595. * @param $award_proportion
  596. * @param $settlement_mode
  597. * @return void
  598. */
  599. public static function planC($log, $grant_id, $award_proportion, $settlement_mode)
  600. {
  601. $configs = \Yii::$app->services->setting->addons->get($log['mall_id'], AddonsEnum::ADDONS_NAME_ACHIEVEMENT, 'basic');
  602. $team_achievement = $log->team_achievement;
  603. $child_achievement_sum = self::getTeamAchievementByParentTeamC($log->user_id, $grant_id);
  604. $child_equal_first = self::getEqualFirstByParentTeamC($log->user_id, $grant_id);
  605. $child_equal_second = self::getEqualSecondByParentTeamC($log->user_id, $grant_id);
  606. if (empty($child_achievement_sum)) {
  607. $child_achievement_sum = 0;
  608. }
  609. $log->achievement_sum = $log->team_achievement + $log->personal_achievement;
  610. if ($team_achievement != $child_achievement_sum) {
  611. $log->team_achievement = $child_achievement_sum ?? 0;
  612. $log->achievement_sum = $log->team_achievement + $log->personal_achievement;
  613. $log->save();
  614. $award_proportion = json_encode($award_proportion);
  615. $award = AchievementLogic::confirmProportion($award_proportion, $log->achievement_sum, $log->personal_achievement, $settlement_mode);
  616. $log->award_proportion = $award['proportion'];
  617. $log->award_money = $award['money'];
  618. }
  619. $log->team_equal_first = empty($configs['equal_type']) ? ($child_equal_first ?? 0) : 0;
  620. $log->team_equal_second = empty($configs['equal_type']) ? ($child_equal_second ?? 0) : 0;
  621. if (!$log->save()) {
  622. var_dump('处理个人业绩日志时失败');
  623. }
  624. }
  625. /**
  626. * 获取团队业绩,c
  627. *
  628. * @param $user_id
  629. * @param $grant_id
  630. * @return bool|int|mixed|string|null
  631. */
  632. public static function getTeamAchievementByParentTeamC($user_id, $grant_id)
  633. {
  634. return AchievementAwardLog::find()->where([
  635. 'parent_team' => $user_id,
  636. 'grant_id' => $grant_id,
  637. 'status' => StatusEnum::ENABLED,
  638. 'award_money' => 0
  639. ])->sum('achievement_sum');
  640. }
  641. /**
  642. * 获取平1,c
  643. * @param $user_id
  644. * @param $grant_id
  645. * @return bool|int|mixed|string|null
  646. */
  647. public static function getEqualFirstByParentTeamC($user_id, $grant_id)
  648. {
  649. return AchievementAwardLog::find()->where([
  650. 'parent_team' => $user_id,
  651. 'grant_id' => $grant_id,
  652. 'status' => StatusEnum::ENABLED,
  653. 'award_money' => 0
  654. ])->sum('equal_first');
  655. }
  656. /**
  657. * 获取平2,c
  658. * @param $user_id
  659. * @param $grant_id
  660. * @return bool|int|mixed|string|null
  661. */
  662. public static function getEqualSecondByParentTeamC($user_id, $grant_id)
  663. {
  664. return AchievementAwardLog::find()->where([
  665. 'parent_team' => $user_id,
  666. 'grant_id' => $grant_id,
  667. 'award_money' => 0
  668. ])->sum('equal_second');
  669. }
  670. /**
  671. * 获取奖励明细列表
  672. *
  673. * @param $user_id
  674. * @param $grant_id
  675. * @return array|\yii\db\ActiveRecord[]
  676. */
  677. public static function getAchievementAwardLogListByParentTeam($user_id, $grant_id)
  678. {
  679. return AchievementAwardLog::find()->where([
  680. 'parent_team' => $user_id,
  681. 'grant_id' => $grant_id
  682. ])->all();
  683. }
  684. }