基于URL的权限管理方法

一、权限管理

1.1什么是权限管理

基本上涉及到用户参与的系统都要进行权限管理,权限管理属于系统安全的范畴,权限管理实现对用户访问系统的控制,按照安全规则或者安全策略控制用户可以访问而且只能访问自己被授权的资源。

权限管理包括用户身份认证和授权两部分,简称认证授权。对于需要访问控制的资源用户首先经过身份认证,认证通过后用户具有该资源的访问权限方可访问。

1.2认证

关键对象

Subject:主体

访问系统的用户,主体可以是用户、程序等,进行认证的都称为主体;

Principal:身份信息

是主体(subject)进行身份认证的标识,标识必须具有唯一性,如用户名、手机号、邮箱地址等,一个主体可以有多个身份,但是必须有一个主身份(Primary Principal)。

credential:凭证信息

是只有主体自己知道的安全信息,如密码、证书等。

1.3 授权

关键对象

授权可简单理解为who对what(which)进行How操作:

Who即主体Subject),主体需要访问系统中的资源。

What即资源(Resource),如系统菜单、页面、按钮、类方法、系统商品信息等。资源包括资源类型和资源实例,比如商品信息为资源类型,类型为t01的商品为资源实例,编号为001的商品信息也属于资源实例。

How权限/许可(Permission),规定了主体对资源的操作许可,权限离开资源没有意义,如用户查询权限、用户添加权限、某个类方法的调用权限、编号为001用户的修改权限等,通过权限可知主体对哪些资源都有哪些操作许可。

权限分为粗颗粒和细颗粒,粗颗粒权限是指对资源类型的权限,细颗粒权限是对资源实例的权限。

1.4访问控制

 基于角色的访问控制

RBAC基于角色的访问控制(Role-Based Access Control)是以角色为中心进行访问控制。

基于资源的访问控制

RBAC基于资源的访问控制(Resource-Based Access Control)是以资源为中心进行访问控制。

二、权限管理解决方案

2.1基于url拦截

基于url拦截是企业中常用的权限管理方法,实现思路是:将系统操作的每个url配置在权限表中,将权限对应到角色,将角色分配给用户,用户访问系统功能通过Filter进行过虑,过虑器获取到用户访问的url,只要访问的url是用户分配角色中的url则放行继续访问。

如下图:

2.1.1 activeUser用户身份类

用户登陆成功记录activeUser信息并将activeUser存入session。

public class ActiveUser implements java.io.Serializable {
    private String userid;//用户id
    private String usercode;// 用户账号
    private String username;// 用户名称

    private List<SysPermission> menus;// 菜单
    private List<SysPermission> permissions;// 权限
View Code

2.1.2anonymousURL.properties

anonymousURL.properties公开访问地址,无需身份认证即可访问。

2.1.3commonURL.properties

commonURL.properties公共访问地址,身份认证通过无需分配权限即可访问。

2.1.4用户身份认证拦截器

使用springmvc拦截器对用户身份认证进行拦截,如果用户没有登陆则跳转到登陆页面,本功能也可以使用filter实现 。

public class LoginInterceptor implements HandlerInterceptor {

    // 在进入controller方法之前执行
    // 使用场景:比如身份认证校验拦截,用户权限拦截,如果拦截不放行,controller方法不再执行
    @Override
    public boolean preHandle(HttpServletRequest request,
            HttpServletResponse response, Object handler) throws Exception {

        // 校验用户访问是否是公开资源地址(无需认证即可访问)
        List<String> open_urls = ResourcesUtil.gekeyList("anonymousURL");

        // 用户访问的url
        String url = request.getRequestURI();
        for (String open_url : open_urls) {
            if (url.indexOf(open_url) >= 0) {
                // 如果访问的是公开 地址则放行
                return true;
            }
        }

        // 校验用户身份是否认证通过
        HttpSession session = request.getSession();
        ActiveUser activeUser = (ActiveUser) session.getAttribute("activeUser");
        if (activeUser != null) {
            // 用户已经登陆认证,放行
            return true;
        }
        // 跳转到登陆页面
        request.getRequestDispatcher("/WEB-INF/jsp/login.jsp").forward(request,
                response);
        return false;
    }
View Code

2.1.5 用户授权拦截器

使用springmvc拦截器对用户访问url进行拦截,如果用户访问的url没有分配权限则跳转到无权操作提示页面(refuse.jsp),本功能也可以使用filter实现。

public class PermissionInterceptor implements HandlerInterceptor {

