LOGO OA教程 ERP教程 模切知识交流 PMS教程 CRM教程 开发文档 其他文档  
 
网站管理员

.net简单的限流过滤器

freeflydom
2024年6月13日 8:42 本文热度 772

API接口都是提供给第三方服务/客户端调用,所有请求地址以及请求参数都是暴露给用户的。

每次请求一个HTTP请求,用户都可以通过F12,或者抓包工具看到请求的URL链接,然后copy出来。这样是非常不安全的,有人可能会恶意的刷我们的接口,那这时该怎么办呢?

增加一个全局过滤器 获取客户端的IP  限制固定时间内的访问次数即可

第一步:创建全局过滤器 RateLimitFilter

public class RateLimitFilter : ActionFilterAttribute

    {

        private const int MaxRequests = 30; //1分钟访问最大频率

        private bool StartUp = true; //是否启用

        public override void OnActionExecuting(ActionExecutingContext context)

        {

            if (StartUp)

            {

                base.OnActionExecuting(context);

                string clientId = GetIP();

                if (GetCache(clientId) == null)

                {

                    SetCacheRelativeTime(clientId, 1, 60);

                }

                else

                {

                    var cs = int.Parse(GetCache(clientId).ToString());

                    SetCacheRelativeTime(clientId, cs += 1, 60);

                }

                //var x = int.Parse(GetCache(clientId).ToString());

                if (int.Parse(GetCache(clientId).ToString()) > MaxRequests)

                {

                    //返回值规范不统一

                    context.Result = new ContentResult { Content = "<script type='text/javascript'>alert('" + clientId + "  访问过于频繁,请稍等片刻!');</script><h1 style='text-align: center; color: red;'>" + clientId + "  访问过于频繁,请稍等片刻!<h1>" };


                    //返回值规范统一   前端有错误提示

                    //context.Result = new JsonResult()

                    //{

                    //    Data = new { Result = false, status = false, suc = false, message = "" + clientId + "  访问过于频繁,请稍等片刻!" },

                    //    JsonRequestBehavior = JsonRequestBehavior.AllowGet

                    //};

                }

            } 

        }



        /// <summary>

        /// 获取客户端IP地址

        /// </summary>

        /// <returns>若失败则返回回送地址</returns>

        public static string GetIP()

        {

            //如果客户端使用了代理服务器,则利用HTTP_X_FORWARDED_FOR找到客户端IP地址

            string userHostAddress = HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"];

            if (!string.IsNullOrEmpty(userHostAddress))

            {

                userHostAddress = HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"].ToString().Split(',')[0].Trim();

            }

            //否则直接读取REMOTE_ADDR获取客户端IP地址

            if (string.IsNullOrEmpty(userHostAddress))

            {

                userHostAddress = HttpContext.Current.Request.ServerVariables["REMOTE_ADDR"];

            }

            //前两者均失败,则利用Request.UserHostAddress属性获取IP地址,但此时无法确定该IP是客户端IP还是代理IP

            if (string.IsNullOrEmpty(userHostAddress))

            {

                userHostAddress = HttpContext.Current.Request.UserHostAddress;

            }

            //最后判断获取是否成功,并检查IP地址的格式(检查其格式非常重要)

            if (!string.IsNullOrEmpty(userHostAddress) && IsIP(userHostAddress))

            {

                return userHostAddress;

            }

            return "127.0.0.1";

        }


        /// <summary>

        /// 检查IP地址格式

        /// </summary>

        /// <param name="ip"></param>

        /// <returns></returns>

        public static bool IsIP(string ip)

        {

            return System.Text.RegularExpressions.Regex.IsMatch(ip, @"^((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?)$");

        }


        #region  设置相对过期时间Cache值(即:访问激活后不过期)

        /// <summary>        

        /// 设置相对过期时间Cache值(即:访问激活后不过期)

        /// </summary>        

        /// <param name="objectkey"></param>        

        /// <param name="objObject"></param>        

        /// <param name="timeSpan">超过多少时间不调用就失效,单位是秒</param>        


        public static void SetCacheRelativeTime(string objectkey, object objObject, int timeSpan)

        {

            System.Web.Caching.Cache objCache = HttpRuntime.Cache;

            objCache.Insert(objectkey, objObject, null, DateTime.MaxValue, TimeSpan.FromSeconds(timeSpan));

        }

        #endregion


        #region  获取当前应用程序指定CacheKey的Cache值

        /// <summary>

        /// 获取当前应用程序指定CacheKey的Cache值

        /// </summary>

        /// <param name="CacheKey"></param>

        /// <returns></returns>y

        public static object GetCache(string CacheKey)

        {

            try

            {

                System.Web.Caching.Cache objCache = HttpRuntime.Cache;

                Object value = objCache[CacheKey];

                if (value != null)

                {

                    return value;

                }

                else

                {

                    return null;

                }

            }

            catch (Exception)

            {

                return null;

            }


        }

        #endregion

    }

第二步:FilterConfig类并注册你的全局过滤器

public class FilterConfig

 {

        public static void RegisterGlobalFilters(GlobalFilterCollection filters)

        {

            filters.Add(new RateLimitFilter()); // 过滤器

        }

 }

第三步:Global.asax 文件中注册全局过滤器

protected void Application_Start()

{

            AreaRegistration.RegisterAllAreas();

            RouteConfig.RegisterRoutes(RouteTable.Routes);

            BundleConfig.RegisterBundles(BundleTable.Bundles);

            UnityConfig.RegisterComponents();


            // 注册全局过滤器

            FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);


}

原文链接https://www.cnblogs.com/zj19940610/p/18244414 作者:风中起舞 


该文章在 2024/6/13 8:42:45 编辑过
关键字查询
相关文章
正在查询...
点晴ERP是一款针对中小制造业的专业生产管理软件系统,系统成熟度和易用性得到了国内大量中小企业的青睐。
点晴PMS码头管理系统主要针对港口码头集装箱与散货日常运作、调度、堆场、车队、财务费用、相关报表等业务管理,结合码头的业务特点,围绕调度、堆场作业而开发的。集技术的先进性、管理的有效性于一体,是物流码头及其他港口类企业的高效ERP管理信息系统。
点晴WMS仓储管理系统提供了货物产品管理,销售管理,采购管理,仓储管理,仓库管理,保质期管理,货位管理,库位管理,生产管理,WMS管理系统,标签打印,条形码,二维码管理,批号管理软件。
点晴免费OA是一款软件和通用服务都免费,不限功能、不限时间、不限用户的免费OA协同办公管理系统。
Copyright 2010-2024 ClickSun All Rights Reserved