zoukankan      html  css  js  c++  java
  • Spring mvc通过访问者IP限制接口访问频率

    https://blog.csdn.net/qq_31384551/article/details/80955215

    我们有的时候系统里面有的用户接口为了控制访问频率,需要使用到,笔记走一波

    环境:

    spring

    spring mvc

    Guava:谷歌高并发工具,下面是maven

    <!--谷歌guava高并发处理工具-->
    <dependency>
    <groupId>com.google.guava</groupId>
    <artifactId>guava</artifactId>
    <version>18.0</version>
    </dependency>
    我们这次主要使用到的是Guava工具的LoadingCache 和 

    RateLimiter 即缓存和限流

     
    由于是在spring 环境中,所以就直接上Service代码了:


    /**
    * 接口访问限流service,此接口主要用于针对ip地址对于接口访问的限流控制
    */
    @Service
    public class LoadingCacheServiceImpl implements LoadingCacheService {
    LoadingCache<String, RateLimiter> ipRequestCaches = CacheBuilder.newBuilder()
    .maximumSize(200)// 设置缓存个数
    .expireAfterWrite(1, TimeUnit.DAYS)
    .build(new CacheLoader<String, RateLimiter>() {
    @Override
    public RateLimiter load(String s) throws Exception {
    return RateLimiter.create(0.2);// 新的IP初始化 (限流每秒0.1个令牌响应,即10s一个令牌)
    }
    });
    public RateLimiter getRateLimiter(String key) throws ExecutionException {
    return ipRequestCaches.get(key);
    }
    }
    控制器使用代码:

    @Controller
    @RequestMapping("/tool/upload/")
    public class FileUploadController{
    @Resource
    LoadingCacheService loadingCacheService;
    /**
    * ajax上传文件
    * @param file 文件对象
    * @return
    */
    @RequestMapping("ajaxUpload")
    @ResponseBody
    public AjaxRes ajaxUpload(@RequestParam("file") MultipartFile file, HttpServletRequest httpServletRequest){
    String ipAddr = IPUtil.getIpAddr(getRequest());
    try {
    RateLimiter limiter = loadingCacheService.getRateLimiter(ipAddr);
    if(limiter.tryAcquire()){
    //获得令牌(不限制访问)
    }else {
    //未获得令牌(限制访问)
    }
    } catch (ExecutionException e) {
    e.printStackTrace();
    }
    return res;
    }
    }
    注:主要就是把没一个用户IP的令牌桶RateLimiter给缓存起来,然后每次用户请求接口的时候就去拿一次令牌,那到令牌则不限制访问,没拿到则限制

    PS:第一次使用,哪里不对请指正,谢谢

    根据qq_35284533兄弟的提示,补充IPUtil工具类代码,这个工具类是用于获取IP地址的。

    package com.jufanshare.myblog.common.util;

    import javax.servlet.http.HttpServletRequest;

    /**
    * 获取客户端IP地址
    */
    public class IPUtil {

    /**
    * 客户端真实IP地址的方法一:
    */
    public static String getRemortIP(HttpServletRequest request) {
    if (request.getHeader("x-forwarded-for") == null) {
    return request.getRemoteAddr();
    }
    return request.getHeader("x-forwarded-for");
    }
    /**
    * 客户端真实IP地址的方法二:
    */
    public static String getIpAddr(HttpServletRequest request) {
    String ip="";
    if(request!=null){
    ip = request.getHeader("x-forwarded-for");
    if(ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
    ip = request.getHeader("Proxy-Client-IP");
    }
    if(ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
    ip = request.getHeader("WL-Proxy-Client-IP");
    }
    if(ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
    ip = request.getRemoteAddr();
    }
    }
    return ip;
    }
    }
     

     
    ————————————————
    版权声明:本文为CSDN博主「聚繁大BUG」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
    原文链接:https://blog.csdn.net/qq_31384551/article/details/80955215

  • 相关阅读:
    每日日报2020.12.1
    每日日报2020.11.30
    981. Time Based Key-Value Store
    1146. Snapshot Array
    565. Array Nesting
    79. Word Search
    43. Multiply Strings
    Largest value of the expression
    1014. Best Sightseeing Pair
    562. Longest Line of Consecutive One in Matrix
  • 原文地址:https://www.cnblogs.com/zhoading/p/12199780.html
Copyright © 2011-2022 走看看