    // 在进入controller方法之前执行
    // 使用场景:比如身份认证校验拦截,用户权限拦截,如果拦截不放行,controller方法不再执行
    // 进入action方法前要执行
    @Override
    public boolean preHandle(HttpServletRequest request,
            HttpServletResponse response, Object handler) throws Exception {
        // TODO Auto-generated method stub
        // 用户访问地址:
        String url = request.getRequestURI();

        // 校验用户访问是否是公开资源地址(无需认证即可访问)
        List<String> open_urls = ResourcesUtil.gekeyList("anonymousURL");
        // 用户访问的url
        for (String open_url : open_urls) {
            if (url.indexOf(open_url) >= 0) {
                // 如果访问的是公开 地址则放行
                return true;
            }
        }
        //从 session获取用户公共访问地址(认证通过无需分配权限即可访问)
        List<String> common_urls = ResourcesUtil.gekeyList("commonURL");
        // 用户访问的url
        for (String common_url : common_urls) {
            if (url.indexOf(common_url) >= 0) {
                // 如果访问的是公共地址则放行
                return true;
            }
        }
        // 从session获取用户权限信息

        HttpSession session = request.getSession();

        ActiveUser activeUser = (ActiveUser) session.getAttribute("activeUser");

        // 取出session中权限url
        // 获取用户操作权限
        List<SysPermission> permission_list = activeUser.getPermissions();
        // 校验用户访问地址是否在用户权限范围内
        for (SysPermission sysPermission : permission_list) {
            String permission_url = sysPermission.getUrl();
            if (url.contains(permission_url)) {
                return true;
            }
        }

        // 跳转到页面
        request.getRequestDispatcher("/WEB-INF/jsp/refuse.jsp").forward(
                request, response);
        return false;
    }
View Code

2.2用户登陆

用户输入用户账号和密码登陆,登陆成功将用户的身份信息(用户账号、密码、权限菜单、权限url等)记入activeUser类,并写入session。

2.2.1controller

//用户登陆提交
    @RequestMapping("/loginsubmit")
    public String loginsubmit(HttpSession session,String usercode,String password,String randomcode) throws Exception{

        //校验验证码
        //从session获取正确的验证码
        String validateCode = (String)session.getAttribute("validateCode");
        if(!randomcode.equals(validateCode)){
            //抛出异常:验证码错误
            throw new CustomException("验证码 错误 !");
        }
        //用户身份认证
        ActiveUser activeUser = sysService.authenticat(usercode, password);
        
        //记录session
        session.setAttribute("activeUser", activeUser);
        
        return "redirect:first.action";
    }
View Code

2.2.3 service接口

    public ActiveUser authenticat(String usercode, String password)
            throws Exception;

    // 根据账号查询用户
    public SysUser findSysuserByUsercode(String usercode) throws Exception;

    // 根据用户id获取权限
    public List<SysPermission> findSysPermissionList(String userid)
            throws Exception;

