首页 文章

编辑更新其他用户表的程序包的权限不足

提问于
浏览
0

我在USER A中有一个对象,用于更新USER B模式中的表 . 运行程序包时,它将使用USER B的登录名在Oracle中运行 .

USER A没有权限更新USER B模式中的表 . 当我尝试在USER A的模式中编译包时,我得到的权限不足错误消息会阻止它编译 .

有没有办法在USER A的模式中编译对象,即使他没有更新USER B表的权限?如果包在USER B的上下文中运行,包是否会正确更新表?

我不想将包放在USER B的架构中 .

1 回答

  • 2

    您可以 . 但它是's probably not the best approach. The package would need to be declared as an invoker'的权利包 . 并且 UPDATE 语句需要使用动态SQL .

    B 中创建表

    SQL> create table b.foo( col1 number );
    
    Table created.
    
    SQL> insert into b.foo values( 1 );
    
    1 row created.
    
    SQL> commit;
    
    Commit complete.
    

    A 中创建包 . 请注意,该包声明为 authid current_user ,这意味着它依赖于调用用户的特权而不是定义用户的特权 . 由于 A 无法查看表,因此我们使用动态SQL,以便将语法检查推迟到运行时

    SQL> create package update_foo
      2    authid current_user
      3  as
      4    procedure set_val( p_new_val in number );
      5  end;
      6  /
    
    Package created.
    
    SQL> ed
    Wrote file afiedt.buf
    
      1  create or replace package body update_foo
      2  as
      3    procedure set_val( p_new_val in number )
      4    as
      5    begin
      6      execute immediate 'update b.foo set col1 = :new_val'
      7        using p_new_val;
      8    end;
      9* end;
    SQL> /
    
    Package body created.
    
    SQL> grant execute on update_foo to b;
    
    Grant succeeded.
    

    现在, B 可以执行包并修改数据

    SQL> exec a.update_foo.set_val( 2 );
    
    PL/SQL procedure successfully completed.
    
    SQL> select * from foo;
    
          COL1
    ----------
             2
    

    然而,一般而言,这不是一种特别明智的方法 . 一般而言,在一个模式中使用代码而在另一个模式中使用对象的关键在于提供职责分离和职责分离 . 如果您必须以无论如何都可以针对该表发出 UPDATE 的用户身份登录,那么使用包来执行此操作并不会增加复杂性 .

相关问题