java 秒杀逻辑的实现,荐 Java秒杀系统方案优化 高性能高并发实战,学习手记(三)...

大家好,我是方圆

我们来实现一下分布式Session

1. 实现分布式Session

1.1 原理图解

ef90c6837d5cc7b4f4a454ea2bcf2ee0.png

作用:用Redis存储Session值,在Redis中通过token值来获取用户信息

1.2 每次登陆,将Session的过期时间进行修正

怎么说呢?我们的Session值固定过期时间为30min,要在每次登陆的时候,以当前时间继续顺延30分钟

我们的解决方法就是,每次登陆时,重新再添加一次Cookie,则能够完成时间延长

以下是封装addCookie()的方法

private void addCookie(HttpServletResponse response, MiaoShaUser user, String token) {

//首次登陆的时候,需要将Cookie存入Redis

redisService.set(MiaoShaUserKey.getTokenPrefix,token,user);

Cookie cookie = new Cookie(COOKIE_NAME_TOKEN, token);

cookie.setMaxAge(MiaoShaUserKey.getTokenPrefix.expireSeconds());

//设置为根目录,则可以在整个应用范围内使用cookie

cookie.setPath("/");

response.addCookie(cookie);

}

2. 解决注解获取参数造成的代码冗余

我们看一下,如下代码

@RequestMapping("/to_list")

public String toList(Model model,

@CookieValue(value = MiaoShaUserService.COOKIE_NAME_TOKEN,required = false) String cookieToken,

@RequestParam(value = MiaoShaUserService.COOKIE_NAME_TOKEN,required = false) String paramToken,

){

if(StringUtils.isEmpty(cookieToken) && StringUtils.isEmpty(paramToken)){

return "login";

}

String token = StringUtils.isEmpty(paramToken) ? cookieToken : paramToken;

MiaoShaUser user = miaoShaUserService.getByToken(response,token);

model.addAttribute("user",user);

return "goods_list";

}

@CookieValue:这个注解能够根据参数value在Cookie中获取值

@RequestParam:该注解让我们在Request中能获取参数,解决的主要是,移动手机端不使用Cookie存值的问题

我们在如上代码中,可以发现,注解标记获取参数,使得代码很厚重,若我们每次想从Cookie中获取token值时,都需要复现如上代码,所以我们要把它剖离出来

2.1 WebMvcConfigurerAdapter

在这个项目中,我们采用的是继承WebMvcConfigurerAdapter,重写其中addArgumentResolvers()方法,该方法实现的是参数解析的功能

@Configuration

public class WebConfig extends WebMvcConfigurerAdapter{

@Autowired

UserArgumentResolver userArgumentResolver;

@Override

public void addArgumentResolvers(List argumentResolvers) {

super.addArgumentResolvers(argumentResolvers);

argumentResolvers.add(userArgumentResolver);

}

}

2.1.1 该方法在Spring5.0之后就过时了

现用方式

实现WebMvcConfigurer

@Configuration

public class WebMvcConfg implements WebMvcConfigurer {

//TODO

}

继承WebMVCConfigurationSupport

@Configuration

public class WebMvcConfg extends WebMvcConfigurationSupport {

//TODO

}

2.2 在argumentResolvers中添加我们的参数解析逻辑

首先,我们应该搞清楚,我们想要的参数是什么?回看代码冗余的问题,最终我们想获取的是MiaoShaUser,这下我们进行代码的编写

@Service

public class UserArgumentResolver implements HandlerMethodArgumentResolver {

@Autowired

MiaoShaUserService miaoShaUserService;

@Override

public boolean supportsParameter(MethodParameter methodParameter) {

//这个方法判断参数类型是否支持

Class> clazz = methodParameter.getParameterType();

return clazz == MiaoShaUser.class;

}

@Override

public Object resolveArgument(MethodParameter methodParameter, ModelAndViewContainer modelAndViewContainer,

NativeWebRequest nativeWebRequest, WebDataBinderFactory webDataBinderFactory) throws Exception {

//这个方法实现对参数的处理

HttpServletRequest request = nativeWebRequest.getNativeRequest(HttpServletRequest.class);

HttpServletResponse response = nativeWebRequest.getNativeResponse(HttpServletResponse.class);

String paramToken = request.getParameter(miaoShaUserService.COOKIE_NAME_TOKEN);

String cookieToken = getCookieValue(request, miaoShaUserService.COOKIE_NAME_TOKEN);

if(StringUtils.isEmpty(paramToken) && StringUtils.isEmpty(cookieToken)){

return null;

}

String token = StringUtils.isEmpty(paramToken) ? cookieToken : paramToken;

return miaoShaUserService.getByToken(response,token);

}

private String getCookieValue(HttpServletRequest request,String cookieName){

Cookie[] cookies = request.getCookies();

for(Cookie cookie : cookies){

if(cookie.getName().equals(cookieName)){

return cookie.getValue();

}

}

return null;

}

}

实现HandlerMethodArgumentResolver接口,必须重写其中的两个方法,supportsParameter()和resolveArgument()

前者是对我们要进行解析的参数类型进行判断,符合才执行后者

后者是我们对参数的处理逻辑,两种情况,一是从request中获取token值,二是从cookie中拿取token值,根据token值来获取到对应的user

以上就将我们需要的参数的处理逻辑实现了,在Mvc配置中,用argumentResolvers.add(userArgumentResolver)方法进行添加即可,这样我们再想获取user的时候就简单多了,如下

2.3 如此清爽的代码

@RequestMapping("/to_list")

public String toList(Model model,MiaoShaUser user){

model.addAttribute("user",user);

return "goods_list";

}

省去了@CookieValue和@RequestParam注解的冗余,而且我们对user的获取也方便多了

理解的原理之后,其实也很简单!

本文地址:https://blog.csdn.net/qq_46225886/article/details/107256719

希望与广大网友互动??

点此进行留言吧!