package com.cyksj.service.user.impl; import cn.hutool.core.bean.BeanUtil; import cn.hutool.core.date.DateTime; import cn.hutool.core.date.DateUtil; import cn.hutool.core.util.RandomUtil; import cn.hutool.core.util.StrUtil; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.cyksj.common.constant.Constant; import com.cyksj.common.exception.BusinessRuntimeException; import com.cyksj.common.i18n.I18nMessageUtil; import com.cyksj.common.task.GlobalThreadPoolTaskExecutor; import com.cyksj.common.util.Codec; import com.cyksj.common.util.Jsons; import com.cyksj.common.util.StringUtil; import com.cyksj.dto.UserSharedDto; import com.cyksj.mapper.GroupsRelationMapper; import com.cyksj.mapper.OrderDonMapper; import com.cyksj.mapper.PhoneCodeMapper; import com.cyksj.mapper.UserMapper; import com.cyksj.mapper.manage.distribute.UserDistributeSharedMapper; import com.cyksj.mapper.market.UserBindDetailMapper; import com.cyksj.model.dto.OrderDonPostDataDto; import com.cyksj.model.dto.UserWhoami; import com.cyksj.model.entity.*; import com.cyksj.model.request.ExchangeCodeTicket; import com.cyksj.model.request.LoginReq; import com.cyksj.model.request.OrderBindCommonReq; import com.cyksj.redis.RedisService; import com.cyksj.service.exchange.ExchangeCodeService; import com.cyksj.service.user.UserService; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.springframework.dao.DuplicateKeyException; import org.springframework.stereotype.Service; import org.springframework.util.Assert; import java.util.ArrayList; import java.util.Date; import java.util.List; import java.util.Optional; /** * @author chan * @date 2021/10/10 下午3:27 */ @Slf4j @Service @RequiredArgsConstructor public class UserServiceImpl extends ServiceImpl implements UserService { private final RedisService redisService; private final UserBindDetailMapper userBindDetailMapper; private final UserMapper userMapper; private final PhoneCodeMapper phoneCodeMapper; private final UserDistributeSharedMapper userDistributeSharedMapper; private final OrderDonMapper orderDonMapper; private final ExchangeCodeService exchangeCodeService; private final GroupsRelationMapper relationMapper; private static final GlobalThreadPoolTaskExecutor TASK_POOL = GlobalThreadPoolTaskExecutor.getInstance(); @Override public UserWhoami whoami(long userId) { User user = this.getById(userId); Assert.notNull(user, I18nMessageUtil.getI18nMsg("login_code_expired")); UserWhoami userWhoami = new UserWhoami(); if (StrUtil.isEmpty(user.getShowId())) { user.setShowId(getUserShowId(userId)); } BeanUtil.copyProperties(user, userWhoami); UserBindDetail bindPhone = userBindDetailMapper.selectOne(Wrappers.lambdaQuery(UserBindDetail.class) .eq(UserBindDetail::getUserId, userId).last("limit 1")); //手机号 if (bindPhone != null) { userWhoami.setBindPhone(bindPhone.getPhone()); userWhoami.setBindEmail(bindPhone.getEmail()); } Integer type = 3; if (StrUtil.isNotBlank(user.getLoginPhone())) { type = 1; } else if (StrUtil.isNotBlank(user.getEmail())) { type = 2; } userWhoami.setType(type); return userWhoami; } @Override public List getRelationUserIdList(Long userId, User selectUser) { List userIds = new ArrayList<>(); userIds.add(userId); UserBindDetail userBindDetail = userBindDetailMapper.selectOne(Wrappers.lambdaQuery(UserBindDetail.class) .eq(UserBindDetail::getUserId, userId).last("limit 1")); if (userBindDetail == null) { User user = Optional.ofNullable(selectUser).orElse(this.getById(userId)); if (StrUtil.isEmpty(user.getOpenId()) && StrUtil.isNotEmpty(user.getLoginPhone())) { userBindDetail = userBindDetailMapper.selectOne(Wrappers.lambdaQuery(UserBindDetail.class) .eq(UserBindDetail::getPhone, user.getLoginPhone()).last("limit 1")); if (userBindDetail != null) { userIds.add(userBindDetail.getUserId()); } } } else { if (StrUtil.isNotBlank(userBindDetail.getPhone())) { User otherUser = this.getOne(Wrappers.lambdaQuery(User.class) .eq(User::getLoginPhone, userBindDetail.getPhone()).last("limit 1")); if (otherUser != null) { userIds.add(otherUser.getId()); } } } return userIds; } @Override public List getUserIdsByNickname(String nickname) { return userMapper.selectListByNickname(nickname); } @Override public String getUserShowId(Long userId) { Integer update = 0; String showId = null; while (update != 1) { showId = StringUtil.randomString(5); try { update = userMapper.update(null, Wrappers.lambdaUpdate(User.class) .set(User::getShowId, showId) .eq(User::getId, userId)); } catch (DuplicateKeyException e) { update = 0; } } return showId; } @Override public Long getUserIdByShowId(String showId) { return userMapper.getUserIdByShowId(showId); } @Override public User webLogin(LoginReq loginReq) throws Exception { LambdaQueryWrapper wrapper = Wrappers.lambdaQuery(User.class).last("limit 1"); if (loginReq.getType() == null || loginReq.getType() < 1 || loginReq.getType() > 3) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("sys_error")); } if (loginReq.getType() == 1) { if (StrUtil.hasEmpty(loginReq.getPhone(), loginReq.getCode())) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("params_error")); } DateTime now = DateTime.now(); PhoneCode phoneCode = phoneCodeMapper.selectOne(Wrappers.lambdaQuery(PhoneCode.class).eq(PhoneCode::getPhone, loginReq.getPhone()).last("limit 1")); if (phoneCode == null || StrUtil.isEmpty(phoneCode.getCode())) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("phone_code_valid_error")); } //3分钟失效 Date updateTime = phoneCode.getUpdateTime(); DateTime afterFiveMinutes = DateUtil.offsetMinute(updateTime, 3); if (now.isAfter(afterFiveMinutes)) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("phone_code_valid_error")); } if (!StrUtil.equals(loginReq.getCode(), phoneCode.getCode())) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("verify_code_error")); } wrapper.eq(User::getLoginPhone, loginReq.getPhone()); } if (loginReq.getType() == 2) { if (StrUtil.isEmpty(loginReq.getEmail())) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("params_error")); } String code = redisService.getStr(RedisService.key.EMAIL_CODE_KEY.getNameFormat(loginReq.getEmail())); if (StrUtil.isEmpty(code)) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("email_code_valid_error")); } if (!StrUtil.equals(loginReq.getCode(), code)) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("verify_code_error")); } wrapper.eq(User::getEmail, loginReq.getEmail()); redisService.del(RedisService.key.EMAIL_CODE_KEY.getNameFormat(loginReq.getEmail())); } if (loginReq.getType() == 3) { wrapper.eq(User::getEmail, loginReq.getEmail()); } //保存用户信息 User user = this.getOne(wrapper); String dsCode = loginReq.getDsCode(); Long sharedId = loginReq.getSharedId(); Long dsPopularizeId = null; Integer dsType = loginReq.getDsType(); Boolean isNewUser = false; if (StrUtil.isNotBlank(dsCode)) { dsCode = dsCode.trim(); User sharedUser = this.getOne(Wrappers.lambdaQuery(User.class) .eq(User::getShowId, dsCode).last("limit 1")); if (sharedUser != null) { sharedId = sharedUser.getId(); } } if (user == null) { user = new User(); isNewUser = true; StringBuilder name = new StringBuilder(); name.append(Constant.DEFAULT_NAME); if (loginReq.getPopularizeId() != null) { user.setPopularizeId(loginReq.getPopularizeId()); } if (loginReq.getType() == 1) { user.setLoginPhone(loginReq.getPhone()); } if (loginReq.getType() == 2 || loginReq.getType() == 3) { user.setEmail(loginReq.getEmail()); name.append("@"); } user.setNickname(String.format("%s%s", name.toString(), Codec.DoDigest.custom().setAlgorithm(Codec.DoDigest.Algorithm.MD5).setStringData(String.format("%s%s", RandomUtil.randomString(6), loginReq.getType() == 1 ? user.getLoginPhone() : user.getEmail())).toHexString().substring(0, 6))); //默认头像 user.setHeadimgurl(Constant.DEFAULT_HEAD_IMG); String registerEnv = loginReq.getRegisterEnv(); user.setRegisterEnv(StrUtil.isEmpty(registerEnv) ? User.RegisterEnv.pc.name() : registerEnv); if (loginReq.getType() == 3) { user.setEmail(loginReq.getEmail()); } this.save(user); //缓存用户注册 回传信息 String callback = loginReq.getCallback(); String callbackType = loginReq.getCallbackType(); if (StrUtil.isNotBlank(callback)) { OrderDonPostDataDto orderDonPostDataDto = new OrderDonPostDataDto().setCallback(callback) .setCallbackType(callbackType); redisService.set(RedisService.key.ORDER_DON_POST_DATA_USER_KEY.getName() + user.getId(), Jsons.toJson(orderDonPostDataDto)); } final String login_email = user.getEmail(); final String login_phone = user.getLoginPhone(); UserBindDetail bindDetail = userBindDetailMapper.selectOne(Wrappers.lambdaQuery(UserBindDetail.class) .and(ub -> ub.eq(StrUtil.isNotBlank(login_email), UserBindDetail::getEmail, login_email) .or().eq(StrUtil.isNotBlank(login_phone), UserBindDetail::getPhone, login_phone)) .last("limit 1")); if (bindDetail != null) { if (StrUtil.isNotBlank(login_phone)) { bindDetail.setPhoneUserId(user.getId()); } if (StrUtil.isNotBlank(login_email)) { bindDetail.setEmailUserId(user.getId()); } userBindDetailMapper.updateById(bindDetail); } } if (StrUtil.isEmpty(user.getShowId())) { user.setShowId(getUserShowId(user.getId())); } Optional.ofNullable(user.getIsBlack()) .ifPresent(black -> { if (black) { throw BusinessRuntimeException.getInstance(I18nMessageUtil.getI18nMsg("user_black_error")); } }); return user; } @Override public UserSharedDto getUserShredDtoByDsCode(String dsCode) { Long sharedId = 0l; Long dsPopularizeId = 0l; dsCode = dsCode.trim(); User sharedUser = getOne(Wrappers.lambdaQuery(User.class) .eq(User::getShowId, dsCode).last("limit 1")); if (sharedUser != null) { sharedId = sharedUser.getId(); } UserSharedDto sharedDto = new UserSharedDto(); sharedDto.setSharedId(sharedId); sharedDto.setDsPopularizeId(dsPopularizeId); return sharedDto; } @Override public Long getSharedIdByUserId(Long userId) { UserDistributeShared distributeShared = userDistributeSharedMapper.selectOne(Wrappers.lambdaQuery(UserDistributeShared.class) .eq(UserDistributeShared::getUserId, userId) .last("limit 1") .select(UserDistributeShared::getSharedId)); if (distributeShared == null) { return 0l; } return distributeShared.getSharedId(); } @Override public void bindUserOrder(OrderBindCommonReq orderBindCommonReq) { String orderNo = orderBindCommonReq.getOrderNo(); OrderDon orderDon = orderDonMapper.selectOne(Wrappers.lambdaQuery(OrderDon.class) .eq(OrderDon::getOrderNo, orderNo) .eq(OrderDon::getUserId, 0) .last("limit 1")); if (orderDon == null) { return; } orderDon.setUserId(orderBindCommonReq.getUserId()); GroupsRelation relation = relationMapper.selectOne(Wrappers.lambdaQuery(GroupsRelation.class) .eq(GroupsRelation::getId, orderDon.getRelationId()) .eq(GroupsRelation::getStatus, GroupsRelation.Status.validity) .last("limit 1")); //免登录兑换流程未成功 继续兑换 if (relation == null) { String exCode = orderDon.getExCode(); ExchangeCodeTicket exchangeCodeTicket = new ExchangeCodeTicket(); exchangeCodeTicket.setCode(exCode); exchangeCodeService.getTicketByExchangeCode(exchangeCodeTicket, orderBindCommonReq.getUserId()); orderDonMapper.updateById(orderDon); } } }