Api to get user from token

This commit is contained in:
harish
2024-08-30 16:29:02 +05:30
parent 6318153300
commit 1184420f89
8 changed files with 80 additions and 13 deletions

View File

@@ -6,12 +6,18 @@ import io.jsonwebtoken.SignatureAlgorithm;
import io.jsonwebtoken.security.Keys; import io.jsonwebtoken.security.Keys;
import jakarta.annotation.PostConstruct; import jakarta.annotation.PostConstruct;
import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletRequest;
import net.gepafin.tendermanagement.config.Translator;
import net.gepafin.tendermanagement.constants.GepafinConstant;
import net.gepafin.tendermanagement.entities.UserEntity; import net.gepafin.tendermanagement.entities.UserEntity;
import net.gepafin.tendermanagement.repositories.UserRepository;
import net.gepafin.tendermanagement.util.Utils; import net.gepafin.tendermanagement.util.Utils;
import net.gepafin.tendermanagement.web.rest.api.errors.Status;
import net.gepafin.tendermanagement.web.rest.api.errors.UnauthorizedAccessException;
import org.apache.commons.lang3.ArrayUtils; import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.time.DateUtils; import org.apache.commons.lang3.time.DateUtils;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value; import org.springframework.beans.factory.annotation.Value;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken; import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication; import org.springframework.security.core.Authentication;
@@ -40,23 +46,43 @@ public class TokenProvider {
@Value("${security.authentication.jwt.token-validity-in-seconds}") @Value("${security.authentication.jwt.token-validity-in-seconds}")
private long tokenValidityInSeconds; private long tokenValidityInSeconds;
@Autowired
private UserRepository userRepository;
private SecretKey key; private SecretKey key;
private static final String AUTHORITIES_KEY = "auth"; private static final String AUTHORITIES_KEY = "auth";
private static final String MERCHANTID="merchantId"; private static final String MERCHANTID="merchantId";
public static final String INVALID_USER = "invalid_user";
static final String AUTH_SECRET = "X-Api-Secret"; static final String AUTH_SECRET = "X-Api-Secret";
private final Set<String> invalidatedTokens = new HashSet<>(); private final Set<String> invalidatedTokens = new HashSet<>();
private static final String USER_ID = "userId";
public UserEntity validateUser(Map<String, Object> userInfo) {
if (userInfo == null || userInfo.get(USER_ID) == null) {
throw new UnauthorizedAccessException(Status.UNAUTHORIZED, Translator.toLocale(GepafinConstant.INVALID_USER));
}
Long userId = Long.valueOf(userInfo.get(USER_ID).toString());
UserEntity userEntity = userRepository.findById(userId).orElse(null);
if (userEntity == null) {
throw new UnauthorizedAccessException(Status.UNAUTHORIZED, Translator.toLocale(GepafinConstant.INVALID_USER));
}
if (!userEntity.getStatus().equals("ACTIVE")) {
throw new UnauthorizedAccessException(Status.UNAUTHORIZED, Translator.toLocale(GepafinConstant.INVALID_USER));
}
return userEntity;
}
@PostConstruct @PostConstruct
public void init() { public void init() {
this.key = Keys.hmacShaKeyFor(secretKey.getBytes(StandardCharsets.UTF_8)); this.key = Keys.hmacShaKeyFor(secretKey.getBytes(StandardCharsets.UTF_8));
log.info("JWT Secret Key initialized."); log.info("JWT Secret Key initialized.");
} }
public String createToken(Authentication authentication, Boolean rememberMe, UserEntity user) { public String createToken(Authentication authentication, Boolean rememberMe, UserEntity user) {
String authorities = authentication.getAuthorities().stream() String authorities = authentication.getAuthorities().stream()
.map(GrantedAuthority::getAuthority) .map(GrantedAuthority::getAuthority)
.collect(Collectors.joining(",")); .collect(Collectors.joining(","));
@@ -75,8 +101,8 @@ public class TokenProvider {
String payload = authentication.getName(); String payload = authentication.getName();
if(user != null) { if(user != null) {
payload += ":"+user.getId(); payload += ":"+user.getId();
} }
String token = Jwts.builder() String token = Jwts.builder()
.setSubject(payload) .setSubject(payload)
@@ -160,7 +186,7 @@ public class TokenProvider {
// isSuperAdmin = true; // isSuperAdmin = true;
// //
// } else // } else
if (!isEmpty(authSecretHeader)) { if (!isEmpty(authSecretHeader)) {
String secret = Utils.decodeBase64String(authSecretHeader); String secret = Utils.decodeBase64String(authSecretHeader);
String[] tokenArr = secret.split("\\.", 2); String[] tokenArr = secret.split("\\.", 2);
String[] merchant = tokenArr[0].split("-"); String[] merchant = tokenArr[0].split("-");
@@ -175,12 +201,12 @@ public class TokenProvider {
if (payload != null && !isSuperAdmin) { if (payload != null && !isSuperAdmin) {
String[] payloadString = payload.split(":");{ String[] payloadString = payload.split(":");{
if (payloadString.length > 1) { if (payloadString.length > 1) {
// userInfo.put(MERCHANTID, payloadString[1]); // userInfo.put(MERCHANTID, payloadString[1]);
// userInfo.put("associatedTags", payloadString[2]); // userInfo.put("associatedTags", payloadString[2]);
userInfo.put("userId", payloadString[1]); userInfo.put("userId", payloadString[1]);
}
} }
}
if (payloadString.length > 1) { if (payloadString.length > 1) {
// userInfo.put(MERCHANTID, payloadString[1]); // userInfo.put(MERCHANTID, payloadString[1]);
@@ -203,7 +229,7 @@ public class TokenProvider {
Gson g = new Gson(); Gson g = new Gson();
return g.fromJson(new String(decoder.decode(parts[1])), Map.class); return g.fromJson(new String(decoder.decode(parts[1])), Map.class);
} }
// public String getSuperUserToken() { // public String getSuperUserToken() {
// return superUserToken; // return superUserToken;
// } // }
public String getUserDetails(String token) { public String getUserDetails(String token) {

View File

@@ -83,5 +83,6 @@ public class GepafinConstant {
public static final String INVALID_STATUS_CHANGE_FROM_DRAFT = "invalid.status.change.from.draft"; public static final String INVALID_STATUS_CHANGE_FROM_DRAFT = "invalid.status.change.from.draft";
public static final String STATUS_CANNOT_BE_CHANGED = "status.cannot.be.changed"; public static final String STATUS_CANNOT_BE_CHANGED = "status.cannot.be.changed";
public static final String PUBLISHED_CALL_NOT_UPDATE = "published.call.not.update"; public static final String PUBLISHED_CALL_NOT_UPDATE = "published.call.not.update";
public static final String INVALID_USER = "invalid_user";
} }

View File

@@ -33,4 +33,6 @@ public interface UserService {
void logoutUser(HttpServletRequest request, HttpServletResponse response); void logoutUser(HttpServletRequest request, HttpServletResponse response);
UserResponseBean updateUserStatus(Long userId, UserStatusEnum statusReq); UserResponseBean updateUserStatus(Long userId, UserStatusEnum statusReq);
UserResponseBean getValidUser(HttpServletRequest request);
} }

View File

@@ -2,6 +2,7 @@ package net.gepafin.tendermanagement.service.impl;
import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import net.gepafin.tendermanagement.config.jwt.TokenProvider;
import net.gepafin.tendermanagement.dao.UserDao; import net.gepafin.tendermanagement.dao.UserDao;
import net.gepafin.tendermanagement.entities.UserEntity; import net.gepafin.tendermanagement.entities.UserEntity;
import net.gepafin.tendermanagement.model.request.LoginReq; import net.gepafin.tendermanagement.model.request.LoginReq;
@@ -16,12 +17,16 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional; import org.springframework.transaction.annotation.Transactional;
import java.util.Map;
@Service @Service
public class UserServiceImpl implements UserService { public class UserServiceImpl implements UserService {
@Autowired @Autowired
private UserDao userDao; private UserDao userDao;
@Autowired
private TokenProvider tokenProvider;
@Transactional(rollbackFor = Exception.class) @Transactional(rollbackFor = Exception.class)
public UserResponseBean createUser(UserReq userReq) { public UserResponseBean createUser(UserReq userReq) {
@@ -81,4 +86,11 @@ public class UserServiceImpl implements UserService {
return userDao.updateUserStatus(userId, statusReq); return userDao.updateUserStatus(userId, statusReq);
} }
@Override
@Transactional(readOnly = true)
public UserResponseBean getValidUser(HttpServletRequest request) {
Map<String, Object> userInfo= tokenProvider.getUserInfoAndUserIdFromToken(request);
UserEntity user=tokenProvider.validateUser(userInfo);
return userDao.getUserById(user.getId());
}
} }

View File

@@ -11,6 +11,7 @@ import jakarta.validation.Valid;
import net.gepafin.tendermanagement.entities.UserEntity; import net.gepafin.tendermanagement.entities.UserEntity;
import net.gepafin.tendermanagement.enums.UserStatusEnum; import net.gepafin.tendermanagement.enums.UserStatusEnum;
import net.gepafin.tendermanagement.model.request.*; import net.gepafin.tendermanagement.model.request.*;
import net.gepafin.tendermanagement.model.response.RoleResponseBean;
import net.gepafin.tendermanagement.model.response.UserResponseBean; import net.gepafin.tendermanagement.model.response.UserResponseBean;
import net.gepafin.tendermanagement.model.util.JWTToken; import net.gepafin.tendermanagement.model.util.JWTToken;
import net.gepafin.tendermanagement.model.util.Response; import net.gepafin.tendermanagement.model.util.Response;
@@ -22,6 +23,8 @@ import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import java.util.List;
@Validated @Validated
public interface UserApi { public interface UserApi {
@@ -174,7 +177,18 @@ public interface UserApi {
@Parameter(description = "status", required = true)@RequestParam(value = "status", required = true) UserStatusEnum status) { @Parameter(description = "status", required = true)@RequestParam(value = "status", required = true) UserStatusEnum status) {
return new ResponseEntity<>(HttpStatus.NOT_IMPLEMENTED); return new ResponseEntity<>(HttpStatus.NOT_IMPLEMENTED);
} }
@Operation(summary = "Api to get valid user from token",
responses = {
@ApiResponse(responseCode = "200", description = "OK"),
@ApiResponse(responseCode = "404", description = "Not Found", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = {
@ExampleObject(value = ErrorConstants.NOTFOUND_ERROR_EXAMPLE) })),
@ApiResponse(responseCode = "401", description = "Unauthorized", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = {
@ExampleObject(value = ErrorConstants.UNAUTHORIZED_ERROR_EXAMPLE) })),
@ApiResponse(responseCode = "400", description = "Bad Request", content = @Content(mediaType = MediaType.APPLICATION_JSON_VALUE, examples = {
@ExampleObject(value = ErrorConstants.BADREQUEST_ERROR_EXAMPLE) })) })
@GetMapping(value = "/me",
produces = { "application/json" })
ResponseEntity<Response<UserResponseBean>> getValidUser(HttpServletRequest request);
} }

View File

@@ -9,6 +9,7 @@ import net.gepafin.tendermanagement.constants.GepafinConstant;
import net.gepafin.tendermanagement.entities.UserEntity; import net.gepafin.tendermanagement.entities.UserEntity;
import net.gepafin.tendermanagement.enums.UserStatusEnum; import net.gepafin.tendermanagement.enums.UserStatusEnum;
import net.gepafin.tendermanagement.model.request.*; import net.gepafin.tendermanagement.model.request.*;
import net.gepafin.tendermanagement.model.response.RoleResponseBean;
import net.gepafin.tendermanagement.model.response.UserResponseBean; import net.gepafin.tendermanagement.model.response.UserResponseBean;
import net.gepafin.tendermanagement.model.util.JWTToken; import net.gepafin.tendermanagement.model.util.JWTToken;
import net.gepafin.tendermanagement.model.util.Response; import net.gepafin.tendermanagement.model.util.Response;
@@ -23,6 +24,8 @@ import org.springframework.http.ResponseEntity;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import java.util.List;
@RestController @RestController
@RequestMapping("${openapi.gepafin.base-path:/v1/user}") @RequestMapping("${openapi.gepafin.base-path:/v1/user}")
@Validated @Validated
@@ -118,5 +121,12 @@ public class UserApiController implements UserApi {
UserResponseBean updatedUser = userService.updateUserStatus(userId, status); UserResponseBean updatedUser = userService.updateUserStatus(userId, status);
return ResponseEntity.ok(new Response<>(updatedUser, Status.SUCCESS, Translator.toLocale(GepafinConstant.UPDATE_USER_STATUS_SUCCESS_MSG))); return ResponseEntity.ok(new Response<>(updatedUser, Status.SUCCESS, Translator.toLocale(GepafinConstant.UPDATE_USER_STATUS_SUCCESS_MSG)));
} }
@Override
public ResponseEntity<Response<UserResponseBean>> getValidUser(HttpServletRequest request) {
log.info("Get Valid User Detail");
UserResponseBean user = userService.getValidUser(request);
return ResponseEntity.status(HttpStatus.OK)
.body(new Response<>(user, Status.SUCCESS, Translator.toLocale(GepafinConstant.GET_USER_SUCCESS_MSG)));
}
} }

View File

@@ -62,6 +62,7 @@ published.call.not.update=Published call cannot be updated.
login.successfully=Login successfully. login.successfully=Login successfully.
pass.min.len.msg=Password must be at least 8 characters long. pass.min.len.msg=Password must be at least 8 characters long.
email.already.exists=A user with this email already exists. email.already.exists=A user with this email already exists.
invalid_user=User validation failed. Check user info, account status, and token expiration.
#Global messages #Global messages
common_message=Something went wrong..Please try again.. common_message=Something went wrong..Please try again..

View File

@@ -61,6 +61,7 @@ published.call.not.update=Il bando pubblicato non pu
login.successfully=Accesso effettuato con successo. login.successfully=Accesso effettuato con successo.
pass.min.len.msg=La password deve essere lunga almeno 8 caratteri. pass.min.len.msg=La password deve essere lunga almeno 8 caratteri.
email.already.exists=Esiste gi� un utente con questa email. email.already.exists=Esiste gi� un utente con questa email.
invalid_user=Validazione utente fallita. Controlla le informazioni, lo stato dell'account e la scadenza del token.
#Global messages #Global messages
common_message=qualcosa é andato storto. Per favore riprova common_message=qualcosa é andato storto. Per favore riprova