如何在应用系统中实现数据权限的控制功能

 我来答
day忘不掉的痛
2017-05-09 · 知道合伙人数码行家
day忘不掉的痛
知道合伙人数码行家
采纳数:62646 获赞数:223941
本人担任公司网络部总经理多年,有充足的网络经验、互联网相关知识和资讯。

向TA提问 私信TA
展开全部
对数据进行控制最好通过弹性的方式,在一个系统里面或者功能模块里面对用户角色或者岗位进行设置,一般权限控制默认在一个权限管理系统模块进行设定,数据权限也应该如此。
权限系统除了可以对用户能操作那些功能进行限定,也还可以对其访问那些组织机构的数据进行限定,我们通过权限系统,把这些权限控制的数据进行保存,在应用系统模块里面进行整合即可,根据角色拥有的数据权限,授予用户对其他部门或者机构的数据进行访问。如下面是我权限系统模块里面对角色权限的设置操作。
1)对角色功能权限进行设置

2)对角色数据权限进行控制

当对角色的数据权限进行保存后,我们就可以把这个角色能够访问的组织机构(公司、部门、工作组等等)进行记录起来了。
2)应用系统的集成,实现数据权限的控制
如我的一个病人资料应用系统,客户要求就是基于互联网的应用系统,因此使用WCF数据通讯模式实现数据的集中管理,而且他们要基于医院单位的数据管理模式,也就是每个单位管理各自的数据,我们可以把不同的医院单位作为不同的公司性质来区分,这样在权限模块中进行设置即可。
1)在应用程序中,通过在程序头部,让可以管理多个医院机构的用户选择管理的数据访问,即可实现不同的数据区分管理。

2)当用户在上面切换不同的机构,所有存在的界面数据全部实现刷新,如打开了很多界面,那么这些界面的数据也随之更新为对应新的机构下的数据。
了解了上面大致的需求,我们应该如何通过整合权限管理系统实现在应用系统的数据权限控制和集成呢?
首先我们需要在用户登陆的时候,获取对应用户的数据权限内容,然后把它转化为我们需要的信息,如下代码所示。

//判断如果用户管理的公司数据多于两个,那么就显示选择单位列表,并绑定公司数据
List<RoleDataInfo> roleDataList = CallerFactory<IRoleDataService>.Instance.FindByUser(info.ID);
List<int> companyList = new List<int>();
foreach (RoleDataInfo roleDataInfo in roleDataList)
{
if (!string.IsNullOrEmpty(roleDataInfo.BelongCompanys))
{
string[] companyArray = roleDataInfo.BelongCompanys.Split(',');
foreach (string company in companyArray)
{
if (!string.IsNullOrEmpty(company) && ValidateUtil.IsNumber(company.Trim()))
{
if (!companyList.Contains(company.ToInt32()))
{
companyList.Add(company.ToInt32());
}
}
}
}
}
Portal.gc.CompanyList = companyList;

//设置选定的公司ID
Cache.Instance["SelectedCompanyID"] = info.Company_ID;
//设置过滤条件给界面基类使用
Cache.Instance["DataFilterCondition"] = string.Format(" (Company_ID is null OR Company_ID = '{0}')", info.Company_ID);

其中CallerFactory方式调用,是以WCF的方式获取对应的数据库数据。在上面代码里面,有一个RoleDataInfo的实体类,这个就是用来承载用户角色的数据权限数据,其中包括了
BelongCompanys(所属公司)和 BelongDepts(所属部门 )的属性,我们把它解析为我需要的数据List<int> companyList 、 SelectedCompanyID 和 DataFilterCondition,当然如果有部门的控制,可以做的更多,我这里仅仅以医院机构进行区分即可。
SelectedCompanyID 就是用户选择查看的组织机构ID,DataFilterCondition就是用来构建一个数据过滤脚本,对用户看到的数据进行一个过滤筛选作用。我们把这两个数据内容,放到Winform的缓存里面,如果是Web可以用Session代替,这样可以在多个模块或者界面中方便访问使用。
为了实现用户选择不同的机构,所有打开的窗体数据实现相应的更新,那么我们需要处理公司选择的操作,具体实现代码如下所示。

