传统观点认为安全应用程序应该为插入,更新和删除操作创建存储过程。您还将使用存储过程,因此您不必使用触发器,从而避免触发器的一些常见陷阱。
另一个想法是用视图覆盖整个数据库 - 所以几乎没有人可以自己访问表,他们只是对视图进行CRUD操作。这样,如果您想要授予某人访问某些列的权限,您可以为包含这些列的人创建一个视图,或者仅为计算创建一个视图。如果你需要在更新&删除操作(即防止某人影响表中总行数的2%以上),您可以通过instead of
触发器执行此操作。
为了不陷入触发器的常见陷阱,(1)触发器应该只更新表,而不是其他视图。 (2)触发器永远不会放在桌子上。 (3)视图无法访问其他视图。 (4)如果由于某种原因你不能按照前三条规则做你想做的事,那就创建一个存储过程。
我通过这种方式实现安全性所看到的好处是你只需要创建一个视图和一些触发器(平均情况 - 另外两个对象),而如果你去存储过程路径,你将始终创建至少3或4个附加对象(取决于您是否为select创建过程)。此外,我们的NHibernate映射会更简单,因为我们不必为每个对象映射三个过程。
问题是使用大多数视图和触发器而不是存储过程是否存在重大安全漏洞或实际问题。
答案 0 :(得分:1)
使用触发器和视图时,Ther并无本质上的错误。与其他代码一样,它们必须正确编写并且通常遭受不良声誉,因为许多可怜的开发人员为他们编写了错误的代码。例如,您不希望视图调用其他视图,因为性能会受到影响。您不希望触发器假定在更新/删除/插入中只影响一行。
答案 1 :(得分:1)
我个人倾向于使用存储过程来访问数据库。我通常使用一组通用的过程来管理每个表的操作并确保数据的完整性。关于谁可以查看或编辑给定信息的所有决定都在应用程序本身中处理。只有应用程序凭据才能访问数据库,任何碰巧在那里找到路径的用户都被锁定,或者最多只能访问该数据库。
我倾向于不喜欢实现业务逻辑的触发器,因为在尝试调试某些东西时很容易错过。如果我的所有插入逻辑都包含在SP中,我可以拉出该SP并跟踪它以诊断插入失败的原因。如果桌子上还有一个我忘记或不知道的触发器,可能需要一段时间才能实现它,并记得在那里看看。 (虽然这可能只是我环境的一个因素,如果在这里使用更多的触发器,我相信它们在我的思维过程中会更加突出)
但我并不完全确定我们是从同一个角度看待这个问题。如果您要为每组用户创建不同的视图,那么听起来他们可以直接访问数据存储并且无法通过应用程序界面工作?如果有这个结构的应用程序接口,那么为了使用正确的视图,是否必须为每组用户更新和重新编译它?
我想我说存储过程适用于支持应用程序接口或预构建报告,但是当用户对没有应用程序接口的公共数据存储具有读/写访问权限时,视图和触发器可能是更好的选择。中间。
我还要指出,您的商店标准是什么的考虑因素。如果那里的其他人都只使用存储过程,而你采取了另一种方法,那么其他任何试图以后出现并维护你的解决方案的人将会遇到困难。
最后,如果它完成了工作而没有维持或引起其他问题的痛苦,那么这是一个很好的解决方案。