【问题标题】:How can I set a limitation for one column on all SQL selects?如何为所有 SQL 选择的一列设置限制?
【发布时间】:2015-10-06 21:15:52
【问题描述】:

我们有一个为众多客户保存数据的数据库。我们想让客户访问数据库,但只能访问属于他们的数据。解析选择然后插入 where 子句“and Company.Name = 'Acme'” 让我觉得很弱,因为 SQL 选择可能非常复杂,并且处理 100% 的所有情况可能很困难。

有什么方法可以做相当于(我知道这不是有效的 SQL):

select * from * where Company.Name = 'Acme' and (passed_in_select)

您可以将完整选择嵌套在大选择的内部。有没有办法做到以上几点?这种方式是对选择的一个非常简单的限制,并且可能 100% 的时间都有效。

【问题讨论】:

  • 您是真的希望客户访问您的数据库服务器,还是希望他们通过网站或应用程序访问数据?
  • 什么数据库系统?
  • @zedfoxus 它将始终通过我们的报告系统,因此通过可以在传入选择时更改选择的应用程序。
  • @PavelGatnar - 任何 SQL 数据库。
  • 在我的帖子中添加了 WITH 子句解决方案

标签: sql select


【解决方案1】:

这里有一个名为“虚拟私有数据库”的Oracle数据库系统解决方案:
https://docs.oracle.com/cd/B28359_01/network.111/b28531/vpd.htm

其他数据库看看有没有类似的内置解决方案。

但是使用 WITH 子句有一个非常简单的解决方案:

WITH
  tab_a__ AS (SELECT * FROM tab_a WHERE comp="xy"),
  tab_b__ AS (SELECT * FROM tab_b WHERE comp="xy")
SELECT ... //original select

你只需要在select中找到所有使用过的表,在后面添加__并将CTEs添加到WITH子句中。
注意:有些数据库不支持 WITH 子句,尽管它是 SQL 标准。某些数据库可能有别名长度限制,您可以通过添加后缀来超出。

【讨论】:

  • 这看起来非常适合 Oracle。对于其他人,我们必须自己做同样的事情。谢谢
【解决方案2】:
select * from
(
  select * from table_a
) outer_table_a
where outer_table_a.col_a = 'test'

我经常做这种事情,特别是当我想对内部查询中的数据(总和、最大值等)执行一些聚合时。我用 SQL Server 做这个,我不知道它是否适用于其他DBMS,但如果不是,我会感到惊讶。

我不知道我是否会依靠这种方法来有效地授予权限。也许视图会让你把事情锁定得更紧一点。听起来您打算将某些内容动态添加到您可能没有编写的查询中?在这种情况下,编写该查询的人可能会改变您感兴趣的列,这将导致您不想要的东西的可见性,例如:

select * from
(
  select 'test' as col_a, launch_codes from table_a
) outer_table_a
where outer_table_a.col_a = 'test'

【讨论】:

  • 我不能使用“where real_table_name.col_a = 'test'”来避免您列出的重命名问题吗?
猜你喜欢
  • 2013-01-01
  • 2019-08-08
  • 1970-01-01
  • 1970-01-01
  • 2019-09-05
  • 1970-01-01
  • 2014-08-24
  • 2013-04-11
  • 1970-01-01
相关资源
最近更新 更多