private void txtCompany_EditValueChanged(object sender, EventArgs e)
{
//如果用户选择公司,以选择为主,否则以当前客户所在公司
if (this.txtCompany.EditValue != null)
{
CListItem item = this.txtCompany.EditValue as CListItem;
if (item != null)
{
//设置选定的公司ID
Cache.Instance["SelectedCompanyID"] = item.Value;
SetSelectedCompanyName();

//设置过滤条件给界面基类使用
string condition = string.Format(" Company_ID = '{0}'", item.Value);
Cache.Instance["DataFilterCondition"] = condition;

//遍历全部窗口,更新
foreach (WHC.Framework.BaseUI.BaseDock form in this.MdiChildren)
{
form.SelectedCompanyID = item.Value;
form.DataFilterCondition = condition;
form.FormOnLoad();
}

string message = string.Format("您已经切换数据显示:{0}", item.Text);
MessageDxUtil.ShowTips(message);
}
}
}

上面是对所有打开的窗体,传递了对应的信息,然后进行了刷新。那么我们在看看窗体本身内部的数据显示逻辑是如何的。
我们以病人资料的查询界面为例,根据不同的输入条件,对数据进行不同查询外,还增加了一个对组织机构过滤的条件,如下所示。

/// <summary>
/// 根据查询条件构造查询语句
/// </summary>
private string GetConditionSql()
{
//如果存在高级查询对象信息,则使用高级查询条件,否则使用主表条件查询
SearchCondition condition = advanceCondition;
if (condition == null)
{
condition = new SearchCondition();
condition.AddCondition("BedNo", this.txtBedNo.Text.Trim(), SqlOperator.Like);
condition.AddCondition("TumorPart", this.txtTumorPart.Text.Trim(), SqlOperator.Like);
........................
condition.AddDateCondition("InDate", this.txtInDate, this.txtInDateEnd);
condition.AddDateCondition("LeaveDate", this.txtLeaveDate, this.txtLeaveDateEnd);if (this.chkHasReferral.Checked)
{
condition.AddCondition("HasReferral", "是", SqlOperator.Equal, true);
}
...................
}

string where = condition.BuildConditionSql().Replace("Where", "");

//如果公司过滤条件不为空,那么需要进行过滤
if (!string.IsNullOrEmpty(this.DataFilterCondition))
{
where += string.Format(" AND {0}", this.DataFilterCondition);
}

return where;
}

/// <summary>
/// 绑定列表数据
/// </summary>
private void BindData()
{
//entity
this.winGridViewPager1.DisplayColumns = "HandNo,BedNo,MidVideo,Name,Sex,IdentityCard,Age,Birthday,HospitalNo,IDNumber,InDate,InDiagnosis,SurgeryDate,DirectorSurgeon,LeaveDate,TumorPart,LeaveDiagnosis,IsFirstTime,LeaveSpecimens,OuterFilm,PreMRI,PreCT,PrePicture,MidPathology,AfterCTMRI,AfterPicture,AfterVideo,LeavePicture,Endocrine,Professor,Address,Telephone,HasReferral,ReferralDate,ReferralTime,Pathology,Note,Report";
this.winGridViewPager1.ColumnNameAlias = CallerFactory<IPatientService>.Instance.GetColumnNameAlias();//字段列显示名称转义

string where = GetConditionSql();
PagerInfo pagerInfo = this.winGridViewPager1.PagerInfo;
List<PatientInfo> list = CallerFactory<IPatientService>.Instance.FindWithPager(where, ref pagerInfo);
this.winGridViewPager1.DataSource = new WHC.Pager.WinControl.SortableBindingList<PatientInfo>(list);
this.winGridViewPager1.PrintTitle = "病人基本资料信息报表";
}

