From 3b55d06b89bf64873e685c3d78fce5affbba3d17 Mon Sep 17 00:00:00 2001 From: zheng_wenlong Date: Tue, 16 Apr 2019 11:20:38 +0900 Subject: Add warehouse server source code. [Patch Set 2] Add ReadMe.md Change-Id: I6ade52d2490f5ca4ba107c1a27ed6d5b39048725 Signed-off-by: zheng_wenlong --- .../market/token/service/RedisTokenManager.java | 268 +++++++++++++++++++++ 1 file changed, 268 insertions(+) create mode 100644 webservice/src/main/java/app/market/token/service/RedisTokenManager.java (limited to 'webservice/src/main/java/app/market/token/service/RedisTokenManager.java') diff --git a/webservice/src/main/java/app/market/token/service/RedisTokenManager.java b/webservice/src/main/java/app/market/token/service/RedisTokenManager.java new file mode 100644 index 0000000..aea419e --- /dev/null +++ b/webservice/src/main/java/app/market/token/service/RedisTokenManager.java @@ -0,0 +1,268 @@ +/* + * Copyright (c) 2019 TOYOTA MOTOR CORPORATION + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package app.market.token.service; + +import java.util.List; +import java.util.UUID; +import java.util.concurrent.TimeUnit; + +import org.apache.commons.lang3.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.stereotype.Component; + +import app.market.WebServiceConstants; +import app.market.model.resource.Resource; +import app.market.model.user.User; +import app.market.token.dao.RedisGeneratorDao; +import app.market.utils.constants.Constants; +import app.market.utils.token.TokenModel; +import app.market.utils.webservice.WebServiceURI; + +@Component +public class RedisTokenManager extends RedisGeneratorDao { + + private static Logger logger = LoggerFactory.getLogger( RedisTokenManager.class ); + + /** + * generate token + * @param loginId + * @param user + * @param list + * @param isPermanent guestUser not expire + * @return + */ + public TokenModel generateToken(String loginId, User user, List list, boolean isPermanent ) { + // user UUID as token + String token = UUID.randomUUID().toString().replace( "-", "" ); + TokenModel model = new TokenModel( loginId, user, token ); + for (Resource res : list) { + if ( res.getResType().equals( WebServiceConstants.RESOURSE_TYPE_RES ) ) { + model.getResourceList().add( res ); + } else if ( res.getResType().equals( WebServiceConstants.RESOURSE_TYPE_API ) ) { + model.getApiList().add( res ); + } + } + // save token, set expire time + if(isPermanent){ + redis.boundValueOps( loginId ).set( model ); + }else{ + redis.boundValueOps( loginId ).set( model, WebServiceConstants.EXPIRE_TIME_MINUTES, TimeUnit.MINUTES ); + } + return model; + } + + + public String generateRefreshToken(String loginId) { + String token = UUID.randomUUID().toString().replace( "-", "" ); + redis.boundValueOps( token ).set( loginId, WebServiceConstants.EXPIRE_TIME_HOURS, TimeUnit.HOURS ); + return token; + } + + public int checkAuthentication(String authentication, String servletPath, String url, String httpMethod) { + int ret = Constants.STATUS_SUCCESS; + if(StringUtils.isEmpty(authentication)){ //guest + ret = validateAuthentication(authentication, servletPath, url, httpMethod); + }else{ + ret = validateToken(authentication, servletPath, url, httpMethod); + } + return ret; + } + + /** + * check Authentication when guest + * @param authentication + * @param servletPath + * @param httpMethod + * @param url + * @return + */ + private int validateAuthentication(String authentication, String servletPath, String url, String httpMethod) { + int ret = Constants.STATUS_FORBIDDEN; + String guestId = Constants.GUEST_ID; + TokenModel model = null; + + if (redis.opsForValue().get(guestId) instanceof TokenModel) { + model = (TokenModel) redis.opsForValue().get(guestId); + } + + if (model == null) { + //ResourceRestController.initGuestResoureList(Constants.GUEST_ID); + logger.debug( "validateAuthentication" + this.getClass().getName() + "--method: " + + Thread.currentThread().getStackTrace()[1].getMethodName() + "model is null" ); + ret = Constants.STATUS_ERROR; + } + + if(checkResoureAuth(model, servletPath, url, httpMethod)) { + ret = Constants.STATUS_SUCCESS; + }else { + ret = Constants.STATUS_FORBIDDEN; + } + + return ret; + } + + /** + * check Authentication when not guest + * @param authentication + * @param servletPath + * @param httpMethod + * @param url + * @return + */ + private int validateToken(String authentication, String servletPath, String url, String httpMethod) { + TokenModel model = getToken( authentication ); + + if ( model == null ) + return Constants.STATUS_UNAUTHORIZED; + // Only one account is online as one time + if ( !model.getToken().equals( authentication.split( Constants.TOKEN_SEPARATOR )[1] ) ) { + return Constants.STATUS_TOO_MANY_CONNECTIONS; + } + // get cache token + TokenModel cacheModel = getCacheModel( model.getLoginId() ); + // check cache token + if ( cacheModel == null ) + return Constants.STATUS_UNAUTHORIZED; + + String token = cacheModel.getToken(); + if ( !token.equals( model.getToken() ) ) + return Constants.STATUS_UNAUTHORIZED; + + if (!checkResoureAuth(cacheModel, servletPath, url, httpMethod)) { + return Constants.STATUS_FORBIDDEN; + } + + // check ok, reset expire time + redis.boundValueOps( model.getLoginId() ).expire( WebServiceConstants.EXPIRE_TIME_MINUTES, TimeUnit.SECONDS ); + return Constants.STATUS_SUCCESS; + } + + /** + * + * @param list + * @param resPath + * @return + */ + private boolean checkResoureAuth(TokenModel model, String resPath, String url, String httpMethod) { + boolean ret = false; + + if (StringUtils.isEmpty(resPath) && !url.contains(WebServiceURI.REST_TOKEN_VALIDATETOKENAUTHORTICATION_LF)) { //URL check + + int s = url.indexOf(WebServiceConstants.PATTERN_RESOURSE_S); + if (s < 0) { + return ret; + } + resPath = url.substring(s + WebServiceConstants.PATTERN_RESOURSE_S.length()-1); + if (resPath.endsWith(WebServiceConstants.SEPARATOR)) { + resPath = resPath.substring(0, resPath.length() - 1); + } + + int count = (resPath.split(WebServiceConstants.SEPARATOR)).length; + + List list = model.getApiList(); + for (Object obj : list) { + Resource r = (Resource) obj; + + //httpmethod check + if (!r.getHttpMethod().equalsIgnoreCase(httpMethod)){ + continue; + } + + //url length check + if(count != r.getAccessPath().split(WebServiceConstants.SEPARATOR).length) { + continue; + } + + String rUrl = r.getAccessPath(); + //delete param depart of url + int paramS = r.getAccessPath().indexOf(WebServiceConstants.PATTERN_RESOURSE_PARAM_S); + if (paramS > 0) { + rUrl = r.getAccessPath().substring(0, paramS); + } + + //url check + if (resPath.indexOf(rUrl) == 0) { + ret = true; + break; + } + } + + } else if(url.contains(WebServiceURI.REST_TOKEN_VALIDATETOKENAUTHORTICATION_LF)){ + // temp code + ret = true; + } else {//For web selertPath check; + List list = model.getResourceList(); + for (Object obj : list) { + Resource res = (Resource) obj; + if (res.getAccessPath().contains(resPath)) { + ret = true; + break; + } + } + } + return ret; + } + + public TokenModel getToken(String authentication) { + String loginId =""; + if (StringUtils.isEmpty(authentication)) { + loginId = Constants.GUEST_ID; + } else { + String[] param = authentication.split(Constants.TOKEN_SEPARATOR); + if (param.length != 2){ + return null; + } + loginId = param[0]; + } + TokenModel model = null; + if (redis.opsForValue().get(loginId) instanceof TokenModel) { + model = (TokenModel) redis.opsForValue().get(loginId); + } + return model; + } + + public TokenModel getCacheModel(String loginId) { + try { + return (TokenModel) redis.boundValueOps( loginId ).get(); + } catch ( Exception e ) { + return null; + } + } + + public String getRefreshtokenValue(String authentication) { + if (StringUtils.isEmpty(authentication)) { + return null; + } + String[] param = authentication.split(Constants.TOKEN_SEPARATOR); + if (param.length != 2){ + return null; + } + String loginId = (String) redis.opsForValue().get(param[1]); + + return loginId; + } + + public void updateTokenInfo(TokenModel model) { + redis.boundValueOps( model.getLoginId() ).set( model, WebServiceConstants.EXPIRE_TIME_MINUTES, + TimeUnit.MINUTES ); + } + + public void deleteToken(String loginId) { + redis.delete( loginId ); + } + +} -- cgit 1.2.3-korg