当前位置:网站首页>Two controller layer interface authentication methods
Two controller layer interface authentication methods
2022-06-29 17:45:00 【llp1110】
Two kinds of Controller Layer interface authentication mode
Recently, I was working on an instant messaging service , It is required to authenticate the input parameters of each interface , Here I have sorted out two ways :1. Authentication based on annotations and interceptors 2. Based on annotations and AOP authentication
What I am using here is aop The way , The interceptor here only completes the pseudo code as a record .
1. Authentication based on annotations and interceptors
Interceptor mode mainly needs to be solved requestBody The problem of repeated acquisition
1. First, we need to define an authentication identifier annotation
/** * Authentication mark annotation */
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
@Documented
public @interface Authorization {
}
2. rewrite HttpServletRequestWrapper
Through custom HttpServletRequestWrapper Back up the dirty data , Customize HttpServletRequestWrapper Call the parent class request.getInputStream() Read all the data and save it in one byte In array , When the stream data is retrieved again , Self defined HttpServletRequestWrapper Will use byte Array regenerates a new stream . The backed up stream data remains in byte Array .
public class RepeatableReadRequestWrapper extends HttpServletRequestWrapper {
private final byte[] bytes;
public RepeatableReadRequestWrapper(HttpServletRequest request, HttpServletResponse response) throws IOException {
super(request);
request.setCharacterEncoding("UTF-8");
response.setCharacterEncoding("UTF-8");
bytes = request.getReader().readLine().getBytes();
}
@Override
public BufferedReader getReader() throws IOException {
return new BufferedReader(new InputStreamReader(getInputStream()));
}
@Override
public ServletInputStream getInputStream() throws IOException {
ByteArrayInputStream bais = new ByteArrayInputStream(bytes);
return new ServletInputStream() {
@Override
public boolean isFinished() {
return false;
}
@Override
public boolean isReady() {
return false;
}
@Override
public void setReadListener(ReadListener readListener) {
}
@Override
public int read() throws IOException {
return bais.read();
}
@Override
public int available() throws IOException {
return bytes.length;
}
};
}
}
3. Define an interceptor
@Component
public class RepeatSubmitInterceptor implements HandlerInterceptor {
@Autowired
RedisCache redisCache;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
if (handler instanceof HandlerMethod) {
HandlerMethod handlerMethod = (HandlerMethod) handler;
Method method = handlerMethod.getMethod();
if (method.isAnnotationPresent(Authorization.class)) {
// Request parameter string
String nowParams = "";
if (request instanceof RepeatableReadRequestWrapper) {
try {
nowParams = ((RepeatableReadRequestWrapper) request).getReader().readLine();
System.out.println("nowParams: " + nowParams);
//TODO Carry out authentication processing
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
return true;
}
}
4. Define a filter
public class RepeatableRequestFilter implements Filter {
@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) servletRequest;
if (StringUtils.startsWithIgnoreCase(request.getContentType(), "application/json")) {
RepeatableReadRequestWrapper requestWrapper = new RepeatableReadRequestWrapper(request, (HttpServletResponse) servletResponse);
filterChain.doFilter(requestWrapper,servletResponse);
return;
}
filterChain.doFilter(servletRequest, servletResponse);
}
}
5. Configuration class
@Configuration
public class WebConfig implements WebMvcConfigurer {
@Autowired
RepeatSubmitInterceptor repeatSubmitInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(repeatSubmitInterceptor).addPathPatterns("/**");
}
@Bean
FilterRegistrationBean<RepeatableRequestFilter> repeatableRequestFilterFilterRegistrationBean() {
FilterRegistrationBean<RepeatableRequestFilter> bean = new FilterRegistrationBean<>();
bean.setFilter(new RepeatableRequestFilter());
bean.addUrlPatterns("/*");
return bean;
}
}
6. Test class
@RestController
public class HelloController {
@Authorization
@PostMapping("/test")
public String authorization(@RequestBody User user) {
System.out.println(user);
return "succes";
}
}
test result