以上绑定代码实现了:分页、条件查询、高级查询、字段列表显示、中文名称转义,以及最重要的,根据公司条件进行数据过滤的操作,从而让用户只能管理自己的数据。
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
光点科技
2023-08-15 广告
通常情况下,我们会按照结构模型把系统产生的数据分为三种类型:结构化数据、半结构化数据和非结构化数据。结构化数据,即行数据,是存储在数据库里,可以用二维表结构来逻辑表达实现的数据。最常见的就是数字数据和文本数据,它们可以某种标准格式存在于文件... 点击进入详情页
本回答由光点科技提供
深圳市励拓软件有限公司
2017-05-09 · 互联网+时代高效组织信息化平台
深圳市励拓软件有限公司
汇讯WiseUC企业即时通讯软件是一款以组织内沟通交流为基础,即时通讯为核心,融合办公协同、IT系统集成,帮助企业降低运营成本、提升组织效率的企业级沟通协同平台。
向TA提问
展开全部
对数据进行控制最好通过弹性的方式,在一个系统里面或者功能模块里面对用户角色或者岗位进行设置,一般权限控制默认在一个权限管理系统模块进行设定,数据权限也应该如此。 权限系统除了可以对用户能操作那些功能进行限定,也还可以对其访问那些组织机构的数据进行限定,我们通过权限系统,把这些权限控制的数据进行保存,在应用系统模块里面进行整合即可,根据角色拥有的数据权限,授予用户对其他部门或者机构的数据进行访问。如下面是我权限系统模块里面对角色权限的设置操作。 1)对角色功能权限进行设置 2)对角色数据权限进行控制 当对角色的数据权限进行保存后,我们就可以把这个角色能够访问的组织机构(公司、部门、工作组等等)进行记录起来了。 2)应用系统的集成,实现数据权限的控制 如我的一个病人资料应用系统,客户要求就是基于互联网的应用系统,因此使用WCF数据通讯模式实现数据的集中管理,而且他们要基于医院单位的数据管理模式,也就是每个单位管理各自的数据,我们可以把不同的医院单位作为不同的公司性质来区分,这样在权限模块中进行设置即可。 1)在应用程序中,通过在程序头部,让可以管理多个医院机构的用户选择管理的数据访问,即可实现不同的数据区分管理。 2)当用户在上面切换不同的机构,所有存在的界面数据全部实现刷新,如打开了很多界面,那么这些界面的数据也随之更新为对应新的机构下的数据。 了解了上面大致的需求,我们应该如何通过整合权限管理系统实现在应用系统的数据权限控制和集成呢? 首先我们需要在用户登陆的时候,获取对应用户的数据权限内容,然后把它转化为我们需要的信息,如下代码所示。 //判断如果用户管理的公司数据多于两个,那么就显示选择单位列表,并绑定公司数据 List<RoleDataInfo> roleDataList = CallerFactory<IRoleDataService>.Instance.FindByUser(info.ID); List<int> companyList = new List<int>(); foreach (RoleDataInfo roleDataInfo in roleDataList) { if (!string.IsNullOrEmpty(roleDataInfo.BelongCompanys)) { string[] companyArray = roleDataInfo.BelongCompanys.Split(','); foreach (string company in companyArray) { if (!string.IsNullOrEmpty(company) && ValidateUtil.IsNumber(company.Trim())) { if (!companyList.Contains(company.ToInt32())) { companyList.Add(company.ToInt32()); } } } } } Portal.gc.CompanyList = companyList; //设置选定的公司ID Cache.Instance["SelectedCompanyID"] = info.Company_ID; //设置过滤条件给界面基类使用 Cache.Instance["DataFilterCondition"] = string.Format(" (Company_ID is null OR Company_ID = '{0}')", info.Company_ID); 其中CallerFactory方式调用,是以WCF的方式获取对应的数据库数据。在上面代码里面,有一个RoleDataInfo的实体类,这个就是用来承载用户角色的数据权限数据,其中包括了 BelongCompanys(所属公司)和 BelongDepts(所属部门 )的属性,我们把它解析为我需要的数据List<int> companyList 、 SelectedCompanyID 和 DataFilterCondition,当然如果有部门的控制,可以做的更多,我这里仅仅以医院机构进行区分即可。 SelectedCompanyID 就是用户选择查看的组织机构ID,DataFilterCondition就是用来构建一个数据过滤脚本,对用户看到的数据进行一个过滤筛选作用。我们把这两个数据内容,放到Winform的缓存里面,如果是Web可以用Session代替,这样可以在多个模块或者界面中方便访问使用。 为了实现用户选择不同的机构,所有打开的窗体数据实现相应的更新,那么我们需要处理公司选择的操作,具体实现代码如下所示。 private void txtCompany_EditValueChanged(object sender, EventArgs e) { //如果用户选择公司,以选择为主,否则以当前客户所在公司 if (this.txtCompany.EditValue != null) { CListItem item = this.txtCompany.EditValue as CListItem; if (item != null) { //设置选定的公司ID Cache.Instance["SelectedCompanyID"] = item.Value; SetSelectedCompanyName(); //设置过滤条件给界面基类使用 string condition = string.Format(" Company_ID = '{0}'", item.Value); Cache.Instance["DataFilterCondition"] = condition; //遍历全部窗口,更新 foreach (WHC.Framework.BaseUI.BaseDock form in this.MdiChildren) { form.SelectedCompanyID = item.Value; form.DataFilterCondition = condition; form.FormOnLoad(); } string message = string.Format("您已经切换数据显示:{0}", item.Text); MessageDxUtil.ShowTips(message); } } } 上面是对所有打开的窗体,传递了对应的信息,然后进行了刷新。那么我们在看看窗体本身内部的数据显示逻辑是如何的。 我们以病人资料的查询界面为例,根据不同的输入条件,对数据进行不同查询外,还增加了一个对组织机构过滤的条件,如下所示。 /// <summary> /// 根据查询条件构造查询语句 /// </summary> private string GetConditionSql() { //如果存在高级查询对象信息,则使用高级查询条件,否则使用主表条件查询 SearchCondition condition = advanceCondition; if (condition == null) { condition = new SearchCondition(); condition.AddCondition("BedNo", this.txtBedNo.Text.Trim(), SqlOperator.Like); condition.AddCondition("TumorPart", this.txtTumorPart.Text.Trim(), SqlOperator.Like); ........................ condition.AddDateCondition("InDate", this.txtInDate, this.txtInDateEnd); condition.AddDateCondition("LeaveDate", this.txtLeaveDate, this.txtLeaveDateEnd);if (this.chkHasReferral.Checked) { condition.AddCondition("HasReferral", "是", SqlOperator.Equal, true); } ................... } string where = condition.BuildConditionSql().Replace("Where", ""); //如果公司过滤条件不为空,那么需要进行过滤 if (!string.IsNullOrEmpty(this.DataFilterCondition)) { where += string.Format(" AND {0}", this.DataFilterCondition); } return where; } /// <summary> /// 绑定列表数据 /// </summary> private void BindData() { //entity this.winGridViewPager1.DisplayColumns = "HandNo,BedNo,MidVideo,Name,Sex,IdentityCard,Age,Birthday,HospitalNo,IDNumber,InDate,InDiagnosis,SurgeryDate,DirectorSurgeon,LeaveDate,TumorPart,LeaveDiagnosis,IsFirstTime,LeaveSpecimens,OuterFilm,PreMRI,PreCT,PrePicture,MidPathology,AfterCTMRI,AfterPicture,AfterVideo,LeavePicture,Endocrine,Professor,Address,Telephone,HasReferral,ReferralDate,ReferralTime,Pathology,Note,Report"; this.winGridViewPager1.ColumnNameAlias = CallerFactory<IPatientService>.Instance.GetColumnNameAlias();//字段列显示名称转义 string where = GetConditionSql(); PagerInfo pagerInfo = this.winGridViewPager1.PagerInfo; List<PatientInfo> list = CallerFactory<IPatientService>.Instance.FindWithPager(where, ref pagerInfo); this.winGridViewPager1.DataSource = new WHC.Pager.WinControl.SortableBindingList<PatientInfo>(list); this.winGridViewPager1.PrintTitle = "病人基本资料信息报表"; } 以上绑定代码实现了:分页、条件查询、高级查询、字段列表显示、中文名称转义,以及最重要的,根据公司条件进行数据过滤的操作,从而让用户只能管理自己的数据。
已赞过 已踩过<
你对这个回答的评价是?
评论 收起
推荐律师服务: 若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询

为你推荐:

下载百度知道APP,抢鲜体验
使用百度知道APP,立即抢鲜体验。你的手机镜头里或许有别人想知道的答案。
扫描二维码下载
×

类别

我们会通过消息、邮箱等方式尽快将举报结果通知您。

说明

0/200

提交
取消

辅 助

模 式