sql - PostgreSQL中如何实现业务逻辑权限?

标签 sql postgresql permissions

假设我有一个项目表:

CREATE TABLE items
(
    item serial PRIMARY KEY,
    ...
);

现在我想为每个项目介绍“权限”的概念(注意,我在这里不是谈论数据库访问权限,而是针对该项目的业务逻辑权限)。每个项目都有默认权限,也有可能覆盖默认权限的每用户权限。

我试图想办法实现这一点,并提出了以下解决方案:

1) bool 解

为每个权限使用一个 bool 列:

CREATE TABLE items
(
    item serial PRIMARY KEY,

    can_change_description boolean NOT NULL,
    can_change_price boolean NOT NULL,
    can_delete_item_from_store boolean NOT NULL,
    ...
);

CREATE TABLE item_per_user_permissions
(
    item int NOT NULL REFERENCES items(item),
    user int NOT NULL REFERENCES users(user),

    PRIMARY KEY(item, user),

    can_change_description boolean NOT NULL,
    can_change_price boolean NOT NULL,
    can_delete_item_from_store boolean NOT NULL,
    ...
);

优点:每个权限都有名称。

缺点:有几十个权限,显着增加了列数,您必须定义它们两次(每个表一次)。

2) 整数解

使用整数并将其视为位域(即位 0 用于can_change_description,位 1 用于can_change_price,依此类推,并使用位运算来设置或读取权限)。

CREATE DOMAIN permissions AS integer;

优点:非常快。

缺点:您必须在数据库和前端界面中跟踪哪个位代表哪个权限。

3) 位域解决方案

与 2) 相同,但使用 bit(n)。很可能优点和缺点相同,也许速度稍慢。

4) 枚举解决方案

为权限使用枚举类型:

CREATE TYPE permission AS ENUM ('can_change_description', 'can_change_price', .....);

然后为默认权限创建一个额外的表:

CREATE TABLE item_default_permissions
(
    item int NOT NULL REFERENCES items(item),
    perm permission NOT NULL,

    PRIMARY KEY(item, perm)
);

并将每个用户定义表更改为:

CREATE TABLE item_per_user_permissions
(
    item int NOT NULL REFERENCES items(item),
    user int NOT NULL REFERENCES users(user),
    perm permission NOT NULL,

    PRIMARY KEY(item, user, perm)    
);

优点:易于命名个人权限(您不必处理位位置)。

缺点:即使只是检索默认权限,也需要访问两个额外的表:首先是默认权限表,其次是存储枚举值的系统目录。

特别是因为必须为该项目的每个页面 View 检索默认权限,所以最后一个替代方案的性能影响可能很重要。

你能想到其他替代方案吗?

应该采用哪种方法?

请注意:这个问题已经reposted on DBA .

最佳答案

这真的取决于您需要达到什么级别才能获得权限

基于角色 - 不是用户

基于用户 - (更难维护)

或两者的结合

用户和角色...

我们系统上的以下内容 用户表 -> 包含用户名等

角色 => 办公室支持、技工等角色列表

安全级别 -> 级别列表,例如只读,管理员

应用程序函数表 -> 包含可以应用权限的函数,例如可以_编辑_用户

应用程序安全表 -> 用户名 + 应用程序功能 ID、角色和是/否权限的任一位 - 或使用安全级别的更复杂角色级别的整数。

这提供了最大的灵 active ,但可能难以为其构建 UI。

在应用程序中我们获得了一次用户权限,并做了一个函数来检查他们是否有权限

例如CurrentUser.HasPermissions("Can_Edit_Users")

public bool HasPermissions(string Permission)
{
return this.Permissions.Any(p=>p.FunctionName==Permission && IsAllowed==true);
}

关于sql - PostgreSQL中如何实现业务逻辑权限?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22743125/

相关文章:

mysql - 使用 Inert 语句中的 Select 将字符串常量插入表中

java - 插入从选择查询中检索的 MySQL 结果集?

postgresql - 无法将 PostgreSQL 作为 Windows 服务运行

PHP 无法使用 mkdir 创建目录

sql - 根据计算值选择,优化

java - 尝试在 Java 应用程序中执行更多 MySql 查询时出现错误 S1000

postgresql - 将字符串转换为列名

Ruby -> PostgreSQL 连接 pg_hba.conf 设置为 "ident sameuser"而不是 "trust"

linux - 在 ubuntu 机器上需要 "ls -al/"的结果(最好是 10.4)

nginx - Nginx的 Alpine docker 失败,没有以前的ls?