sql >> Databáze >  >> RDS >> Oracle

Oracle:Je možné vytvořit roli ve spouštěči?

Nemůžeme nativně spustit DDL v žádné formě PL/SQL. včetně spouštěčů. K tomu potřebujeme použít dynamické SQL.

Spouštěče mají další vrásku:jsou spouštěny jako součást transakce a mají omezení, které nám zakazuje vydat potvrzení v jejich těle. V Oracle každý příkaz DDL vydá dvě potvrzení, jedno před a jedno po provedení příkazu DDL. Abychom mohli spustit DDL ve spouštěči, musíme použít autonomous_transaction pragma , což znamená, že DDL běží v samostatné, vnořené transakci.

create or replace TRIGGER TestTrigger
    BEFORE INSERT ON TestTable
    REFERENCING OLD AS OLD NEW AS NEW 
FOR EACH ROW 
declare
    pragma autonomous_transaction;
BEGIN 
    execute immediate 'create role '|| :New.RoleName;
END;

Autonomní transakce jsou jedním z těch konstrukcí, které lze snadno zneužít a sabotovat naše vlastní aplikace. Ve vašem scénáři je zádrhel v tom, že CREATE ROLE může uspět ve své transakční bublině, zatímco INSERTT do TestTable selže; takový je význam „autonomní transakce“. Stále tedy nemáte zaručeno „soudržnost mezi [vaší] tabulkou a rolemi orákula jedna“.

Lepším řešením by bylo zabalit oba příkazy do procedurálního volání, než se pokoušet oklamat DML, aby udělal něco, co dělat nemá.

create or replace procedure create_role
     ( p_role_name in user_roles.role%type
       , p_desc in testtable.description%type )
is
    pragma autonomous_transaction;
begin 
    insert into testtable
        ( id, creationdate, rolename, description) 
    values
        ( some_seq.nextval, sysdate, p_role_name, p_desc );
    execute immediate 'create role '|| p_role_name;
end; 



  1. Vytvořte xml kořenový element pro clob, který nemá kořenový element v Oracle

  2. Nebyl nalezen žádný vhodný ovladač pro jdbc:mysql/localhost:3306/world

  3. Oprava chyby 1064 SQL při importu databáze do Wampserveru

  4. jak uniknout oddělovači z obsahu sloupce při exportu csv