数据库设置:我正在使用连接到 SQL Server 后端的 MS Access 前端。出于安全目的,前端(用户 =MyDbsFront - 名称已更改)使用的对象(视图和存储过程)具有与数据库所有者 (schema1) 不同的架构 (schema2),存放数据表。通过视图或存储过程(通过所有权链)有选择地向MyDbsFront提供数据访问。
其中一个表 (schema1.MyTable) 有一个触发器集,当行中的值发生更改时,该触发器会更新 Updated 和 UpdatedByUserId 列中的日期。我将此功能放在后端,因为我有时手动上传数据(通过 SSMS),并且我想确保这些列正确更新,无论表更新的方式如何。前端无法直接编辑这两列。
自动填充过程:最近,我创建了一个存储过程(schema1.AutoUpdate),它自动填充一些列。当使用该过程修改一行时,我想将代表“Auto”的 ID 而不是当前用户的 ID 插入到 UpdatedByUserId 列中。为了防止更新触发器恢复此更改,我包含一个 ALTER 语句来暂时禁用触发器,然后在更改完成后重新启用它。
问题:。当从后端执行时,该过程运行良好。但是,当我尝试从前端执行触发器时,出现权限错误(“找不到该对象,因为它不存在或没有权限...”)。我已将问题范围缩小到与 ALTER 语句相关的权限问题,如果我向 schema1.MyTable 上的 MyDbsFront 用户授予 ALTER 权限,则一切正常。但是,我不想无限期地向前端授予 ALTER 权限,因为这会带来安全责任。
问题: 有没有办法从数据库前端执行包含 ALTER 语句的存储过程而不授予它 ALTER 权限?
我尝试使用过程中的代码临时授予更改权限并撤销它,但它失败了,因为您无法向数据库所有者或您自己授予权限。
将存储过程配置为“EXECUTE AS OWNER”。 默认为“EXECUTE AS CALLER”,调用者没有禁用触发器的权限。
EG
create or alter procedure usp_foo
with execute as owner
as
begin
set xact_abort on;
begin transaction;
disable trigger tg_tt on tt;
insert into TT(UpdatedBy) values ('Auto');
enable trigger tg_tt on tt;
commit transaction;
end