UserChance.php 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315
  1. <?php
  2. namespace app\admin\controller\lottery;
  3. use app\common\controller\Backend;
  4. use think\Db;
  5. use think\exception\ValidateException;
  6. use think\exception\PDOException;
  7. use Exception;
  8. /**
  9. * 用户抽奖机会管理
  10. *
  11. * @icon fa fa-users
  12. */
  13. class UserChance extends Backend
  14. {
  15. /**
  16. * UserChance模型对象
  17. * @var \app\admin\model\lottery\UserChance
  18. */
  19. protected $model = null;
  20. public function _initialize()
  21. {
  22. parent::_initialize();
  23. $this->model = new \app\admin\model\lottery\UserChance;
  24. // 获取枚举值列表
  25. $this->view->assign("sourceTypeList", $this->model->getSourceTypeList());
  26. $this->view->assign("statusList", $this->model->getStatusList());
  27. }
  28. /**
  29. * 查看
  30. */
  31. public function index()
  32. {
  33. //当前是否为关联查询
  34. $this->relationSearch = true;
  35. //设置过滤方法
  36. $this->request->filter(['strip_tags', 'trim']);
  37. if ($this->request->isAjax()) {
  38. //如果发送的来源是Selectpage,则转发到Selectpage
  39. if ($this->request->request('keyField')) {
  40. return $this->selectpage();
  41. }
  42. list($where, $sort, $order, $offset, $limit) = $this->buildparams();
  43. $list = $this->model
  44. ->with(['activity', 'user'])
  45. ->where($where)
  46. ->order($sort, $order)
  47. ->paginate($limit);
  48. foreach ($list as $row) {
  49. $row->visible(['id','activity_id','user_id','chance_count','used_count','source_type','source_value','expire_time','status','createtime']);
  50. $row->visible(['activity', 'user']);
  51. $row->getRelation('activity')->visible(['name']);
  52. $row->getRelation('user')->visible(['nickname', 'mobile']);
  53. }
  54. $result = array("total" => $list->total(), "rows" => $list->items());
  55. return json($result);
  56. }
  57. return $this->view->fetch();
  58. }
  59. /**
  60. * 添加
  61. */
  62. public function add()
  63. {
  64. if ($this->request->isPost()) {
  65. $params = $this->request->post("row/a");
  66. if ($params) {
  67. $params = $this->preExcludeFields($params);
  68. // 处理过期时间
  69. if (isset($params['expire_time']) && $params['expire_time']) {
  70. $params['expire_time'] = strtotime($params['expire_time']);
  71. }
  72. // 初始化已使用次数
  73. if (!isset($params['used_count'])) {
  74. $params['used_count'] = 0;
  75. }
  76. $result = false;
  77. Db::startTrans();
  78. try {
  79. //是否采用模型验证
  80. if ($this->modelValidate) {
  81. $name = str_replace("\\model\\", "\\validate\\", get_class($this->model));
  82. $validate = is_bool($this->modelValidate) ? ($this->modelSceneValidate ? $name . '.add' : $name) : $this->modelValidate;
  83. $this->model->validateFailException(true)->validate($validate);
  84. }
  85. $result = $this->model->allowField(true)->save($params);
  86. Db::commit();
  87. } catch (ValidateException $e) {
  88. Db::rollback();
  89. $this->error($e->getMessage());
  90. } catch (PDOException $e) {
  91. Db::rollback();
  92. $this->error($e->getMessage());
  93. } catch (Exception $e) {
  94. Db::rollback();
  95. $this->error($e->getMessage());
  96. }
  97. if ($result !== false) {
  98. $this->success();
  99. } else {
  100. $this->error(__('No rows were inserted'));
  101. }
  102. }
  103. $this->error(__('Parameter %s can not be empty', ''));
  104. }
  105. return $this->view->fetch();
  106. }
  107. /**
  108. * 编辑
  109. */
  110. public function edit($ids = null)
  111. {
  112. $row = $this->model->get($ids);
  113. if (!$row) {
  114. $this->error(__('No Results were found'));
  115. }
  116. $adminIds = $this->getDataLimitAdminIds();
  117. if (is_array($adminIds)) {
  118. if (!in_array($row[$this->dataLimitField], $adminIds)) {
  119. $this->error(__('You have no permission'));
  120. }
  121. }
  122. if ($this->request->isPost()) {
  123. $params = $this->request->post("row/a");
  124. if ($params) {
  125. $params = $this->preExcludeFields($params);
  126. // 处理过期时间
  127. if (isset($params['expire_time']) && $params['expire_time']) {
  128. $params['expire_time'] = strtotime($params['expire_time']);
  129. }
  130. $result = false;
  131. Db::startTrans();
  132. try {
  133. //是否采用模型验证
  134. if ($this->modelValidate) {
  135. $name = str_replace("\\model\\", "\\validate\\", get_class($this->model));
  136. $validate = is_bool($this->modelValidate) ? ($this->modelSceneValidate ? $name . '.edit' : $name) : $this->modelValidate;
  137. $row->validateFailException(true)->validate($validate);
  138. }
  139. $result = $row->allowField(true)->save($params);
  140. Db::commit();
  141. } catch (ValidateException $e) {
  142. Db::rollback();
  143. $this->error($e->getMessage());
  144. } catch (PDOException $e) {
  145. Db::rollback();
  146. $this->error($e->getMessage());
  147. } catch (Exception $e) {
  148. Db::rollback();
  149. $this->error($e->getMessage());
  150. }
  151. if ($result !== false) {
  152. $this->success();
  153. } else {
  154. $this->error(__('No rows were updated'));
  155. }
  156. }
  157. $this->error(__('Parameter %s can not be empty', ''));
  158. }
  159. // 处理时间显示
  160. if ($row->expire_time) {
  161. $row->expire_time = date('Y-m-d H:i:s', $row->expire_time);
  162. }
  163. $this->view->assign("row", $row);
  164. return $this->view->fetch();
  165. }
  166. /**
  167. * 批量发放抽奖机会
  168. */
  169. public function batchGrant()
  170. {
  171. if ($this->request->isPost()) {
  172. $activity_id = $this->request->post('activity_id');
  173. $user_ids = $this->request->post('user_ids');
  174. $chance_count = $this->request->post('chance_count', 1);
  175. $source_type = $this->request->post('source_type', 1);
  176. $expire_time = $this->request->post('expire_time');
  177. if (empty($activity_id) || empty($user_ids)) {
  178. $this->error('活动ID和用户ID不能为空');
  179. }
  180. // 处理用户ID数组
  181. if (is_string($user_ids)) {
  182. $user_ids = array_filter(explode(',', $user_ids));
  183. }
  184. $expire_timestamp = $expire_time ? strtotime($expire_time) : null;
  185. $success_count = 0;
  186. Db::startTrans();
  187. try {
  188. foreach ($user_ids as $user_id) {
  189. $data = [
  190. 'activity_id' => $activity_id,
  191. 'user_id' => $user_id,
  192. 'chance_count' => $chance_count,
  193. 'used_count' => 0,
  194. 'source_type' => $source_type,
  195. 'source_value' => '管理员批量发放',
  196. 'expire_time' => $expire_timestamp,
  197. 'status' => 1,
  198. 'createtime' => time(),
  199. 'updatetime' => time()
  200. ];
  201. // 检查是否已存在
  202. $exists = $this->model->where([
  203. 'activity_id' => $activity_id,
  204. 'user_id' => $user_id,
  205. 'source_type' => $source_type
  206. ])->find();
  207. if ($exists) {
  208. // 更新现有记录
  209. $exists->chance_count += $chance_count;
  210. $exists->save();
  211. } else {
  212. // 创建新记录
  213. $this->model->create($data);
  214. }
  215. $success_count++;
  216. }
  217. Db::commit();
  218. $this->success("成功为 {$success_count} 个用户发放抽奖机会");
  219. } catch (Exception $e) {
  220. Db::rollback();
  221. $this->error('批量发放失败:' . $e->getMessage());
  222. }
  223. }
  224. // 获取活动列表
  225. $activityModel = new \app\admin\model\lottery\Activity;
  226. $activities = $activityModel->where('status', 1)->column('name', 'id');
  227. $this->view->assign('activities', $activities);
  228. return $this->view->fetch();
  229. }
  230. /**
  231. * 用户抽奖机会统计
  232. */
  233. public function statistics()
  234. {
  235. if ($this->request->isAjax()) {
  236. $activity_id = $this->request->get('activity_id');
  237. $where = [];
  238. if ($activity_id) {
  239. $where['activity_id'] = $activity_id;
  240. }
  241. // 统计数据
  242. $total_users = $this->model->where($where)->count('DISTINCT user_id');
  243. $total_chances = $this->model->where($where)->sum('chance_count');
  244. $used_chances = $this->model->where($where)->sum('used_count');
  245. $remain_chances = $total_chances - $used_chances;
  246. // 按来源类型统计
  247. $source_stats = $this->model->field('source_type, COUNT(*) as count, SUM(chance_count) as total_chance, SUM(used_count) as used_chance')
  248. ->where($where)
  249. ->group('source_type')
  250. ->select();
  251. $data = [
  252. 'total_users' => $total_users,
  253. 'total_chances' => $total_chances,
  254. 'used_chances' => $used_chances,
  255. 'remain_chances' => $remain_chances,
  256. 'source_stats' => $source_stats
  257. ];
  258. return json(['code' => 1, 'msg' => 'success', 'data' => $data]);
  259. }
  260. // 获取活动列表
  261. $activityModel = new \app\admin\model\lottery\Activity;
  262. $activities = $activityModel->where('status', 1)->column('name', 'id');
  263. $this->view->assign('activities', $activities);
  264. return $this->view->fetch();
  265. }
  266. /**
  267. * 清理过期机会
  268. */
  269. public function clearExpired()
  270. {
  271. $count = $this->model->where('expire_time', '<', time())
  272. ->where('expire_time', '>', 0)
  273. ->where('status', 1)
  274. ->update(['status' => 0]);
  275. $this->success("已清理 {$count} 条过期的抽奖机会");
  276. }
  277. }