    // 根据用户id获取菜单
    public List<SysPermission> findMenuList(String userid) throws Exception;
View Code

 

转载于:https://www.cnblogs.com/yanmingyuan/p/10584812.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
RBAC(Role-Based Access Control)是一种基于角色的访问控制,它将权限授予角色,然后将角色授予用户。在Django中,可以使用django-guardian或django-rules等第三方库来实现RBAC权限管理,也可以自己编写代码实现。 下面是一个基于Django自己编写的简单RBAC权限管理系统的实现过程: 1. 定义权限模型 在Django中,可以通过定义模型来表示权限。例如,可以定义一个Permission模型,用来表示系统中的所有权限: ``` from django.db import models class Permission(models.Model): name = models.CharField(max_length=255, unique=True) codename = models.CharField(max_length=100, unique=True) ``` 其中name字段表示权限的名称,codename字段表示权限的代码名称。 2. 定义角色模型 同样地,可以定义一个Role模型,用来表示系统中的所有角色: ``` from django.db import models class Role(models.Model): name = models.CharField(max_length=255, unique=True) permissions = models.ManyToManyField('Permission') ``` 其中name字段表示角色的名称,permissions字段表示角色拥有的权限。 3. 定义用户模型 可以使用Django自带的User模型或者自己定义一个用户模型。在用户模型中,可以添加一个roles字段,用来表示用户所拥有的角色: ``` from django.contrib.auth.models import AbstractUser from django.db import models class User(AbstractUser): roles = models.ManyToManyField('Role') ``` 4. 编写权限检查装饰器 在Django中,可以使用装饰器来检查用户是否拥有某个权限。下面是一个简单的权限检查装饰器的实现: ``` from functools import wraps from django.http import HttpResponseForbidden def permission_required(perm): def decorator(view_func): @wraps(view_func) def _wrapped_view(request, *args, **kwargs): if not request.user.has_perm(perm): return HttpResponseForbidden() return view_func(request, *args, **kwargs) return _wrapped_view return decorator ``` 在上面的代码中,permission_required装饰器接受一个权限codename作为参数,返回一个装饰器函数。这个装饰器函数接受一个视图函数作为参数,返回一个新的视图函数。新的视图函数在执行前会检查用户是否拥有该权限,如果没有则返回403禁止访问状态码。 5. 在视图函数中使用权限检查装饰器 在需要进行权限检查的视图函数上加上permission_required装饰器即可: ``` @permission_required('app.view_model') def my_view(request): # do something ``` 在上面的代码中,my_view函数需要拥有view_model权限才能访问。 6. 编写角色管理视图 可以编写一个简单的角色管理视图,用来管理系统中的角色和权限: ``` from django.shortcuts import render from .models import Role, Permission def role_list(request): roles = Role.objects.all() return render(request, 'role_list.html', {'roles': roles}) def role_detail(request, role_id): role = Role.objects.get(id=role_id) permissions = Permission.objects.all() return render(request, 'role_detail.html', {'role': role, 'permissions': permissions}) ``` 在上面的代码中,role_list函数返回所有角色的列表,role_detail函数返回指定角色的详细信息和所有权限的列表。 7. 编写用户角色管理视图 可以编写一个简单的用户角色管理视图,用来管理用户和角色的关联关系: ``` from django.shortcuts import render from django.contrib.auth.models import User from .models import Role def user_list(request): users = User.objects.all() return render(request, 'user_list.html', {'users': users}) def user_detail(request, user_id): user = User.objects.get(id=user_id) roles = Role.objects.all() return render(request, 'user_detail.html', {'user': user, 'roles': roles}) ``` 在上面的代码中,user_list函数返回所有用户的列表,user_detail函数返回指定用户的详细信息和所有角色的列表。 8. 编写用户角色管理视图的表单处理函数 可以编写一个简单的表单处理函数,用来处理用户和角色的关联关系: ``` from django.shortcuts import redirect from django.contrib.auth.models import User from .models import Role def assign_role(request, user_id): if request.method == 'POST': user = User.objects.get(id=user_id) role_ids = request.POST.getlist('roles') roles = Role.objects.filter(id__in=role_ids) user.roles.set(roles) return redirect('user_detail', user_id=user_id) ``` 在上面的代码中,assign_role函数接受一个用户ID作为参数,从POST请求中获取选中的角色ID,将这些角色和用户关联起来,然后重定向到用户详细信息页面。 9. 编写角色管理视图的表单处理函数 可以编写一个简单的表单处理函数,用来处理角色和权限的关联关系: ``` from django.shortcuts import redirect from .models import Role, Permission def assign_permission(request, role_id): if request.method == 'POST': role = Role.objects.get(id=role_id) permission_ids = request.POST.getlist('permissions') permissions = Permission.objects.filter(id__in=permission_ids) role.permissions.set(permissions) return redirect('role_detail', role_id=role_id) ``` 在上面的代码中,assign_permission函数接受一个角色ID作为参数,从POST请求中获取选中的权限ID,将这些权限和角色关联起来,然后重定向到角色详细信息页面。 10. 编写模板 最后,可以编写一些简单的模板来渲染上述视图函数返回的数据。 例如,可以编写role_list.html模板来渲染角色列表: ``` <ul> {% for role in roles %} <li><a href="{% url 'role_detail' role.id %}">{{ role.name }}</a></li> {% endfor %} </ul> ``` 可以编写role_detail.html模板来渲染角色详细信息和权限列表: ``` <h1>{{ role.name }}</h1> <h2>Permissions</h2> <form method="post" action="{% url 'assign_permission' role.id %}"> {% csrf_token %} {% for permission in permissions %} <label> <input type="checkbox" name="permissions" value="{{ permission.id }}" {% if permission in role.permissions.all %}checked{% endif %}> {{ permission.name }} </label> {% endfor %} <button type="submit">Save</button> </form> ``` 可以编写user_list.html模板来渲染用户列表: ``` <ul> {% for user in users %} <li><a href="{% url 'user_detail' user.id %}">{{ user.username }}</a></li> {% endfor %} </ul> ``` 可以编写user_detail.html模板来渲染用户详细信息和角色列表: ``` <h1>{{ user.username }}</h1> <h2>Roles</h2> <form method="post" action="{% url 'assign_role' user.id %}"> {% csrf_token %} {% for role in roles %} <label> <input type="checkbox" name="roles" value="{{ role.id }}" {% if role in user.roles.all %}checked{% endif %}> {{ role.name }} </label> {% endfor %} <button type="submit">Save</button> </form> ``` 至此,一个简单的RBAC权限管理系统就完成了。当然,实际应用中可能需要更复杂的权限管理需求,可以根据具体情况进行扩展。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值