【问题标题】:Ensure data can only be changed by its actual owner in a database确保数据只能由数据库中的实际所有者更改
【发布时间】:2018-08-18 14:18:45
【问题描述】:

背景

我们正在构建一个新项目,目前正在 在数据库设计中。我们 偶然发现了一个问题 我们无法解决,我们相信我们 有一些解决方案,但我们不确定。 这个问题似乎有点不可搜索, 可能是因为我们还不够了解 这个话题的关键词。

问题

在我们的例子中,我们正在构建一个 rest-api 用户使用令牌进行身份验证的地方 对端点进行 CRUD 操作。

没关系,您需要提供一个 访问或修改资源的有效令牌。 标准的东西。

但是,经过身份验证不会阻止您修改行 那不属于你。

因此,一个用户可能会更改其他用户的数据, 因为没有处理这个的逻辑。 如果表彼此相距很远,则不能依赖外键或主键约束 - 除非参见解决方案 2。

解决方案 1

向每个表添加一个字段,该字段要么只是一个值持有者,要么是一个实际的 fk。 在我们的例子中,该字段引用“所有者”或用户的主键。

解决方案 2

接受性能冲击并实际遍历 一路回溯到“所有者” 对象/行。

解决方案 3

实施 RLS(行级安全)解决方案,但 这似乎不是 RLS 的用例,或者至少感觉不是 对于我们的用例来说有点高级。

问题

所以问题是在解决问题的同时什么是最高效的 安全问题?还有其他解决方案吗?

解决方案 2 示例:

表格

user
    id - pk
    … 

company 
    id - pk
    … 
    user_id - fk 

note
    id - pk
    … 
    user_id

会话

user_session
    user_id
    … 

数据用户可以更改:

SELECT
    *
FROM
    note
WHERE
    user_id = :session.user_id

当用户想要更新数据时:

UPDATE note
SET text = “foobar”
WHERE user_id = :session.user_id AND id=payload.id

如果存在对应的 user_id 行 给请求的用户,如果提供的笔记的主键 存在。

参考文献

【问题讨论】:

    标签: sql database postgresql security database-design


    【解决方案1】:

    首先,您需要确定租户策略(“多租户”是您的关键字)。您可以将用户的数据放在不同的集群、数据库、模式或行中

    Tenant-per-database 是我的首选解决方案

    似乎不是 RLS 的用例

    这绝对是 RLS 的一个用例

    您需要在每个“安全”表中都有一个“owner_id”列。确保 current_user 是该所有者。如果 owner_id 发生变化,级联外键以更新它

    您可以使用 WITH CHECK OPTION 视图代替 RLS,但 RLS 仍然更简单

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-07-18
      • 1970-01-01
      • 1970-01-01
      • 2011-05-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多