【ASP.NET】ASP.NET中权限验证使用OnAuthorization实现

在项目开发中,通常我们都会涉及到用户登录才能访问的网页,比如购物网站,我们浏览商品,添加购物车(以前开发的时候在这里就需要登录用户,但是现在有了缓存的实现,这里可以将商品加入缓存,等到结账的时候再登录),选择结账的时候需要登录,那么这时候我们需要跳转到登录页面登录,登录之后还可以回到记录下来的原始的页面,那么这之后我们有好几种方法可以实现这种效果,下面笔者举例两种:

第一种:登录模块不管怎么样都是统一的,就是在每个需要登录的方法里面判断用户是否登录,如果没有登录,则跳转登录,这种的缺点是工作量大,代码冗余。

第二种:使用MVC的特性,定义类继承IAuthorizationFilter,重写OnAuthorization方法即可实现。此方法工作量少,代码不冗余,如果需要登录我们只需要给Controller或者Action给上标签即可。

上面列举了权限认证的两种形式,在实际开发中使用OnAuthorization和特性相结合的情况比较多,在任何能够使用特性的判断中都可以按照下面的思路来实现,例如(登录判断,权限判断,请求判断,去除空格,读取返回路径)等等。

接下来是笔者使用OnAuthorization的一个案例:

BaseController.cs

namespace MvcApplication1.Controllers
{
    public class BaseController : Controller
    {
        protected override void OnAuthorization(AuthorizationContext context)
        {
            //解析控制器的名称
            string ControllerName = context.ActionDescriptor.ControllerDescriptor.ControllerName;
            if (ControllerName.ToLower() == "Manager".ToLower())//这里只对Manager的控制器进行权限验证
            {
                var b = context.HttpContext.Request.Browser;//浏览器判断 ie8 居然是7.0
                if (b.Browser == "IE" && float.Parse(b.Version) < 7)
                {
                    context.Result = Content("ie浏览器就只支持ie8+", "text/json");
                    return;
                }
                //解析出对应的方法
                var Method = context.Controller.GetType().GetMethods().Where(c => c.Name.ToLower() == context.ActionDescriptor.ActionName.ToLower()).FirstOrDefault();
                if (Method == null)
                {
                    context.Result = Content("权限不够", "text/json");
                    return;
                }
                //解析出方法上面对应的特性
                AccessAttribute acc = Method.GetCustomAttributes(typeof(AccessAttribute), true).FirstOrDefault() as AccessAttribute;
                if (acc != null)
                {
                    if (acc.IsAccess == AccessEnum.Login)//需要登录权限
                    {
                        if (!IsLogin())
                        {
                            context.HttpContext.Response.Redirect("~/Manager/Login");//如果没有登录,就跳转到登录页面
                            return;
                        }
                    }
                    else if (acc.IsAccess == AccessEnum.Access)//需要其他权限
                    {
                        if (!IsAccess(context))
                        {
                            context.Result = Content("权限不够", "text/json");
                            return;
                        }
                    }
                }
            }
            base.OnAuthorization(context);
        }
        /// <summary>
        /// 检查是否登录
        /// </summary>
        /// <returns>一个bool类型的数据,表示用户是否登录</returns>
        public bool IsLogin()
        {
            String userName = (String)System.Web.HttpContext.Current.Session["UserName"];
            String Password = (String)System.Web.HttpContext.Current.Session["Password"];
            if (System.Web.HttpContext.Current.Session["UserName"] != null)
            {
                if ("abc".Equals(userName) && "123".Equals(Password)) {
                    return true;
                }
            }
            else
            {
                //检查Cookies
                 HttpCookie cookie_UserName=System.Web.HttpContext.Current.Request.Cookies.Get("UserName");
                 HttpCookie cookie_Password = System.Web.HttpContext.Current.Request.Cookies.Get("Password");
                //检查用户名和密码
                 if (cookie_UserName == null || cookie_Password == null)
                 {
                     return false;
                 }
                 else {
                     String user= cookie_UserName.Value;
                     String pass = cookie_Password.Value;
                     //在数据库中检查
                     if ("abc".Equals(user) && "123".Equals(pass)) {
                         return true;
                     }
                 }
            }
            return false;
        }
        /// <summary>
        /// 权限检查
        /// </summary>
        /// <param name="context"></param>
        /// <returns>一个bool的数据,表示用户是否拥有其他权限</returns>
        public bool IsAccess(AuthorizationContext context)
        {
            bool isAccess = false;

            var controller = context.RouteData.Values.Keys.First(p => p == "controller");
            var action = context.RouteData.Values.Keys.First(p => p == "action");
            var url = "/" + context.RouteData.Values[controller] + "/" + context.RouteData.Values[action];

            //根据controller和action 可以判断权限了
            //isAccess = true;

            return isAccess;
        }
    }
}

