UserService.php 9.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328
  1. <?php
  2. namespace app\api\service;
  3. use app\api\model\massager\Collect;
  4. use app\api\model\massager\Comment;
  5. use app\api\model\massager\Massager;
  6. use app\api\model\system\Message;
  7. use app\api\model\order\Order;
  8. use app\api\model\User;
  9. use app\api\model\user\Bill;
  10. use app\api\model\user\Voucher;
  11. use app\api\model\user\Wallet;
  12. use app\common\library\Auth;
  13. use app\common\model\Sms;
  14. use fast\Random;
  15. use GatewayWorker\Lib\Db;
  16. class UserService extends BaseService
  17. {
  18. private $model;
  19. private $userBillModel;
  20. private $walletModel;
  21. public function __construct()
  22. {
  23. $this->model = new User();
  24. $this->userBillModel = new Bill();
  25. $this->walletModel = new Wallet();
  26. }
  27. function findUser($user_id)
  28. {
  29. $user = $this->model->findById($user_id);
  30. if (!$user)
  31. return $this->fail("用户不存在!");
  32. return $this->ok(User::fmtUser($user));
  33. }
  34. function findWallet($user_id)
  35. {
  36. $w = $this->walletModel->getUserWallet($user_id);
  37. return [
  38. "user_id" => $w->user_id,
  39. "score" => $w->score,
  40. "money" => (float)$w->money,
  41. "give_money" => (float)$w->give_money,
  42. "total_money" => fixed2Float($w->money + $w->give_money),
  43. ];
  44. }
  45. function summary($user_id)
  46. {
  47. $wallet = $this->findWallet($user_id);
  48. return [
  49. "msg_count" => (new Message())->where(["to_user_id" => $user_id, "is_read" => 0])->count(),
  50. "collect_count" => (new Collect())->where(["user_id" => $user_id])->count(),
  51. "score" => $wallet["score"],
  52. "total_money" => $wallet["total_money"],
  53. "voucher_count" => (new Voucher())->fetchVoucherCount($user_id),
  54. "order_count" => (new Order())->where("user_id", $user_id)->count()
  55. ];
  56. }
  57. public function fetchCollectMassager($user_id, $page, $size)
  58. {
  59. $paginate = (new Collect())->fetchCollectMassager($user_id, $page, $size);
  60. $items = array_map(function ($data) {
  61. return $data["massager"];
  62. }, $paginate->items());
  63. foreach ($items as &$item) {
  64. $item['recently_work_date'] = null;
  65. $item['is_can_collet'] = false;
  66. unset($item['nearly_two_days_orders']);
  67. }
  68. return [
  69. array_map(function ($data) {
  70. return Massager::fmtMassager($data);
  71. }, $items),
  72. $paginate->total()
  73. ];
  74. }
  75. public function fetchMassagerComment($user_id, $page, $size)
  76. {
  77. $paginate = (new Comment())->fetchByUserId($user_id, $page, $size);
  78. return [
  79. $paginate->items(),
  80. $paginate->total()
  81. ];
  82. }
  83. public function fetchSystemMessage($user_id, $page, $size)
  84. {
  85. $messageModel = new Message();
  86. $paginate = $messageModel->fetchUserSystemMessage($user_id, $page, $size);
  87. $messageModel->update(["is_read" => 1], [
  88. "to_user_id" => $user_id,
  89. "is_read" => 0,
  90. "identity_type" => \E_IDENTITY_TYPE::User
  91. ]);
  92. return [
  93. $paginate->items(),
  94. $paginate->total()
  95. ];
  96. }
  97. public function findByUnionId($union_id)
  98. {
  99. return $this->model->findByUnionId($union_id);
  100. }
  101. public function bindAppWx($u_id, $params)
  102. {
  103. $user = $this->findByUnionId($params["unionId"]);
  104. if ($user)
  105. return $this->fail("该微信已经绑定用户,请解绑后再进行绑定!");
  106. $this->model->update([
  107. "app_openid" => $params["openId"],
  108. "union_id" => $params["unionId"],
  109. "nickname" => $params["nickName"],
  110. "avatar" => $params["avatarUrl"],
  111. ], ["id" => $u_id]);
  112. return $this->ok(true);
  113. }
  114. public function unbindWx($u_id)
  115. {
  116. $this->model->update([
  117. "app_openid" => null,
  118. "web_openid" => null,
  119. "union_id" => null,
  120. ], ["id" => $u_id]);
  121. return $this->ok(true);
  122. }
  123. public function bindMobile($u_id, $mobile, $sms_code)
  124. {
  125. $check = \app\common\library\Sms::check($mobile, $sms_code, "bind_mobile");
  126. if (!$check)
  127. return $this->fail("短信验证码不正确!");
  128. $user = $this->model->where("mobile", $mobile)->find();
  129. if ($user)
  130. return $this->fail("该手机号码已经绑定用户,无法继续绑定!");
  131. $this->model->update([
  132. "mobile" => $mobile
  133. ], ["id" => $u_id]);
  134. return $this->ok(true);
  135. }
  136. public function resetPwd($u_id, $sms_code, $new_password)
  137. {
  138. $user = $this->model->get($u_id);
  139. if (!$user || mb_strlen($user["mobile"]) != 11)
  140. return $this->fail("请先绑定手机再修改登录密码!");
  141. $check = \app\common\library\Sms::check($user["mobile"], $sms_code, "reset_pwd");
  142. if (!$check)
  143. return $this->fail("短信验证码不正确!");
  144. $this->model->update([
  145. "password" => $new_password
  146. ], ["id" => $u_id]);
  147. return $this->ok(true);
  148. }
  149. // 更新用户分组
  150. public static function updateGrouping($user_id)
  151. {
  152. $grouping_config = [
  153. [
  154. "grouping" => "D",
  155. "rule" => ["已消费总金额" => 0, "累计下单次数" => 0]
  156. ],
  157. [
  158. "grouping" => "C",
  159. "rule" => config("site.user_level_C")
  160. ],
  161. [
  162. "grouping" => "B",
  163. "rule" => config("site.user_level_B")
  164. ],
  165. [
  166. "grouping" => "A",
  167. "rule" => config("site.user_level_A")
  168. ],
  169. ];
  170. $total_consume_amount = Order::sumByUser($user_id);
  171. $now_place_order_count = Order::countByUser($user_id);
  172. $grouping = "D";
  173. foreach ($grouping_config as $item) {
  174. if ($item["rule"]["已消费总金额"] >= $total_consume_amount || $item["rule"]["累计下单次数"] >= $now_place_order_count)
  175. break;
  176. $grouping = $item["grouping"];
  177. }
  178. User::update([
  179. "grouping" => $grouping
  180. ], ["id" => $user_id]);
  181. return $grouping;
  182. }
  183. public function fetchInviteCount($user_id)
  184. {
  185. $change_type = \E_USER_BILL_CHANGE_TYPE::ProfitIncrease[0];
  186. $total_profit = \db()->query("select sum(`change`) as total_profit_amount from ma_user_bill where user_id = {$user_id} AND change_type = {$change_type}");
  187. $users = $this->model->where([
  188. "parent_id" => $user_id,
  189. "is_use_award" => 0,
  190. ])->field("id")->select();
  191. $user_ids = array_map(function ($data) {
  192. return $data['id'];
  193. }, $users);
  194. $two_users = $this->model->where("parent_id", "in", $user_ids)->where("is_use_award", 0)->field("id")->select();
  195. $two_user_ids = array_map(function ($data) {
  196. return $data['id'];
  197. }, $two_users);
  198. $user_ids_str = join(",", array_merge($user_ids, $two_user_ids));
  199. $order_status_str = join(",", ["'" . \E_ORDER_STATUS::Purchase . "'", "'" . \E_ORDER_STATUS::Proceed . "'", "'" . \E_ORDER_STATUS::WaitFeedback . "'"]);
  200. $total_wait_profit = 0;
  201. if (mb_strlen($user_ids_str) > 0) {
  202. $orders = \db()->query("
  203. SELECT
  204. o.user_id,
  205. o.total_real_amount,
  206. o.trip_amount
  207. FROM
  208. ma_user u
  209. JOIN ma_order o ON u.id = o.user_id
  210. WHERE
  211. u.id IN ({$user_ids_str})
  212. AND o.`status` IN ({$order_status_str})
  213. ORDER BY
  214. o.pay_time DESC
  215. ");
  216. foreach ($orders as $order) {
  217. $total_real_amount = ($order["total_real_amount"] - $order["trip_amount"]);
  218. if (in_array($order["user_id"], $user_ids)) {
  219. $item_wait_profit = fixed2Float($total_real_amount * (config("site.user_direct_invite_rate") / 100));
  220. } else {
  221. $item_wait_profit = fixed2Float($total_real_amount * (config("site.user_two_invite_rate") / 100));
  222. }
  223. $total_wait_profit += $item_wait_profit;
  224. }
  225. }
  226. return [
  227. "total_number" => $this->model->where("parent_id", $user_id)->count(),
  228. "total_profit_amount" => $total_profit[0]["total_profit_amount"] ?? 0,
  229. "total_wait_profit" => $total_wait_profit,
  230. "users" => $this->model->where("parent_id", $user_id)->field("id,nickname,avatar")->limit(4)->select()
  231. ];
  232. }
  233. public function fetchInviteDetails($user_id, $page = 1, $size = 10)
  234. {
  235. $paginate = $this->model->where("parent_id", $user_id)->field("id,nickname,avatar,is_use_award")->page($page)->paginate($size);
  236. return [
  237. $paginate->items(),
  238. $paginate->total()
  239. ];
  240. }
  241. public function fetchRanking()
  242. {
  243. $change_type = \E_USER_BILL_CHANGE_TYPE::ProfitIncrease[0];
  244. $rows = \db()->query("select user_id,sum(`change`) as total from ma_user_bill where change_type = {$change_type} group by user_id order by total DESC limit 20");
  245. $ids = array_map(function ($data) {
  246. return $data["user_id"];
  247. }, $rows);
  248. $users = $this->model
  249. ->where("id", "in", $ids)
  250. ->field("id,nickname,avatar")
  251. ->select();
  252. $fmt_users = [];
  253. foreach ($users as $user) {
  254. $fmt_users[$user["id"]] = $user;
  255. }
  256. return array_map(function ($data) use ($fmt_users) {
  257. $now = isset($fmt_users[$data["user_id"]]) ? $fmt_users[$data["user_id"]] : null;
  258. return [
  259. "user_id" => $data["user_id"],
  260. "nickname" => $now ? $now["nickname"] : null,
  261. "avatar" => $now ? $now["avatar"] : null,
  262. "total_profit_amount" => $data["total"]
  263. ];
  264. }, $rows);
  265. }
  266. }