UserServiceImpl.java
6.92 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
package isa.qa.service.impl;
import isa.qa.config.security.GeneratorUserDetailService;
import isa.qa.config.security.SecurityUser;
import isa.qa.core.ServiceException;
import isa.qa.dao.RoleDao;
import isa.qa.dao.UserDao;
import isa.qa.dto.request.UserLoginRequestDTO;
import isa.qa.dto.request.UserRegisterRequestDTO;
import isa.qa.dto.request.UserRequestDTO;
import isa.qa.entity.Role;
import isa.qa.entity.User;
import isa.qa.service.UserService;
import lombok.AllArgsConstructor;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.context.SecurityContext;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.session.FindByIndexNameSessionRepository;
import org.springframework.session.Session;
import org.springframework.session.data.redis.RedisOperationsSessionRepository;
import org.springframework.stereotype.Service;
import org.springframework.transaction.TransactionException;
import org.springframework.transaction.annotation.Transactional;
import java.security.Principal;
import java.time.Instant;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.concurrent.TimeUnit;
import static isa.qa.constants.CacheConstants.KEY_PREFIX_VERIFY_CODE;
import static isa.qa.utils.ArgumentCheckUtils.checkEquals;
import static isa.qa.utils.ArgumentCheckUtils.checkNonNull;
import static isa.qa.utils.ResultMapUtils.genIdResultMap;
import static isa.qa.utils.ResultMapUtils.genUpdateResultMap;
import static java.lang.Boolean.TRUE;
import static org.apache.commons.lang3.RandomStringUtils.randomNumeric;
import static org.apache.commons.lang3.StringUtils.isNotEmpty;
/**
* User service implement
*
* @author May
* @version 1.0
* @date 2018/11/22 9:48
*/
@Service
@AllArgsConstructor
public class UserServiceImpl implements UserService {
/**
* logger
*/
private static final Logger LOGGER = LoggerFactory.getLogger(UserServiceImpl.class);
private final UserDao userDao;
private final RoleDao roleDao;
private final PasswordEncoder passwordEncoder;
private final AuthenticationManager authenticationManager;
private final GeneratorUserDetailService userDetailService;
private final StringRedisTemplate stringRedisTemplate;
private final FindByIndexNameSessionRepository<? extends Session> sessionRepository;
private final RedisOperationsSessionRepository redisOperationsSessionRepository;
@Override
public List<User> listUser() {
return userDao.findAll();
}
@Override
public SecurityUser login(UserLoginRequestDTO loginRequestDTO) {
//根据用户输入的账号及密码生成AuthenticationToken
UsernamePasswordAuthenticationToken upToken = new UsernamePasswordAuthenticationToken(
loginRequestDTO.getEmail(), loginRequestDTO.getPassword());
try {
//用户名密码登陆效验
final Authentication authentication = authenticationManager.authenticate(upToken);
//认证成功,将认证信息存入holder中
SecurityContext ctx = SecurityContextHolder.createEmptyContext();
SecurityContextHolder.setContext(ctx);
SecurityContextHolder.getContext().setAuthentication(authentication);
return userDetailService.loadUserByUsername(loginRequestDTO.getEmail());
} catch (AuthenticationException e) {
throw new ServiceException("用户不存在或密码错误");
}
}
@Override
@Transactional(rollbackFor = TransactionException.class)
public Map<String, Long> registerUser(UserRegisterRequestDTO registerRequestDTO) {
Role role = roleDao.getOne(registerRequestDTO.getRoleId());
checkNonNull(role, "未找到对应的角色");
String cachedVerifyCode = stringRedisTemplate.opsForValue().get(KEY_PREFIX_VERIFY_CODE + registerRequestDTO.getEmail());
checkEquals(registerRequestDTO.getVerifyCode(), cachedVerifyCode, "验证码错误或已失效");
Date now = Date.from(Instant.now());
User user = new User();
user.setRole(role);
user.setName(registerRequestDTO.getName());
user.setPhone(registerRequestDTO.getPhone());
user.setPassword(passwordEncoder.encode(registerRequestDTO.getPassword()));
user.setIsEnabled(TRUE);
user.setEmail(registerRequestDTO.getEmail());
user.setRegisterTime(now);
user.setUpdatedTime(now);
user.setLastPasswordResetTime(now);
userDao.save(user);
return genIdResultMap("userId", user.getId());
}
@Override
public Map<String, Boolean> logout(Principal principal) {
String phone = principal.getName();
SecurityContextHolder.clearContext();
// 查询用户的 Session 信息,返回值 key 为 sessionId
// Map<String, ? extends Session> userSessions = sessionRepository.findByIndexNameAndIndexValue(FindByIndexNameSessionRepository.PRINCIPAL_NAME_INDEX_NAME, phone);
// // 移除用户的 session 信息
// List<String> sessionIds = new ArrayList<>(userSessions.keySet());
// for (String session : sessionIds) {
// redisOperationsSessionRepository.deleteById(session);
// }
return genUpdateResultMap("isSuccess", TRUE);
}
@Override
public Map<String, Boolean> checkEmail(String email) {
Optional<User> user = userDao.findByEmail(email);
return genUpdateResultMap("isRegistered", user.isPresent());
}
@Override
@Transactional(rollbackFor = TransactionException.class)
public Map<String, Boolean> updateUser(Long id, UserRequestDTO userRequestDTO) {
User user = userDao.getOne(id);
checkNonNull(user, "未找到对应的用户");
if (isNotEmpty(userRequestDTO.getName())) {
user.setName(userRequestDTO.getName());
}
if (isNotEmpty(userRequestDTO.getEmail())) {
user.setEmail(userRequestDTO.getEmail());
}
user.setUpdatedTime(Date.from(Instant.now()));
userDao.save(user);
return genUpdateResultMap("isSuccess", TRUE);
}
@Override
public Map<String, Boolean> sendVerifyCode(String phone) {
String verifyCode = randomNumeric(6);
LOGGER.debug("Email={}, VerifyCode={}", phone, verifyCode);
String key = KEY_PREFIX_VERIFY_CODE + phone;
stringRedisTemplate.opsForValue().set(key, verifyCode);
stringRedisTemplate.expire(key, 180, TimeUnit.SECONDS);
return genUpdateResultMap(key, TRUE);
}
}