简体   繁体   English

使用EF在MVC4中实现公司,部门,部门用户访问控制

[英]Implementing Company, Division, Department User Access Control in MVC4 with EF

This is my first question on stackoverflow, so please be gentle. 这是我关于stackoverflow的第一个问题,所以请保持温和。 I am writing a customer portal to a warehouse application using MVC4, Entity Framework and SimpleMembership. 我正在使用MVC4,Entity Framework和SimpleMembership为仓库应用程序编写客户门户。 The warehouse hosts contents for multiple companies. 仓库托管多家公司的内容。 Each company has divisions and departments. 每个公司都有部门和部门。 The users will have varying access to the information for their company, divisions, and departments. 用户将拥有对其公司,部门和部门的信息的不同访问权限。 I am looking for an elegant solution for access control. 我正在寻找一种优雅的访问控制解决方案。 So far, my model looks like this: 到目前为止,我的模型看起来像这样:

public class UserProfile
{
    UserProfile()
    {
        this.AccessControl = new HashSet<AccessControl>();
    }

    [Key]
    [DatabaseGeneratedAttribute(DatabaseGeneratedOption.Identity)]
    public int UserId { get; set; }
    public string UserName { get; set; }
    public Nullable<int> CompanyId { get; set; }
    public virtual ICollection<AccessControl> { get; set; }
    public virtual Company Company { get; set; }
}

public class AccessControl
{
    public int AccessControlId { get; set; }
    public int UserId { get; set; }
    public int CompanyId { get; set; }
    public Nullable<int> DivisionId { get; set; }
    public Nullable<int> DepartmentId { get; set; }
    public Boolean ReadAccess { get; set; }
    public Boolean WriteAccess { get; set; }

    // other properties for access control

    public virtual UserProfile UserProfile { get; set; }
    public virtual Company Company { get; set; }
    public virtual Division Division { get; set; }
    public virtual Department Department { get; set; }
}

public class Content
{
    public int ContentId { get; set; }
    public int CompanyId { get; set; }
    public int DivisionId { get; set; }
    public int DepartmentId { get; set; }

    // Various other properties

    public virtual Company Company { get; set; }
    public virtual Division Division { get; set; }
    public virtual Department { get; set; }
}

My thought was that a NULL Division means all divisions and a NULL Department means all departments. 我的想法是NULL分区意味着所有分区而NULL分区意味着所有分区。 My questions are: 我的问题是:

  1. What is an elegant way to write the repository method to retrieve a list of Content objects for a user based on their access control list as well as populating division and department select lists in CRUD views? 编写存储库方法以根据用户的访问控制列表检索内容对象列表以及在CRUD视图中填充部门和部门选择列表的优雅方法是什么?
  2. Is there a better way to model this access control list? 有没有更好的方法来建模这个访问控制列表?

I don't think this addresses all of your questions yet, but I think a repository that looks something like this: 我认为这还没有解决您的所有问题,但我认为存储库看起来像这样:

public class accessRepository
{
    accessContext context = new accessContext();

    public IQueryable<Content> GetAccessibleContentFor(int userId)
    {
        var up = context.UserProfiles.Single(u => u.UserId == userId);
        var companyId = up.CompanyId;

        return from c in context.Content 
               where c.CompanyId == companyId 
               && (up.AccessControl.Any(
                    a=> 
                        a.CompanyId == c.CompanyId && 
                        a.DivisionId == c.DivisionId && 
                        a.DepartmentId == c.DepartmentId) 
               || up.AccessControl.Any(
                    a=>a.CompanyId == c.CompanyId && 
                        a.DivisionId == c.DivisionId && 
                        a.DepartmentId == null)
               || up.AccessControl.Any(
                    a=>
                        a.CompanyId == c.CompanyId && 
                        a.DivisionId == null)
               select c;
    }
}

would allow you get back the content that is accessible if: 允许您在以下情况下获取可访问的内容:

  1. The content belongs to the user's Company. 内容属于用户的公司。
  2. The user Can access content for the Company, Division, and Department 用户可以访问公司,部门和部门的内容
  3. Or the user can access content for the Company and Division (all Departments) 或者用户可以访问公司和部门(所有部门)的内容
  4. Or the user can access content for the Company (all divisions) [ all departments, is assumed in this case.] 或者用户可以访问公司(所有部门)的内容[在这种情况下假定所有部门。]

You should look into a policy- and attribute-based solution that's independent of your app where you can write authorization policies eg 您应该查看基于策略和属性的解决方案,该解决方案独立于您的应用程序,您可以在其中编写授权策略,例如

a user can access content in the warehouse if the content.department==user.department && content.company==user.company. 如果content.department == user.department && content.company == user.company,则用户可以访问仓库中的内容。

XACML sounds like the perfect model. XACML听起来就像是完美的模型。 I wrote this demo where I do access control on purchase orders based on the purchaser, the amount, the location and the status of the PO. 我写了这个演示,我根据购买者,数量,位置和PO的状态对采购订单进行访问控制。 I don't need to change the app code because I use XACML externally. 我不需要更改应用程序代码,因为我在外部使用XACML。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM