ACL授权实例
上一篇关于ACL的文章中:位运算实现ACL授权与认证过程的原理解析,我们学习了通过位运算实现ACL授权与认证的原理核心,今天我们一起来看授权的实例。
实现的功能很简单:打开授权界面时,加载已授权信息。通过点击授权界面上面的复选框,实现授权与取消授权。
下面是Manager层的实现:
package com.lzq.manager.impl; import java.util.List;
import com.lzq.model.ACL; /**
* 主体授权管理实现
* @author lzq
*
*/
public class ACLManager extends AbstractPageManager { /**
* 授权过程
* 添加或更新授权操作
* @param principalType 主体类型 用户或角色
* @param principalSn 主体标识 用户Id或角色Id
* @param resourceSn 资源标识 模块Id
* @param permission 权限 C/R/U/D 0 1 2 3
* @param yes 是否允许,true表示允许授权;false表示不允许授权
*/
public void addOrUpdatePermission(String principalType, int principalSn,
int resourceSn, int permission, boolean yes) {
//根据主体标识和资源标识查找ACL实例
ACL acl = findACL(principalType, principalSn, resourceSn); //如果存在ACL实例,则更新其授权
if (acl != null) {
acl.setPermission(permission, yes);
getHibernateTemplate().update(acl);
return;
} //如果不存在ACL实例,则创建ACL实例
acl = new ACL();
acl.setPrincipalType(principalType);
acl.setPrincipalSn(principalSn);
acl.setResourceSn(resourceSn);
acl.setPermission(permission, yes);
getHibernateTemplate().save(acl);
} /**
* 删除授权
* @param principalType 主体类型
* @param principalSn 主体标识
* @param resourceSn 资源标识
*/
public void delPermission(String principalType, int principalSn,
int resourceSn) {
getHibernateTemplate()
.delete
(
findACL(principalType, principalSn, resourceSn)
);
} /**
* 这是在用户授权页面调用的方法
* 设置用户某个资源授权的继承特性
* 添加或更新用户的继承特性
* i. -1继承:这些权限将使用其(即用户)所拥有的角色的权限,而不使用其(即用户)单独设置的权限
* ii. 0表示不继承:这些权限将使用其单独设置的权限,而不使用其所拥有的角色的权限
* @param userId 用户标识
* @param sourceSn 资源标识 模块Id
* @param yes true表示继承,false表示不继承
*/
public void addOrUpdateUserExtends(int userId, int sourceSn, boolean yes) { //根据主体标识和资源标识查找ACL实例
ACL acl = findACL(ACL.TYPE_USER ,userId, sourceSn); //如果存在ACL实例,则更新其授权
if (yes) {
acl.setExtends(yes);
getHibernateTemplate().update(acl);
return;
} //如果不存在ACL实例,则创建ACL实例
acl = new ACL();
acl.setPrincipalType(ACL.TYPE_USER);
acl.setPrincipalSn(userId);
acl.setResourceSn(sourceSn);
acl.setExtends(yes);
getHibernateTemplate().save(acl);
} /**
* 根据主体类型、主体标识、资源标识查找ACL实例
* @param principalType
* @param principalSn
* @param resourceSn
* @param permission
* @return
*/
private ACL findACL(String principalType, int principalSn,int resourceSn){
String strSql ="select acl from ACL acl where acl.principalType = ? and acl.principalSn = ? and acl.resourceSn = ?";
ACL acl =(ACL)getSession().createQuery(strSql)
.setParameter(0, principalType)
.setParameter(1, principalSn)
.setParameter(2, resourceSn)
.uniqueResult(); return acl;
} /**
* 页面加载时,加载所有的授权信息
* @param principalType
* @param principalSn
* @return
*/
public List searchACLRecord(String principalType, int principalSn) {
String sql = "select resourceSn,aclState&1,aclState&2,"
+ "aclState&4,aclState&8,aclTriState from T_ACL where "
+ "principalType='"+principalType+"' and principalSn="+principalSn; List aclRecord = getSession().createSQLQuery(sql).list();
return aclRecord;
}
}
通过DWR,在jsp页面上面调用Manager层的相应的方法,加载时实现对已授权信息的加载,以及用户对权限的动态控制。
<%@ page language="java" contentType="text/html; charset=GB18030"
pageEncoding="GB18030"%>
<%@ include file="/common/common.jsp" %> <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=GB18030"> <c:choose>
<c:when test="${aclForm.principalType eq 'Role' }">
<c:set var="title" value="请给角色【${role.name }】授权" />
</c:when>
<c:otherwise>
<c:set var="title" value="请给用户【${user.person.name }】授权" />
</c:otherwise>
</c:choose>
<title>${title }</title> <link href="style/oa.css" rel="stylesheet" type="text/css">
<script language="javascript" src="script/public.js"></script>
<script type="text/javascript" src="dwr/engine.js"></script>
<script type="text/javascript" src="dwr/util.js"></script>
<script type="text/javascript" src="dwr/interface/aclManager.js"></script>
<script type="text/javascript">
//授权
function addOrUpdatePermission(field){
//如果被选择上,则同时选择其"不继承"和"启用"checkbox
if(field.checked){
$(field.resourceSn+"_USE").checked = true;
<c:if test="${aclForm.principalType eq 'User' }">
$(field.resourceSn+"_EXT").checked = true;
</c:if>
}
aclManager.addOrUpdatePermission(
"${aclForm.principalType}",
${aclForm.principalSn},
field.resourceSn,
field.permission,
field.checked
);
} //设置用户的继承特性
function addOrUpdateUserExtends(field){
aclManager.addOrUpdateUserExtends(
${aclForm.principalSn},
field.resourceSn,
!field.checked
);
}
//点击 启用 checkbox
function usePermission(field){
//如果checkbox被选中,意味着需要更新ACL的状态
//更新C/R/U/D以及Extends状态 //设置为同步状态,以便DWR依次发出下列请求
dwr.engine.setAsync(false); if(field.checked){
//更新C状态
addOrUpdatePermission($(field.resourceSn+"_C"));
//更新R状态
addOrUpdatePermission($(field.resourceSn+"_R"));
//更新U状态
addOrUpdatePermission($(field.resourceSn+"_U"));
//更新D状态
addOrUpdatePermission($(field.resourceSn+"_D"));
//更新Extends状态
<c:if test="${aclForm.principalType eq 'User' }">
addOrUpdateUserExtends($(field.resourceSn+"_EXT"));
</c:if>
}else{
//如果不启用,则删除授权信息
aclManager.delPermission(
"${aclForm.principalType}",
${aclForm.principalSn},
field.resourceSn
); //并且在界面上去掉相应的CRUD选择的选项
$(field.resourceSn+"_C").checked = false;
$(field.resourceSn+"_R").checked = false;
$(field.resourceSn+"_U").checked = false;
$(field.resourceSn+"_D").checked = false;
<c:if test="${aclForm.principalType eq 'User' }">
$(field.resourceSn+"_EXT").checked = false;
</c:if>
}
} //打开界面时,从数据库中加载授权信息
function initTable(){
aclManager.searchACLRecord(
"${aclForm.principalType}",
${aclForm.principalSn},
function(datas){
for(var i=0;i<datas.length;i++){
var resourceSn =datas[i][0];
var cState = datas[i][1];
var rState = datas[i][2];
var uState = datas[i][3];
var dState = datas[i][4];
var extState = datas[i][5];
$(resourceSn+"_C").checked =cState ==0 ? false : true;
$(resourceSn+"_R").checked =rState ==0 ? false : true;
$(resourceSn+"_U").checked =uState ==0 ? false : true;
$(resourceSn+"_D").checked =dState ==0 ? false : true;
//等于0,不继承,就要选择上,所以为true
<c:if test="${aclForm.principalType eq 'User' }">
$(resourceSn+"_EXT").checked=extState ==0 ? true : false;
</c:if>
$(resourceSn+"_USE").checked = true;
}
}
);
}
</script>
</head>
<body onload="initTable()">
<form action="person.do">
<TABLE class="tableEdit" border="0" cellspacing="1" cellpadding="0" style="width:580px;">
<TBODY>
<TR>
<td>
<table class="tableEdit" style="width:580px;" cellspacing="0" border="0" cellpadding="0">
<tr>
<!-- tdEditContent -->
<td class="tdEditLabel" >顶级模块</td>
<td class="tdEditContent">二级模块</td>
<td class="tdEditLabel">权限</td> <c:if test="${aclForm.principalType eq 'User' }">
<td class="tdEditLabel">不继承</td>
</c:if>
<td class="tdEditLabel">启用</td>
</tr> <!-- 输出模块树 -->
<c:forEach items="${moduleList }" var="module">
<tr>
<td>${module.name }</td>
<td> </td>
<td>
<input type="checkbox" id="${module.id }_C" resourceSn="${module.id }" permission="0" onclick="addOrUpdatePermission(this)">C
<input type="checkbox" id="${module.id }_R" resourceSn="${module.id }" permission="1" onclick="addOrUpdatePermission(this)">R
<input type="checkbox" id="${module.id }_U" resourceSn="${module.id }" permission="2" onclick="addOrUpdatePermission(this)">U
<input type="checkbox" id="${module.id }_D" resourceSn="${module.id }" permission="3" onclick="addOrUpdatePermission(this)">D
</td>
<c:if test="${aclForm.principalType eq 'User' }">
<td>
<input type="checkbox" id="${module.id }_EXT" resourceSn="${module.id }" onclick="addOrUpdateUserExtends(this)">
</td>
</c:if>
<td>
<input type="checkbox" id="${module.id }_USE" resourceSn="${module.id }" onclick="usePermission(this)">
</td>
</tr> <c:forEach items="${module.children }" var="child">
<tr>
<td> </td>
<td>${child.name }</td>
<td>
<input type="checkbox" id="${child.id }_C" resourceSn="${child.id }" permission="0" onclick="addOrUpdatePermission(this)">C
<input type="checkbox" id="${child.id }_R" resourceSn="${child.id }" permission="1" onclick="addOrUpdatePermission(this)">R
<input type="checkbox" id="${child.id }_U" resourceSn="${child.id }" permission="2" onclick="addOrUpdatePermission(this)">U
<input type="checkbox" id="${child.id }_D" resourceSn="${child.id }" permission="3" onclick="addOrUpdatePermission(this)">D
</td>
<c:if test="${aclForm.principalType eq 'User' }">
<td>
<input type="checkbox" id="${child.id }_EXT" resourceSn="${child.id }" onclick="addOrUpdateUserExtends(this)">
</td>
</c:if>
<td><input type="checkbox" id="${child.id }_USE" onclick="usePermission(this)" resourceSn="${child.id }"></td>
</tr>
</c:forEach>
</c:forEach>
</table>
</td>
</TR>
</TBODY>
</TABLE>
</form>
</body>
</html>
下面是通过点击角色授权或者用户授权,进入的授权界面:
这个过程说难不难,说简单也不简单。我认为这个功能的主要亮点有:
1、对多选框的动态控制;
2、巧妙的使用位运算完成授权与认证。
ACL授权实例的更多相关文章
- Identity Server 4 原理和实战(完结)_建立Identity Server 4项目,Client Credentials 授权实例
创建项目 dotnet new -i IdentityServer4.Templates 多出来的这些模板 adminUI用来测试,想要用再生产环境,需要交钱 结合core的 Identity来使用 ...
- Identity Server 4 原理和实战(完结)_Resource Owner Password Credentials 授权实例
今天要讲的 用fiddler来监听,昨天的客户端的请求 这是一个post的请求 这是响应的数据 Expores_in超时时间, 今天的内容 在服务端再声明一个client端 wpf的应用的效果图 首先 ...
- ACL登陆认证
前篇文章ACL授权实例介绍了授权,授权完成之后,就要进行认证.ACL的认证主要分为登陆认证与即时认证.所谓登录认证就是在用户登陆的时候,进行信息认证.根据用户Id,加载上来该用户所拥有的权限模块:而即 ...
- ACL权限设置命令setfacl和getfacl命令
ACL权限设置命令setfacl和getfacl命令 setfacl命令是用来在命令行里设置ACL(访问控制列表).在命令行里,一系列的命令跟随以一系列的文件名. [TOC] 选项 |参数|说明| ...
- phalcon——访问控制列表ACL
一个完整的使用实例(将acl封装成一个插件使用): use Phalcon\Acl; use Phalcon\Acl\Role; use Phalcon\Acl\Resource; use Phalc ...
- MySQL-5.6.36-多实例-部署(编译版)
MySQL多实例_沁贰百科 注:部署双实例前,首先需要部署单实例,单实例部署详情如下: https://www.cnblogs.com/wangqiner/p/9081002.html 1.如已经安装 ...
- 实战Kafka ACL机制
1.概述 在Kafka0.9版本之前,Kafka集群时没有安全机制的.Kafka Client应用可以通过连接Zookeeper地址,例如zk1:2181:zk2:2181,zk3:2181等.来获取 ...
- PSR-4 规范实例讲解 -- php 自动加载
参考 参考文档:https://www.kancloud.cn/thinkphp/php-fig-psr/3144 参考实例:https://github.com/php-fig/fig-standa ...
- Kubernetes 部署kafka ACL(单机版)
一.概述 在Kafka0.9版本之前,Kafka集群时没有安全机制的.Kafka Client应用可以通过连接Zookeeper地址,例如zk1:2181:zk2:2181,zk3:2181等.来获取 ...
随机推荐
- css中选择器
css中常用的选择器有: 1.元素选择器:h1{} 如<h1></h1> 2.类选择器:.test{}或者h1.test{} 如<h1 class="test ...
- python的读写和写读操作
# 读写操作 (读写操作是正常的)f = open('log',mode='r+',encoding='utf-8') # log是文件名 print(f.read()) f.write(" ...
- godaddy nginx https 配置
一. 生成秘钥key,运行: $ openssl genrsa -des3 -out server.key 2048 1 会有两次要求输入密码,输入同一个即可 输入密码 然后你就获得了一个server ...
- Scrapy简单入门及实例讲解-转载
Scrapy是一个为了爬取网站数据,提取结构性数据而编写的应用框架. 其可以应用在数据挖掘,信息处理或存储历史数据等一系列的程序中.其最初是为了页面抓取 (更确切来说, 网络抓取 )所设计的, 也可以 ...
- bedtools简介及应用
1)背景处理基因组数据中,比较基因组不同区域,例如寻找overlap等,是一种基本的且常见的问题.虽然UCSC 中‘Table Browser’或者Galaxy可以用来处理,但是当这些工具面对大的数据 ...
- 【英宝通Unity4.0公开课学习 】(五)47讲到75讲
不知不觉今天都已经看了快30讲了,虽然很想快马加鞭地将后面的内容看完,但为了学习的质量,还是挺下来写一篇blog :) 这两天有些昏昏沉沉的,但感觉生活还安排得不错,原因找去找来觉得是没怎么开窗透气. ...
- win10下安装oracle11G Examples出错[INS-32025][INS-52001]
安装oracle examples时提示出错:[INS-32025] 所选安装与指定 Oracle 主目录中已安装的软件冲突.[INS-52001] Oracle Database Examples ...
- mysql优化概述2
一.索引的概念 利用关键字,就是记录的部分数据(某个字段,某些字段,某个字段的一部份),建立与记录位置的对应关系,就是索引.索引的关键字一定是排序的. 二.索引的类型 mysql支持四种索引: 1.主 ...
- springmvc将处理后的数据通过get方法传给页面时,可能会出现乱码。下面对于get请求中文参数出现乱码提出解决办法。
对于get请求中文参数出现乱码解决办法有两个: 1.修改tomcat配置文件(tomcat--->conf--->server.xml)添加编码与工程编码一致,如下: <Connec ...
- SSH框架整合jar包时的注意事项
SSH框架整合jar包时的注意事项: 在将三个框架所需的jar整合到一起后,要看一下有没有相同类型但是版本不同的jar包,如果有的话,需要把低版本的jar包删除掉,否则会报错.我这里整合的时候java ...