2. Based on annotations and AOP authentication
1. Define an authentication identifier annotation
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Authorization {
}
2. Definition AOP class
@Aspect
@Order(value = Integer.MAX_VALUE-1)
@Component
public class AuthorizationAspect {
private static Logger log = LoggerFactory.getLogger(AuthorizationAspect.class);
@Autowired
private AuthConfigService authConfigService;
@Before(value = "@annotation(com.llp.api.annotation.Authorization))")
public void authorization(JoinPoint joinPoint) throws Exception {
// Get request parameters
Object[] args = joinPoint.getArgs();
Signature signature = joinPoint.getSignature();
// Get method signature
MethodSignature methodSignature = (MethodSignature) signature;
// obtain Method object
Method method = methodSignature.getMethod();
// Determine whether the method is customized by us @Authorization To modify
if (method.isAnnotationPresent(Authorization.class)) {
// Traversal request parameters
for (Object arg : args) {
// Judge whether the request parameter belongs to BaseConfigRequest type
if (arg instanceof BaseConfigRequest) {
// Belong to , Then the request parameters are forcibly converted
BaseConfigRequest baseConfigRequest = (BaseConfigRequest) arg;
log.info(" Authentication base class -baseConfigRequest:{}", ObjectUtils.getDisplayString(baseConfigRequest));
// Get Authentication id
String appId = baseConfigRequest.getAppId();
// Get ciphertext
String cipherText = baseConfigRequest.getCipherText();
// Through authentication id Get the authentication configuration object
EduAuthConfig authConfig = authConfigService.getAuthConfig(appId);
log.info("authConfig:{}", ObjectUtils.getDisplayString(authConfig));
// If authentication id If it is not found, an exception will be thrown. Authentication fails
Assert.notNull(authConfig, " No appId Corresponding authentication configuration information , Authentication failure ");
// According to the ciphertext 、 Decrypt the private key to obtain authentication key
String appKey = RSAUtil.decrypt(cipherText, authConfig.getPrivateKey());
log.info(" Decrypt and get appKey:{}", appKey);
// If authentication key Null or decrypted authentication key And configured authentication key If not, an exception will be thrown. Authentication fails
if (appKey == null || !appKey.equals(authConfig.getAppKey())) {
throw new BaseException(" Authentication parameter error , Authentication failure ");
}
// The authentication ends the cycle
return;
}
}
}
}
}
3. Define an authentication base class
@Data
@ApiModel(value = " Authentication base class ")
public class BaseConfigRequest<T> implements Serializable {
private static final long serialVersionUID = 1L;
@ApiModelProperty(value = " authentication Id")
@NotBlank(message = " authentication id Can't be empty ")
private String appId;
@ApiModelProperty(value = " Ciphertext ")
@NotBlank(message = " Ciphertext cannot be empty ")
private String cipherText;
@ApiModelProperty(value = " Any other data ",notes = " Use when authenticating @Valid Comment on check ")
@Valid
private T data;
}
4. The test method
@Authorization
@ApiOperation(value = " receive messages ")
@RequestMapping(value = "/receiveMsg", method = RequestMethod.POST)
public BaseResult<String> receiveMsg(@Validated @RequestBody BaseConfigRequest<MessageSendRequest> request) {
return BaseResult.judgeOperate(messageService.receiveMsg(request));
}
边栏推荐
- SRM供应商协同管理系统功能介绍
- Set double click to run the jar file
- Maidong Internet won the bid of Dajia Insurance Group
- R语言使用glm函数构建泊松对数线性回归模型处理三维列联表数据构建饱和模型、使用exp函数和coef函数获取模型所有变量的事件密度比(Incidence Density Ratio,IDR)并解读
- selenium 文件上传方法
- 基于gis三维可视化的智慧城市行业运用
- selenium 组合键操作
- Basic operations such as MySQL startup under Windows platform
- mysql在linux中2003错误如何解决
- Uploading files using AutoIT
猜你喜欢

0 basic self-study STM32 (wildfire) - register lit LED

Selenium upload file

布隆过滤器:

自动收售报机

面试中问最常问的海量数据处理你拿捏了没?
![[webdriver] upload files using AutoIT](/img/69/8c27626d515976b47f1df4831d09c8.png)
[webdriver] upload files using AutoIT

最受欢迎的30款开源软件

0 basic self-study STM32 (wildfire) -- use register to light LED -- Explanation of GPIO function block diagram

Openfeign use step polling strategy and weight log4j configuration of openfeign interceptor
![[the sixth operation of modern signal processing]](/img/49/7844a00077e56fd4d73e3ba515f8a6.png)
[the sixth operation of modern signal processing]
随机推荐
mac安装php7.2
基于STM32F103ZET6库函数独立看门狗(IWDG)实验
[webdriver] upload files using AutoIT
VB. Net read / write NFC ntag tag source code
sequential detector
reflex
Selenium upload file
Does MySQL support foreign keys
Web Scraping with Beautiful Soup for Data Scientist
SSH协议学习笔记
阿里云不同账号新旧服务器镜像迁移数据迁移同步
2022 spring summer collection koreano essential reshapes the vitality of fashion
Selenium file upload method
Openfeign use step polling strategy and weight log4j configuration of openfeign interceptor
linux中mysql 1045错误如何解决
Tencent cloud released orbit, an automated delivery and operation and maintenance product, to promote enterprise applications to be fully cloud native
mysql视图能不能创建索引
Bottom level internal skill cultivation
一次采集JSON解析错误的修复
2022春夏系列 KOREANO ESSENTIAL重塑时装生命力