BaseController.cs

这里的BaseController类继承了Controller,并且重写了其中了OnAuthorization方法,在OnAuthorization方法中,首先解析出用户请求的Controller名称,然后判断是否需要验证这个Controller,案例中验证的是名为Manager的Controller,得到了对应的Controller后,接下来解析用户请求的具体是什么方法,再利用反射找出方法有什么特性,根据特性进行权限验证。

ManagerController.cs

namespace MvcApplication1.Controllers
{
    public class ManagerController : BaseController
    {

        [Access(IsAccess = AccessEnum.Login)]
        public ActionResult Index()
        {
            return View("index");
        }

        [Access(IsAccess = AccessEnum.Anonymous)]
        public ActionResult ToLogin(){
            String user = Request["UserName"];
            String password = Request["Password"];
            if ("abc".Equals(user) && "123".Equals(password)) {
                Session.Add("UserName", "abc");
                Session.Add("Password", "123");
                return Index();
            }
            return View("Error");
        }

        [Access(IsAccess = AccessEnum.Anonymous)]
        public ActionResult Login()
        {
            return View();
        }
    }
}

ManagerController.cs

AccessAttribute.cs

namespace MvcApplication1.Models.Attribute
{
    /// <summary>
    /// <para>创建自定义权限认证特性</para>
    /// <para>该特性应用的范围可以为类、构造方法、字段、方法、属性</para>
    /// </summary>
    [AttributeUsage(AttributeTargets.Class |
     AttributeTargets.Constructor |
     AttributeTargets.Field |
     AttributeTargets.Method |
     AttributeTargets.Property,
     AllowMultiple = true)]
    public class AccessAttribute : System.Attribute
    {
        public AccessEnum IsAccess { set; get; }
    }

    /// <summary>
    /// 权限认证级别
    /// </summary>
    public enum AccessEnum
    {
        /// <summary>
        /// 权限认证
        /// </summary>
        Access,
        /// <summary>
        /// 只需要登录
        /// </summary>
        Login,
        /// <summary>
        /// 不需要登录
        /// </summary>
        Anonymous
    }
}

AccessAttribute.cs

Error.cshtml

@{
    ViewBag.Title = "error";
    Layout = "~/Views/Shared/_Layout.cshtml";
}

<h2>账号密码错误</h2>

Error.cshtml

Index.cshtml

@{
    ViewBag.Title = "Index";
    Layout = "~/Views/Shared/_Layout.cshtml";
}

<h2>登录成功,恭喜你登录成功</h2>

Index.cshtml

Login.cshtml

@{
    ViewBag.Title = "登录";
    Layout = "~/Views/Shared/_Layout.cshtml";
}
<div>
    <form action="tologin" method="post">
        <input type="text" name="UserName"/><br />
        <input type="password" name="Password" /><br/>
         <input type="submit" value="提交" />
    </form>
</div>

Login.cshtml

时间: 2024-08-02 04:49:28

【ASP.NET】ASP.NET中权限验证使用OnAuthorization实现的相关文章

[转]ASP.NET MVC过滤器中权限过滤器ValidateAntiForgeryToken的用法(Post-Only)

用途:防止CSRF(跨网站请求伪造). 用法:在View->Form表单中:<%:Html.AntiForgeryToken()%> 在Controller->Action动作上:[ValidateAntiForgeryToken] 原理: 1.<%:Html.AntiForgeryToken()%>这个方法会生成一个隐藏域:<inputname="__RequestVerificationToken" type="hidden&qu

ASP.NET MVC过滤器中权限过滤器ValidateAntiForgeryToken的用法(Post-Only)

