forked from matrixorigin/matrixorigin.io
-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #5 from addw1/ning/summer-code
Added the token interceptor for the http req
- Loading branch information
Showing
12 changed files
with
346 additions
and
2 deletions.
There are no files selected for viewing
26 changes: 26 additions & 0 deletions
26
...bot-chat-server/src/main/java/com/ning/codebot/common/common/annotation/RedissonLock.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
package com.ning.codebot.common.common.annotation; | ||
|
||
import java.lang.annotation.ElementType; | ||
import java.lang.annotation.Retention; | ||
import java.lang.annotation.RetentionPolicy; | ||
import java.lang.annotation.Target; | ||
import java.util.concurrent.TimeUnit; | ||
|
||
/** | ||
* distributed lock | ||
*/ | ||
@Retention(RetentionPolicy.RUNTIME) | ||
@Target(ElementType.METHOD) | ||
public @interface RedissonLock { | ||
|
||
String prefixKey() default ""; | ||
String key(); | ||
/** | ||
* do not wait -1 | ||
* @return second | ||
*/ | ||
int waitTime() default -1; | ||
TimeUnit unit() default TimeUnit.MILLISECONDS; | ||
|
||
} | ||
|
36 changes: 36 additions & 0 deletions
36
...t-chat-server/src/main/java/com/ning/codebot/common/common/aspect/RedissonLockAspect.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
package com.ning.codebot.common.common.aspect; | ||
|
||
|
||
import cn.hutool.core.util.StrUtil; | ||
import com.ning.codebot.common.common.annotation.RedissonLock; | ||
import com.ning.codebot.common.common.service.LockService; | ||
import lombok.extern.slf4j.Slf4j; | ||
import org.aspectj.lang.ProceedingJoinPoint; | ||
import org.aspectj.lang.annotation.Around; | ||
import org.aspectj.lang.annotation.Aspect; | ||
import org.aspectj.lang.reflect.MethodSignature; | ||
import org.springframework.beans.factory.annotation.Autowired; | ||
import org.springframework.core.annotation.Order; | ||
import org.springframework.stereotype.Component; | ||
import com.ning.codebot.common.common.utils.SpElUtils; | ||
|
||
import java.lang.reflect.Method; | ||
|
||
@Slf4j | ||
@Aspect | ||
@Component | ||
@Order(0) | ||
public class RedissonLockAspect { | ||
@Autowired | ||
private LockService lockService; | ||
|
||
@Around("@annotation(com.ning.codebot.common.common.annotation.RedissonLock)") | ||
public Object around(ProceedingJoinPoint joinPoint) throws Throwable { | ||
Method method = ((MethodSignature) joinPoint.getSignature()).getMethod(); | ||
RedissonLock redissonLock = method.getAnnotation(RedissonLock.class); | ||
String prefix = StrUtil.isBlank(redissonLock.prefixKey()) ? SpElUtils.getMethodKey(method) : redissonLock.prefixKey();//默认方法限定名+注解排名(可能多个) | ||
String key = SpElUtils.parseSpEl(method, joinPoint.getArgs(), redissonLock.key()); | ||
return lockService.executeWithLockThrows(prefix + ":" + key, redissonLock.waitTime(), redissonLock.unit(), joinPoint::proceed); | ||
} | ||
} | ||
|
23 changes: 23 additions & 0 deletions
23
...ot-chat-server/src/main/java/com/ning/codebot/common/common/config/InterceptorConfig.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
package com.ning.codebot.common.common.config; | ||
|
||
import com.ning.codebot.common.common.interceptor.TokenInterceptor; | ||
import org.springframework.beans.factory.annotation.Autowired; | ||
import org.springframework.context.annotation.Configuration; | ||
import org.springframework.web.servlet.config.annotation.InterceptorRegistry; | ||
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; | ||
|
||
@Configuration | ||
public class InterceptorConfig implements WebMvcConfigurer { | ||
|
||
@Autowired | ||
private TokenInterceptor tokenInterceptor; | ||
|
||
@Override | ||
public void addInterceptors(InterceptorRegistry registry) { | ||
registry.addInterceptor(tokenInterceptor) | ||
.addPathPatterns("/codebot/**"); | ||
|
||
} | ||
} | ||
|
||
|
8 changes: 8 additions & 0 deletions
8
...ode-bot-chat-server/src/main/java/com/ning/codebot/common/common/exception/ErrorEnum.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
package com.ning.codebot.common.common.exception; | ||
|
||
public interface ErrorEnum { | ||
|
||
Integer getErrorCode(); | ||
|
||
String getErrorMsg(); | ||
} |
35 changes: 35 additions & 0 deletions
35
...bot-chat-server/src/main/java/com/ning/codebot/common/common/exception/HttpErrorEnum.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,35 @@ | ||
package com.ning.codebot.common.common.exception; | ||
|
||
import cn.hutool.http.ContentType; | ||
import cn.hutool.json.JSONUtil; | ||
import com.google.common.base.Charsets; | ||
import com.ning.codebot.common.domain.vo.response.ApiResult; | ||
import lombok.AllArgsConstructor; | ||
|
||
import javax.servlet.http.HttpServletResponse; | ||
import java.io.IOException; | ||
|
||
@AllArgsConstructor | ||
public enum HttpErrorEnum implements ErrorEnum{ | ||
ACCESS_DENIED(401, "token is invalid, please login"), | ||
; | ||
private Integer httpCode; | ||
private String msg; | ||
|
||
@Override | ||
public Integer getErrorCode() { | ||
return httpCode; | ||
} | ||
|
||
@Override | ||
public String getErrorMsg() { | ||
return msg; | ||
} | ||
|
||
public void sendHttpError(HttpServletResponse response) throws IOException { | ||
response.setStatus(this.getErrorCode()); | ||
ApiResult responseData = ApiResult.fail(this); | ||
response.setContentType(ContentType.JSON.toString(Charsets.UTF_8)); | ||
response.getWriter().write(JSONUtil.toJsonStr(responseData)); | ||
} | ||
} |
61 changes: 61 additions & 0 deletions
61
...hat-server/src/main/java/com/ning/codebot/common/common/interceptor/TokenInterceptor.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
package com.ning.codebot.common.common.interceptor; | ||
|
||
import com.ning.codebot.common.common.exception.HttpErrorEnum; | ||
import com.ning.codebot.common.user.service.LoginService; | ||
import lombok.extern.slf4j.Slf4j; | ||
import org.jboss.logging.MDC; | ||
import org.springframework.beans.factory.annotation.Autowired; | ||
import org.springframework.core.annotation.Order; | ||
import org.springframework.stereotype.Component; | ||
import org.springframework.web.servlet.HandlerInterceptor; | ||
|
||
import javax.servlet.http.HttpServletRequest; | ||
import javax.servlet.http.HttpServletResponse; | ||
import java.util.Objects; | ||
import java.util.Optional; | ||
|
||
@Order(-2) | ||
@Slf4j | ||
@Component | ||
public class TokenInterceptor implements HandlerInterceptor { | ||
public static final String AUTHORIZATION_HEADER = "Authorization"; | ||
public static final String AUTHORIZATION_SCHEMA = "Bearer "; | ||
public static final String ATTRIBUTE_UID = "uid"; | ||
|
||
@Autowired | ||
private LoginService loginService; | ||
|
||
|
||
@Override | ||
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { | ||
//get login user token | ||
String token = getToken(request); | ||
Long validUid = loginService.getValidUid(token); | ||
if (Objects.nonNull(validUid)) { | ||
request.setAttribute(ATTRIBUTE_UID, validUid); | ||
} else { | ||
boolean isPublicURI = isPublicURI(request.getRequestURI()); | ||
if (!isPublicURI) { | ||
HttpErrorEnum.ACCESS_DENIED.sendHttpError(response); | ||
return false; | ||
} | ||
} | ||
return true; | ||
} | ||
|
||
/** | ||
* Check whether it is public resources | ||
* @param requestURI | ||
*/ | ||
private boolean isPublicURI(String requestURI) { | ||
//TODO: add check logic | ||
return false; | ||
} | ||
private String getToken(HttpServletRequest request) { | ||
String header = request.getHeader(AUTHORIZATION_HEADER); | ||
return Optional.ofNullable(header) | ||
.filter(h -> h.startsWith(AUTHORIZATION_SCHEMA)) | ||
.map(h -> h.substring(AUTHORIZATION_SCHEMA.length())) | ||
.orElse(null); | ||
} | ||
} |
55 changes: 55 additions & 0 deletions
55
...ode-bot-chat-server/src/main/java/com/ning/codebot/common/common/service/LockService.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,55 @@ | ||
package com.ning.codebot.common.common.service; | ||
|
||
import lombok.extern.slf4j.Slf4j; | ||
import org.redisson.api.RLock; | ||
import org.redisson.api.RedissonClient; | ||
import org.springframework.beans.factory.annotation.Autowired; | ||
import org.springframework.stereotype.Service; | ||
import lombok.SneakyThrows; | ||
|
||
import java.util.concurrent.TimeUnit; | ||
import java.util.function.Supplier; | ||
|
||
@Service | ||
@Slf4j | ||
public class LockService { | ||
|
||
@Autowired | ||
private RedissonClient redissonClient; | ||
|
||
public <T> T executeWithLockThrows(String key, int waitTime, TimeUnit unit, SupplierThrow<T> supplier) throws Throwable { | ||
RLock lock = redissonClient.getLock(key); | ||
boolean lockSuccess = lock.tryLock(waitTime, unit); | ||
if (!lockSuccess) { | ||
//TODO: add new exception | ||
throw new Exception(); | ||
} | ||
try { | ||
return supplier.get(); | ||
} finally { | ||
if (lock.isLocked() && lock.isHeldByCurrentThread()) { | ||
lock.unlock(); | ||
} | ||
} | ||
} | ||
|
||
@SneakyThrows | ||
public <T> T executeWithLock(String key, int waitTime, TimeUnit unit, Supplier<T> supplier) { | ||
return executeWithLockThrows(key, waitTime, unit, supplier::get); | ||
} | ||
|
||
public <T> T executeWithLock(String key, Supplier<T> supplier) { | ||
return executeWithLock(key, -1, TimeUnit.MILLISECONDS, supplier); | ||
} | ||
|
||
@FunctionalInterface | ||
public interface SupplierThrow<T> { | ||
|
||
/** | ||
* Gets a result. | ||
* | ||
* @return a result | ||
*/ | ||
T get() throws Throwable; | ||
} | ||
} |
30 changes: 30 additions & 0 deletions
30
...ot/code-bot-chat-server/src/main/java/com/ning/codebot/common/common/utils/SpElUtils.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
package com.ning.codebot.common.common.utils; | ||
|
||
import org.springframework.core.DefaultParameterNameDiscoverer; | ||
import org.springframework.expression.EvaluationContext; | ||
import org.springframework.expression.Expression; | ||
import org.springframework.expression.ExpressionParser; | ||
import org.springframework.expression.spel.standard.SpelExpressionParser; | ||
import org.springframework.expression.spel.support.StandardEvaluationContext; | ||
|
||
import java.lang.reflect.Method; | ||
import java.util.Optional; | ||
|
||
public class SpElUtils { | ||
private static final ExpressionParser parser = new SpelExpressionParser(); | ||
private static final DefaultParameterNameDiscoverer parameterNameDiscoverer = new DefaultParameterNameDiscoverer(); | ||
|
||
public static String parseSpEl(Method method, Object[] args, String spEl) { | ||
String[] params = Optional.ofNullable(parameterNameDiscoverer.getParameterNames(method)).orElse(new String[]{});//解析参数名 | ||
EvaluationContext context = new StandardEvaluationContext(); | ||
for (int i = 0; i < params.length; i++) { | ||
context.setVariable(params[i], args[i]); | ||
} | ||
Expression expression = parser.parseExpression(spEl); | ||
return expression.getValue(context, String.class); | ||
} | ||
|
||
public static String getMethodKey(Method method) { | ||
return method.getDeclaringClass() + "#" + method.getName(); | ||
} | ||
} |
51 changes: 51 additions & 0 deletions
51
...e-bot-chat-server/src/main/java/com/ning/codebot/common/domain/vo/response/ApiResult.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
package com.ning.codebot.common.domain.vo.response; | ||
|
||
|
||
import com.ning.codebot.common.common.exception.ErrorEnum; | ||
import lombok.Data; | ||
|
||
@Data | ||
public class ApiResult<T> { | ||
|
||
private Boolean success; | ||
|
||
private Integer errCode; | ||
|
||
private String errMsg; | ||
|
||
private T data; | ||
|
||
public static <T> ApiResult<T> success() { | ||
ApiResult<T> result = new ApiResult<T>(); | ||
result.setData(null); | ||
result.setSuccess(Boolean.TRUE); | ||
return result; | ||
} | ||
|
||
public static <T> ApiResult<T> success(T data) { | ||
ApiResult<T> result = new ApiResult<T>(); | ||
result.setData(data); | ||
result.setSuccess(Boolean.TRUE); | ||
return result; | ||
} | ||
|
||
public static <T> ApiResult<T> fail(Integer code, String msg) { | ||
ApiResult<T> result = new ApiResult<T>(); | ||
result.setSuccess(Boolean.FALSE); | ||
result.setErrCode(code); | ||
result.setErrMsg(msg); | ||
return result; | ||
} | ||
|
||
public static <T> ApiResult<T> fail(ErrorEnum errorEnum) { | ||
ApiResult<T> result = new ApiResult<T>(); | ||
result.setSuccess(Boolean.FALSE); | ||
result.setErrCode(errorEnum.getErrorCode()); | ||
result.setErrMsg(errorEnum.getErrorMsg()); | ||
return result; | ||
} | ||
|
||
public boolean isSuccess() { | ||
return this.success; | ||
} | ||
} |
19 changes: 19 additions & 0 deletions
19
...at-server/src/main/java/com/ning/codebot/common/repository/controller/RepoController.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
package com.ning.codebot.common.repository.controller; | ||
|
||
import com.ning.codebot.common.common.annotation.RedissonLock; | ||
import com.ning.codebot.common.domain.vo.response.ApiResult; | ||
import org.springframework.stereotype.Controller; | ||
import org.springframework.web.bind.annotation.PostMapping; | ||
import org.springframework.web.bind.annotation.RequestBody; | ||
import org.springframework.web.bind.annotation.RequestMapping; | ||
|
||
@Controller | ||
@RequestMapping("codebot/reporsitory") | ||
public class RepoController { | ||
@PostMapping("/subscribe") | ||
@RedissonLock(key = "#subscribe") | ||
public ApiResult<Void> subscribe(@RequestBody String author, @RequestBody String repoName){ | ||
//TODO: finish the check logic to avoid multiple times download | ||
return new ApiResult<>(); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -7,7 +7,7 @@ | |
|
||
|
||
@Controller | ||
@RequestMapping("/user") | ||
@RequestMapping("codebot/user") | ||
public class UserController { | ||
|
||
} | ||
|