首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >实体框架深度查询多对多

实体框架深度查询多对多
EN

Stack Overflow用户
提问于 2012-11-20 07:22:51
回答 2查看 262关注 0票数 0

Entity Framework新手,试着弄清楚一些东西。我有下面列出的表格:

代码语言:javascript
运行
复制
Users
---------
UserID
UserName

Roles
---------
RoleID
RoleName

UserRoles
---------
UserRoleID
UserID
RoleID

我使用的是存储库模式。下面是一个存储库的示例(它们本质上都是相同的)

代码语言:javascript
运行
复制
public class RoleRepository : IRoleRepository
{
    private AuthorizationContext context = new AuthorizationContext();
    public IQueryable<Role> Roles
    {
        get
        {
            return this.context.Roles;
        }
    }
    public bool Save(Role pRole)
    {
        if (pRole.RoleID == 0 || pRole.RoleID == null)
        {
            context.Roles.Add(pRole);
        }
        context.SaveChanges();
        return true;
    }
    public bool Delete(Role pRole)
    {
        context.Roles.Remove(pRole);
        context.SaveChanges();
        return true;
    }
}

现在,我想测试一个用户(通过UserName)是否属于一个角色(通过RoleName)。如何查询?我希望它是这样的,但它不起作用:

代码语言:javascript
运行
复制
public bool IsUserInRole(string username, string roleName)
{
    var repo = new UserRepository();
    var user = repo.Users.FirstOrDefault(u => u.NetID == username && u.UserRoles.FirstOrDefault(r => r.Role.Name == roleName));
}

如何查询该用户是否属于该角色?如果可能的话,我更喜欢使用谓词。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-11-20 08:22:39

我将像这样使用.Any函数:

代码语言:javascript
运行
复制
public static bool IsUserInRole(string username, string roleName)
{
  using(var roleRepository = new RoleRepository())
  {
    return roleRepository.Roles.Any(r => r.RoleName == roleName && r.UserRoles.Any(ur => ur.User.UserName == username));
  }
}

下面是一个控制台应用程序示例:

代码语言:javascript
运行
复制
class Program
{
  static void Main(string[] args)
  {
    var users = new List<string> { "A", "B", "C", "D" };
    var roles = new List<string> { "User", "Admin", "Superuser"};

    //User A has roles: User, Admin, Superuser
    Debug.Assert(IsUserInRole(users[0], roles[0]) == true);
    Debug.Assert(IsUserInRole(users[0], roles[1]) == true);
    Debug.Assert(IsUserInRole(users[0], roles[2]) == true);

    //User B has roles: User, Admin
    Debug.Assert(IsUserInRole(users[1], roles[0]) == true);
    Debug.Assert(IsUserInRole(users[1], roles[1]) == true);
    Debug.Assert(IsUserInRole(users[1], roles[2]) == false);

    //User C has roles: User
    Debug.Assert(IsUserInRole(users[2], roles[0]) == true);
    Debug.Assert(IsUserInRole(users[2], roles[1]) == false);
    Debug.Assert(IsUserInRole(users[2], roles[2]) == false);

    //User D has no roles
    Debug.Assert(IsUserInRole(users[3], roles[0]) == false);
    Debug.Assert(IsUserInRole(users[3], roles[1]) == false);
    Debug.Assert(IsUserInRole(users[3], roles[2]) == false);

    Debugger.Break();
  }

  public static bool IsUserInRole(string username, string roleName)
  {
    using(var roleRepository = new RoleRepository())
    {
      return roleRepository.Roles.Any(r => r.RoleName == roleName && r.UserRoles.Any(ur => ur.User.UserName == username));
    }
  }
}

public interface IRoleRepository : IDisposable
{

}

public class RoleRepository : IRoleRepository
{
  private Context context = new Context();
  public IQueryable<Role> Roles
  {
    get
    {
      return this.context.Roles.AsQueryable<Role>();
    }
  }

  public void Dispose()
  {
      //Do nothing
  }
}

public class Context : IDisposable
{
  public IList<User> Users { get; set; }
  public IList<Role> Roles { get; set; }
  public IList<UserRole> UserRoles { get; set; }

  public Context()
  {
    //Generate Some Fake Data
    Users = new List<User>();
    Users.Add(new User { UserID = 1, UserName = "A" });
    Users.Add(new User { UserID = 2, UserName = "B" });
    Users.Add(new User { UserID = 3, UserName = "C" });
    Users.Add(new User { UserID = 4, UserName = "D" });

    Roles = new List<Role>();
    Roles.Add(new Role { RoleID = 1, RoleName = "User" });
    Roles.Add(new Role { RoleID = 2, RoleName = "Admin" });
    Roles.Add(new Role { RoleID = 3, RoleName = "Superuser" });

    UserRoles = new List<UserRole>();
    UserRoles.Add(new UserRole(1, Users[0], Roles[0]));
    UserRoles.Add(new UserRole(1, Users[0], Roles[1]));
    UserRoles.Add(new UserRole(1, Users[0], Roles[2]));
    UserRoles.Add(new UserRole(1, Users[1], Roles[0]));
    UserRoles.Add(new UserRole(1, Users[1], Roles[1]));
    UserRoles.Add(new UserRole(1, Users[2], Roles[0]));

    //User A has roles: User, Admin, Superuser
    //User B has roles: User, Admin
    //User C has roles: User
    //User D has no roles
  }

  public void Dispose()
  {
    //Do nothing
  }
}

public class User
{
  public int UserID { get; set; }
  public string UserName { get; set; }

  public IList<UserRole> UserRoles { get; set; }

  public User()
  {
    UserRoles = new List<UserRole>();
  }
}

public class Role
{
  public int RoleID { get; set; }
  public string RoleName { get; set; }

  public IList<UserRole> UserRoles { get; set; }

  public Role()
  {
    UserRoles = new List<UserRole>();
  }
}

public class UserRole
{
  public int UserRoleID { get; set; }

  public int UserId { get; set; }
  public User User { get; set; }

  public int RoleId { get; set; }
  public Role Role { get; set; }

  public UserRole(int id, User user, Role role)
  {
    UserRoleID = id;

    UserId = user.UserID;
    User = user;
    user.UserRoles.Add(this);

    RoleId = role.RoleID;
    Role = role;
    role.UserRoles.Add(this);
  }
}
票数 1
EN

Stack Overflow用户

发布于 2012-11-20 08:43:05

下面是您已经创建的修改后的IsUserInRole接口:

代码语言:javascript
运行
复制
    public bool IsUserInRole(string username, string roleName)
    {
        var repo = new UserRepository();
        return repo.Users.Any(u => u.UserName == username && u.UserRoles.Any(userrole => userrole.Role.RoleName == roleName));
    }

您的应用程序接口的问题在于FirstOrDefault,它限制了导航属性。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/13464209

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档