用途:防止CSRF(跨网站请求伪造). 用法:在View->Form表单中:<%:Html.AntiForgeryToken()%> 在Controller->Action动作上:[ValidateAntiForgeryToken] 原理: 1.<%:Html.AntiForgeryToken()%>这个方法会生成一个隐藏域:<inputname="__RequestVerificationToken" type="hidden&qu

2_MVC+EF+Autofac(dbfirst)轻型项目框架_用户权限验证

前言 接上面两篇 0_MVC+EF+Autofac(dbfirst)轻型项目框架_基本框架 与 1_MVC+EF+Autofac(dbfirst)轻型项目框架_core层(以登陆为例) .在第一篇中介绍了此架构的基本分层,在第二篇中,以登陆功能为例,介绍了项目的代码结构.在本篇中将通过过滤器实现用户权限验证功能. 同样,文中有问题的地方欢迎批评指正!谢谢! 开发背景  在一个常规系统中权限验证是不可缺的,在较简单的系统中,用户只会被简单归为登陆用户和游客,而在较为复杂的系统中,除了判断用户是否登

ASP.NET MVC:窗体身份验证及角色权限管理示例

ASP.NET MVC 建立 ASP.NET 基础之上,很多 ASP.NET 的特性(如窗体身份验证.成员资格)在 MVC 中可以直接使用.本文旨在提供可参考的代码,不会涉及这方面太多理论的知识. 本文仅使用 ASP.NET 的窗体身份验证,不会使用它的 成员资格(Membership) 和 角色管理 (RoleManager),原因有二:一是不灵活,二是和 MVC 关系不太. 一.示例项目 User.cs 是模型文件,其中包含了 User 类: public class User { publ

Asp.net Core, 基于 claims 实现权限验证 - 引导篇

什么是Claims? 这个直接阅读其他大神些的文章吧,解释得更好. 相关文章阅读: http://www.cnblogs.com/JustRun1983/p/4708176.html http://www.cnblogs.com/jesse2013/p/aspnet-identity-claims-based-authentication-and-owin.html http://www.cnblogs.com/savorboard/p/aspnetcore-identity.html clai

ASP.NET通用权限验证组件实现

沙发(SF)通用权限验证组件 开篇 本篇介绍通用权限验证的实现代码思路,总共分为导入参数.解析XML.根据XML配置进行处理.返回结果. 代码架构图 1.   类介绍 1.SFWebPermission:实现IHttpModule接口,权限验证入口: 2.SFConfig:导入XML配置类: 3.SFPermission:解析XML配置进行权限验证: 4.SFAccessOper:数据库操作类: 5.SFPermissionSQL:XML节点实体类: 6.SFParameter:XML节点实体类

Asp.net Mvc 身份验证、异常处理、权限验证(拦截器)实现代码

本问主要介绍asp.net的身份验证机制及asp.net MVC拦截器在项目中的运用.现在让我们来模拟一个简单的流程:用户登录>权限验证>异常处理 1.用户登录 验证用户是否登录成功步骤直接忽略,用户登录成功后怎么保存当前用户登录信息(session,cookie),本文介绍的是身份验证(其实就是基于cookie)的,下面看看代码. 引入命名空间 using System.Web.Security; Users ModelUser = new Users() { ID = 10000, Nam

ASP.NET MVC View 和 Web API 的基本权限验证

ASP.NET MVC 5.0已经发布一段时间了,适应了一段时间,准备把原来的MVC项目重构了一遍,先把基本权限验证这块记录一下. 环境:Windows 7 Professional SP1 + Microsoft Visual Studio 2013(MVC 5 + Web API 2) 修改Web.config,增加Forms验证模式,在system.web节点中增加以下配置: <authentication mode="Forms"> <forms loginU

ABP(现代ASP.NET样板开发框架)系列之18、ABP应用层——权限验证

点这里进入ABP系列文章总目录 ABP(现代ASP.NET样板开发框架)系列之18.ABP应用层——权限验证 ABP是“ASP.NET Boilerplate Project (ASP.NET样板项目)”的简称. ABP的官方网站:http://www.aspnetboilerplate.com ABP在Github上的开源项目:https://github.com/aspnetboilerplate 几乎所有的企业级应用程序都会有不同级别的权限验证.权限验证是用于检查用户是否允许某些指定操作.