将权限信息存储在数据库中,支持动态调整。根据用户所属的角色、特定的功能模块,动态加载权限"
1. 数据库设计
根据这种需求,可以通过以下表设计:
- 用户表 (Users):存储用户信息。
- 角色表 (Roles):存储角色信息。
- 模块表 (Modules):存储系统的功能模块。
- 权限表 (Permissions):存储权限信息。
- 用户角色表 (UserRoles):存储用户和角色的关系,一个用户对应一个角色。
- 角色权限表 (RolePermissions):存储角色与权限的关系,允许不同用户的权限定制。
- 用户权限表 (UserPermissions):为每个用户定制权限(可覆盖角色权限)。
表结构
sql
-- 用户表
CREATE TABLE Users (
UserId INT PRIMARY KEY,
UserName VARCHAR(100)
);
-- 角色表
CREATE TABLE Roles (
RoleId INT PRIMARY KEY,
RoleName VARCHAR(100)
);
-- 模块表
CREATE TABLE Modules (
ModuleId INT PRIMARY KEY,
ModuleName VARCHAR(100)
);
-- 权限表
CREATE TABLE Permissions (
PermissionId INT PRIMARY KEY,
PermissionName VARCHAR(100)
);
-- 用户角色表:每个用户对应一个角色
CREATE TABLE UserRoles (
UserId INT,
RoleId INT,
FOREIGN KEY (UserId) REFERENCES Users(UserId),
FOREIGN KEY (RoleId) REFERENCES Roles(RoleId)
);
-- 角色权限表:角色与权限的关系,一个角色可以有多个权限
CREATE TABLE RolePermissions (
RoleId INT,
PermissionId INT,
ModuleId INT,
FOREIGN KEY (RoleId) REFERENCES Roles(RoleId),
FOREIGN KEY (PermissionId) REFERENCES Permissions(PermissionId),
FOREIGN KEY (ModuleId) REFERENCES Modules(ModuleId)
);
-- 用户权限表:为用户定制权限,覆盖角色权限
CREATE TABLE UserPermissions (
UserId INT,
PermissionId INT,
ModuleId INT,
FOREIGN KEY (UserId) REFERENCES Users(UserId),
FOREIGN KEY (PermissionId) REFERENCES Permissions(PermissionId),
FOREIGN KEY (ModuleId) REFERENCES Modules(ModuleId)
);
2. 权限加载逻辑
- 用户角色 :每个用户通过
UserRoles
表与一个角色关联。 - 角色权限 :通过
RolePermissions
表为角色分配权限。 - 用户权限 :通过
UserPermissions
表为用户定制权限,覆盖角色的默认权限。
3. 权限查询
- 查询用户权限 :首先通过
UserRoles
获取该用户的角色,再通过RolePermissions
查询该角色的权限。然后,如果该用户有自定义权限,可以通过UserPermissions
覆盖角色权限。
查询用户权限的顺序
- 查询用户所属角色。
- 查询该角色的权限。
- 查询该用户是否有自定义权限。
示例查询
sql
-- 查询用户的角色
SELECT r.RoleId, r.RoleName
FROM Users u
JOIN UserRoles ur ON u.UserId = ur.UserId
JOIN Roles r ON ur.RoleId = r.RoleId
WHERE u.UserId = @UserId;
-- 查询角色的权限
SELECT p.PermissionName
FROM RolePermissions rp
JOIN Permissions p ON rp.PermissionId = p.PermissionId
WHERE rp.RoleId = @RoleId AND rp.ModuleId = @ModuleId;
-- 查询用户的自定义权限(如果有)
SELECT p.PermissionName
FROM UserPermissions up
JOIN Permissions p ON up.PermissionId = p.PermissionId
WHERE up.UserId = @UserId AND up.ModuleId = @ModuleId;
4. C# 代码实现
获取用户权限
csharp
public class PermissionService
{
private string connectionString = "your_connection_string";
// 获取用户权限
public List<string> GetPermissionsByUserId(int userId, int moduleId)
{
List<string> permissions = new List<string>();
using (SqlConnection connection = new SqlConnection(connectionString))
{
connection.Open();
// 获取用户角色
string roleQuery = @"
SELECT r.RoleId
FROM Users u
JOIN UserRoles ur ON u.UserId = ur.UserId
JOIN Roles r ON ur.RoleId = r.RoleId
WHERE u.UserId = @UserId";
SqlCommand roleCommand = new SqlCommand(roleQuery, connection);
roleCommand.Parameters.AddWithValue("@UserId", userId);
int roleId = (int)roleCommand.ExecuteScalar();
// 获取角色权限
string rolePermissionQuery = @"
SELECT p.PermissionName
FROM RolePermissions rp
JOIN Permissions p ON rp.PermissionId = p.PermissionId
WHERE rp.RoleId = @RoleId AND rp.ModuleId = @ModuleId";
SqlCommand rolePermissionCommand = new SqlCommand(rolePermissionQuery, connection);
rolePermissionCommand.Parameters.AddWithValue("@RoleId", roleId);
rolePermissionCommand.Parameters.AddWithValue("@ModuleId", moduleId);
SqlDataReader reader = rolePermissionCommand.ExecuteReader();
while (reader.Read())
{
permissions.Add(reader.GetString(0)); // 角色权限
}
reader.Close();
// 获取用户自定义权限(如果有)
string userPermissionQuery = @"
SELECT p.PermissionName
FROM UserPermissions up
JOIN Permissions p ON up.PermissionId = p.PermissionId
WHERE up.UserId = @UserId AND up.ModuleId = @ModuleId";
SqlCommand userPermissionCommand = new SqlCommand(userPermissionQuery, connection);
userPermissionCommand.Parameters.AddWithValue("@UserId", userId);
userPermissionCommand.Parameters.AddWithValue("@ModuleId", moduleId);
SqlDataReader userReader = userPermissionCommand.ExecuteReader();
while (userReader.Read())
{
permissions.Add(userReader.GetString(0)); // 用户自定义权限
}
}
return permissions;
}
}
public class AccessControlService
{
private PermissionService permissionService = new PermissionService();
// 检查用户是否有权限
public bool CanAccessModule(int userId, int moduleId, string requiredPermission)
{
List<string> permissions = permissionService.GetPermissionsByUserId(userId, moduleId);
return permissions.Contains(requiredPermission); // 判断用户是否拥有特定权限
}
}
5. 总结
- 用户与角色的关系:一个用户对应一个角色,多个用户可以对应相同角色。
- 角色与权限的关系 :角色通过
RolePermissions
表分配权限,一个角色可以对应多个权限。 - 用户自定义权限 :通过
UserPermissions
表为用户定制权限,覆盖角色的默认权限。 - 灵活的权限控制:用户的权限不仅继承自角色,还可以根据需要定制,确保权限控制的灵活性。