GroupRelationController.java 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372
  1. package com.cyksj.web.controller.group;
  2. import cn.hutool.core.date.DateTime;
  3. import cn.hutool.core.date.DateUtil;
  4. import cn.hutool.core.thread.ThreadUtil;
  5. import cn.hutool.core.util.StrUtil;
  6. import cn.hutool.extra.servlet.ServletUtil;
  7. import cn.hutool.json.JSONObject;
  8. import com.baomidou.mybatisplus.core.toolkit.Wrappers;
  9. import com.cyksj.common.constant.Constant;
  10. import com.cyksj.common.exception.BusinessRuntimeException;
  11. import com.cyksj.common.task.GlobalThreadPoolTaskExecutor;
  12. import com.cyksj.common.util.GoogleGenerator;
  13. import com.cyksj.common.util.Jsons;
  14. import com.cyksj.common.util.StringUtil;
  15. import com.cyksj.dto.Result;
  16. import com.cyksj.enums.GatewayResponse;
  17. import com.cyksj.mapper.*;
  18. import com.cyksj.model.dto.DoubleVerifyDto;
  19. import com.cyksj.model.entity.*;
  20. import com.cyksj.model.manage.views.GroupsRelationView;
  21. import com.cyksj.model.request.OrderPayRequest;
  22. import com.cyksj.model.views.DoubleVerifyCodeView;
  23. import com.cyksj.model.views.RenewalView;
  24. import com.cyksj.model.views.UserTicketView;
  25. import com.cyksj.redis.RedisService;
  26. import com.cyksj.service.mange.coupon.CouponCommonService;
  27. import com.cyksj.service.order.OrderDonService;
  28. import com.cyksj.service.relation.GroupRelationFrontService;
  29. import com.cyksj.service.user.UserService;
  30. import com.cyksj.web.util.StpUserUtil;
  31. import com.ejlchina.searcher.BeanSearcher;
  32. import com.ejlchina.searcher.param.Operator;
  33. import com.ejlchina.searcher.util.MapUtils;
  34. import lombok.RequiredArgsConstructor;
  35. import lombok.extern.slf4j.Slf4j;
  36. import org.springframework.validation.annotation.Validated;
  37. import org.springframework.web.bind.annotation.*;
  38. import javax.servlet.http.HttpServletRequest;
  39. import java.util.List;
  40. import java.util.concurrent.TimeUnit;
  41. /**
  42. * @author chan
  43. * @date 2022/9/27 11:48 AM
  44. */
  45. @Slf4j
  46. @RequiredArgsConstructor
  47. @RestController
  48. @RequestMapping("/applets/group/relation")
  49. public class GroupRelationController {
  50. private final BeanSearcher beanSearcher;
  51. private final OrderDonService orderDonService;
  52. private final GroupsRelationMapper relationMapper;
  53. private final GroupRelationFrontService groupRelationFrontService;
  54. private final UserService userService;
  55. private final ChatGptPwdViewRecordMapper chatGptPwdViewRecordMapper;
  56. private final HttpServletRequest request;
  57. private final AccountDoubleVerifyRecordMapper accountDoubleVerifyRecordMapper;
  58. private final DoubleVerifyClickRecordMapper doubleVerifyRecordMapper;
  59. private final RedisService redisService;
  60. private final SysConfigMapper sysConfigMapper;
  61. private final DoubleVerifyClickRefreshRecordMapper refreshRecordMapper;
  62. private final QuestionResponseRecordMapper questionResponseRecordMapper;
  63. private final CouponCommonService couponCommonService;
  64. private final GlobalThreadPoolTaskExecutor THREAD_POOL;
  65. @RequestMapping("/get/renewal")
  66. public Result<List<RenewalView>> get(Boolean isLoginPopularize) {
  67. long userId = StpUserUtil.getLoginIdAsLong();
  68. List<RenewalView> list = groupRelationFrontService.getMyTicket(userId, isLoginPopularize);
  69. return GatewayResponse.SUCCESS.newBuilder().toResult(list);
  70. }
  71. @PostMapping("/post/renewal")
  72. public Result<OrderDon> renewal(@RequestBody OrderPayRequest request) throws Exception {
  73. long userId = StpUserUtil.getLoginIdAsLong();
  74. request.setUserId(userId);
  75. OrderDon orderDon = orderDonService.renewal(request);
  76. return GatewayResponse.SUCCESS.newBuilder().toResult(orderDon);
  77. }
  78. @PutMapping("/update/set/account")
  79. public Result<String> setAccount(@RequestBody GroupsRelation relation) {
  80. long userId = StpUserUtil.getLoginIdAsLong();
  81. List<Long> userIds = userService.getRelationUserIdList(userId, null);
  82. GroupsRelation re = relationMapper.selectOne(Wrappers.lambdaQuery(GroupsRelation.class)
  83. .eq(GroupsRelation::getId, relation.getId())
  84. .in(GroupsRelation::getUserId, userIds)
  85. .last(" limit 1"));
  86. if (re == null) {
  87. throw new BusinessRuntimeException("该车票不存在,请联系客服.");
  88. }
  89. relationMapper.update(relation, Wrappers.lambdaUpdate(GroupsRelation.class).set(GroupsRelation::getAccount, relation.getAccount()).eq(GroupsRelation::getId, relation.getId()));
  90. return GatewayResponse.SUCCESS.newBuilder().toResult();
  91. }
  92. /**
  93. * 查询是否加入了企业微信
  94. */
  95. @GetMapping("/check/joinCorpWx")
  96. public Result<Boolean> isJoinCorpWx() {
  97. long userId = StpUserUtil.getLoginIdAsLong();
  98. Boolean flag = groupRelationFrontService.isJoinCorpWx(userId, false, false);
  99. return GatewayResponse.SUCCESS.newBuilder().toResult(flag);
  100. }
  101. /**
  102. * 获取全部车票
  103. */
  104. @GetMapping("/get")
  105. public Result<List<UserTicketView>> getUserTicketView() {
  106. long userId = StpUserUtil.getLoginIdAsLong();
  107. List<Long> userIds = userService.getRelationUserIdList(userId, null);
  108. List<UserTicketView> ticketViews = beanSearcher.searchAll(UserTicketView.class, MapUtils.builder()
  109. .field(UserTicketView::getUserId, userIds).op(Operator.InList)
  110. .orderBy(UserTicketView::getRelationId).asc()
  111. .build());
  112. return GatewayResponse.SUCCESS.newBuilder().toResult(ticketViews);
  113. }
  114. /**
  115. * 记录查看ChatGPT车票密码
  116. */
  117. @GetMapping("/recordView/{relationId}")
  118. public Result<String> recordGPTPwdView(@PathVariable Long relationId) {
  119. long userId = StpUserUtil.getLoginIdAsLong();
  120. List<Long> userIds = userService.getRelationUserIdList(userId, null);
  121. GroupsRelationView groupsRelationView = beanSearcher.searchFirst(GroupsRelationView.class, MapUtils.builder()
  122. .field(GroupsRelationView::getUserId, userIds).op(Operator.InList)
  123. .field(GroupsRelationView::getId, relationId).build());
  124. if (groupsRelationView == null) {
  125. log.info("userId:{}查看relationId:{}车票不存在", userId, relationId);
  126. throw BusinessRuntimeException.getInstance("该车票已不存在");
  127. }
  128. if (groupsRelationView.getAccountId() == null) throw BusinessRuntimeException.getInstance("该车队未配置账号");
  129. if (groupRelationFrontService == null) throw BusinessRuntimeException.getInstance("车票已不存在");
  130. ChatGptPwdViewRecord viewRecord = new ChatGptPwdViewRecord();
  131. viewRecord.setUserId(userId);
  132. viewRecord.setRelationId(relationId);
  133. viewRecord.setSkuId(groupsRelationView.getSkuId());
  134. viewRecord.setOperateLocation(StringUtil.getRealAddressByIP(ServletUtil.getClientIP(request)));
  135. chatGptPwdViewRecordMapper.insert(viewRecord);
  136. if (StrUtil.isEmpty(groupsRelationView.getApiSecret())) {
  137. THREAD_POOL.execute(() -> {
  138. //车队所有人查看密码
  139. Integer num = groupsRelationView.getGtNum();
  140. Integer viewNum = relationMapper.selectViewPwdCount(groupsRelationView.getGroupsId());
  141. if (num <= viewNum) {
  142. AccountDoubleVerifyRecord exist = accountDoubleVerifyRecordMapper.selectOne(Wrappers.lambdaQuery(AccountDoubleVerifyRecord.class)
  143. .eq(AccountDoubleVerifyRecord::getAccountId, groupsRelationView.getAccountId())
  144. .eq(AccountDoubleVerifyRecord::getDeleted, true).last("limit 1"));
  145. if (exist == null) {
  146. if (redisService.setNx(String.format("%s-%s", groupsRelationView.getAccountId(), groupsRelationView.getId()), groupsRelationView.getId(), 60l)) {
  147. //记录
  148. AccountDoubleVerifyRecord accountDoubleVerifyRecord = new AccountDoubleVerifyRecord();
  149. accountDoubleVerifyRecord.setAccountId(groupsRelationView.getAccountId());
  150. accountDoubleVerifyRecord.setAccount(groupsRelationView.getTripsAccount());
  151. accountDoubleVerifyRecord.setGroupsId(groupsRelationView.getGroupsId());
  152. accountDoubleVerifyRecord.setSkuId(groupsRelationView.getSkuId());
  153. accountDoubleVerifyRecord.setRemark("车队所有人看过密码");
  154. accountDoubleVerifyRecordMapper.insert(accountDoubleVerifyRecord);
  155. }
  156. }
  157. }
  158. });
  159. }
  160. return GatewayResponse.SUCCESS.newBuilder().toResult(groupsRelationView.getTripsPassword());
  161. }
  162. /**
  163. * 获取AI类 ChatGPT产品谷歌验证码
  164. */
  165. @GetMapping("/get/authCode")
  166. public Result<String> getAuthCode(Long relationId) {
  167. long userId = StpUserUtil.getLoginIdAsLong();
  168. List<Long> userIds = userService.getRelationUserIdList(userId, null);
  169. //每个人 每月只能获取两次
  170. if (relationId == null) throw BusinessRuntimeException.getInstance("车票不存在");
  171. GroupsRelationView groupsRelationView = beanSearcher.searchFirst(GroupsRelationView.class, MapUtils.builder()
  172. .field(GroupsRelationView::getId, relationId)
  173. .field(GroupsRelationView::getUserId, userIds).op(Operator.InList).build());
  174. if (groupsRelationView == null) throw BusinessRuntimeException.getInstance("车票不存在");
  175. if (StrUtil.isEmpty(groupsRelationView.getApiSecret())) throw BusinessRuntimeException.getInstance("未开启验证");
  176. DateTime now = DateTime.now();
  177. Integer count = doubleVerifyRecordMapper.selectCount(Wrappers.lambdaQuery(DoubleVerifyClickRecord.class)
  178. .in(DoubleVerifyClickRecord::getUserId, userIds)
  179. .eq(DoubleVerifyClickRecord::getRelationId, relationId)
  180. .eq(DoubleVerifyClickRecord::getAccountId, groupsRelationView.getAccountId())
  181. .between(DoubleVerifyClickRecord::getCreatedTime, DateUtil.beginOfMonth(now), DateUtil.endOfMonth(now)));
  182. SysConfig double_verify_num = sysConfigMapper.selectOne(Wrappers.lambdaQuery(SysConfig.class).eq(SysConfig::getSysKey, Constant.ACCOUNT_DOUBLE_VERIFY_KEY));
  183. int num = 2;
  184. if (double_verify_num != null) {
  185. num = Integer.parseInt(double_verify_num.getSysValue());
  186. }
  187. if (count >= num) throw BusinessRuntimeException.getInstance("获取双重验证码次数上限");
  188. int second = now.second();
  189. if (second < 30 && 30 - second < 3) {
  190. ThreadUtil.sleep(30 - second + 1, TimeUnit.SECONDS);
  191. } else if (second > 30 && 60 - second < 3) {
  192. ThreadUtil.sleep(60 - second + 1, TimeUnit.SECONDS);
  193. }
  194. StringBuilder sb = new StringBuilder();
  195. try {
  196. long code = GoogleGenerator.getCode(groupsRelationView.getApiSecret(), now.getTime());
  197. sb.append(code);
  198. while (sb.length() < 6) {
  199. sb.insert(0, 0);
  200. }
  201. DoubleVerifyClickRecord doubleVerifyClickRecord = new DoubleVerifyClickRecord();
  202. doubleVerifyClickRecord.setRelationId(relationId);
  203. doubleVerifyClickRecord.setUserId(userId);
  204. doubleVerifyClickRecord.setAccountId(groupsRelationView.getAccountId());
  205. doubleVerifyClickRecord.setAccount(groupsRelationView.getTripsAccount());
  206. doubleVerifyClickRecord.setSkuId(groupsRelationView.getSkuId());
  207. doubleVerifyRecordMapper.insert(doubleVerifyClickRecord);
  208. DoubleVerifyDto doubleVerifyDto = new DoubleVerifyDto();
  209. doubleVerifyDto.setClickId(doubleVerifyClickRecord.getId());
  210. doubleVerifyDto.setApiSecret(groupsRelationView.getApiSecret());
  211. redisService.set(String.format("%s-%s", userId, sb.toString()), 0, 60 * 10l);
  212. redisService.set(String.format("%s/%s", userId, sb.toString()), Jsons.toJson(doubleVerifyDto), 60 * 10l);
  213. } catch (Exception e) {
  214. throw BusinessRuntimeException.getInstance("获取双重验证码错误,请联系客服");
  215. }
  216. JSONObject re = new JSONObject();
  217. re.putOpt("code", sb.toString());
  218. int nowSecond = DateTime.now().second();
  219. int time = 0;
  220. if (nowSecond < 30) {
  221. time = 30 - nowSecond;
  222. } else {
  223. time = 60 - nowSecond;
  224. }
  225. re.putOpt("time", time);
  226. return GatewayResponse.SUCCESS.newBuilder().toResult(re.toString());
  227. }
  228. /**
  229. * 刷新验证码
  230. */
  231. @GetMapping("/refresh/code")
  232. public Result<String> refreshCode(String code) {
  233. long userId = StpUserUtil.getLoginIdAsLong();
  234. String numKey = String.format("%s-%s", userId, code);
  235. Object num = redisService.get(numKey);
  236. String objKey = String.format("%s/%s", userId, code);
  237. Object objValue = redisService.get(objKey);
  238. if (objValue == null || num == null) {
  239. throw BusinessRuntimeException.getInstance("请重新获取双重验证码");
  240. }
  241. Integer refreshNum = Integer.parseInt(num.toString());
  242. String apiSecret = null;
  243. Long clickId = 0l;
  244. try {
  245. DoubleVerifyDto dto = Jsons.parseObject(objValue.toString(), DoubleVerifyDto.class);
  246. apiSecret = dto.getApiSecret();
  247. clickId = dto.getClickId();
  248. } catch (Exception e) {
  249. apiSecret = objValue.toString();
  250. }
  251. if (refreshNum >= 3) {
  252. redisService.del(numKey);
  253. redisService.del(objKey);
  254. throw BusinessRuntimeException.getInstance("刷新次数已达到3次,请重新获取验证码");
  255. }
  256. if (apiSecret == null) {
  257. throw BusinessRuntimeException.getInstance("请重新获取双重验证码");
  258. }
  259. StringBuilder sb = new StringBuilder();
  260. try {
  261. long c = GoogleGenerator.getCode(apiSecret, DateTime.now().getTime());
  262. sb.append(c);
  263. while (sb.length() < 6) {
  264. sb.insert(0, 0);
  265. }
  266. redisService.incr(numKey, 1l);
  267. } catch (Exception e) {
  268. throw BusinessRuntimeException.getInstance("刷新双重验证码错误,请联系客服");
  269. }
  270. if (clickId != 0) {
  271. //刷新双重验证码记录
  272. DoubleVerifyClickRefreshRecord refreshRecord = new DoubleVerifyClickRefreshRecord();
  273. refreshRecord.setClickId(clickId);
  274. refreshRecord.setUserId(userId);
  275. refreshRecordMapper.insert(refreshRecord);
  276. }
  277. return GatewayResponse.SUCCESS.newBuilder().toResult(sb.toString());
  278. }
  279. /**
  280. * 获取双重验证码记录
  281. */
  282. @GetMapping("/get/doubleVerify/codeList")
  283. public Result<List<DoubleVerifyCodeView>> getDoubleVerifyCodeList(Long relationId) {
  284. long userId = StpUserUtil.getLoginIdAsLong();
  285. List<DoubleVerifyCodeView> views = doubleVerifyRecordMapper.getDoubleVerifyCodeList(userId, relationId);
  286. return GatewayResponse.SUCCESS.newBuilder().toResult(views);
  287. }
  288. /**
  289. * 用户是不是自然流量渠道
  290. * 且未回答答题
  291. */
  292. @GetMapping("/natural/channel")
  293. public Result<Boolean> isNaturalChannel() {
  294. long userId = StpUserUtil.getLoginIdAsLong();
  295. String question_key = RedisService.key.QUESTION_RESPONSE_KEY.getNameFormat(userId);
  296. if (redisService.get(question_key) != null) {
  297. return GatewayResponse.SUCCESS.newBuilder().toResult(false);
  298. }
  299. User user = userService.getById(userId);
  300. if (user.getPopularizeId() != 0) {
  301. redisService.set(question_key, userId, RedisService.key.QUESTION_RESPONSE_KEY.getTimeout());
  302. return GatewayResponse.SUCCESS.newBuilder().toResult(false);
  303. }
  304. if (user.getPopularizeId() == 0) {
  305. QuestionResponseRecord record = questionResponseRecordMapper.selectOne(Wrappers.lambdaQuery(QuestionResponseRecord.class)
  306. .eq(QuestionResponseRecord::getUserId, userId).select(QuestionResponseRecord::getId).last("limit 1"));
  307. if (record != null) {
  308. redisService.set(question_key, userId, RedisService.key.QUESTION_RESPONSE_KEY.getTimeout());
  309. return GatewayResponse.SUCCESS.newBuilder().toResult(false);
  310. }
  311. return GatewayResponse.SUCCESS.newBuilder().toResult(true);
  312. }
  313. return GatewayResponse.SUCCESS.newBuilder().toResult(false);
  314. }
  315. /**
  316. * 问卷记录
  317. */
  318. @PostMapping("/record/replyQuestion")
  319. public Result<String> recordReplyQuestion(@RequestBody @Validated QuestionResponseRecord record) {
  320. long userId = StpUserUtil.getLoginIdAsLong();
  321. User user = userService.getById(userId);
  322. String nickname = user.getNickname();
  323. String question_key = RedisService.key.QUESTION_RESPONSE_KEY.getNameFormat(userId);
  324. QuestionResponseRecord dbRecord = questionResponseRecordMapper.selectOne(Wrappers.lambdaQuery(QuestionResponseRecord.class)
  325. .eq(QuestionResponseRecord::getUserId, userId).select(QuestionResponseRecord::getId).last("limit 1"));
  326. if (dbRecord == null) {
  327. if (redisService.setNx(String.format("%s-%s", userId, nickname), userId, 10l)) {
  328. record.setUserId(userId);
  329. record.setNickname(nickname);
  330. questionResponseRecordMapper.insert(record);
  331. //发放优惠券
  332. couponCommonService.sendCouponToUser(userId, 100l, 0l, 0l, 0l, CouponUser.Channel.ques_response);
  333. redisService.set(question_key, userId, RedisService.key.QUESTION_RESPONSE_KEY.getTimeout());
  334. }
  335. }
  336. return GatewayResponse.SUCCESS.newBuilder().toResult();
  337. }
  338. }