Situationen er den at vi fra tid til anden, støder ind i et projekt - der typisk har en applikation i den anden ende, big surprise. Denne kan f.eks bl.a. liste brugere i en Oracle database. De har så typisk haft lov til at de kan markerer brugeren, og trykke på en knap. Bagved dannes så et statement som ALTER SYSTEM KILL SESSION 'sid, serial#'. Hvad er problemmet egentlig så her ? ALTER SYSTEM priv er da bedre end at grante DBA rollen, kan man jo agumentere - hvilket jeg er enig i. Ligeledes sker det jo kontrolleret gennem applikationen, og man kunne fortsætte med de gode argumenter.
Personligt har jeg mange erfaringer for at får udviklere et priv som f.eks ALTER SYSTEM, sker der ofte det, at de på et eller andet tidspunkt udnytter det, og så kan det være farligt, og tidskrævende at rette op på.
Derfor foretrækker jeg personligt, at skal applikationer have ALTER SYSTEM, sker det gennem en procedure som f.eks her.
[workday:XO:/home/oracle/kbirch] sqlplus / as sysdba
SQL> grant alter system to system;
SQL> connect system
SQL> CREATE OR REPLACE procedure kill_session(i_sid in number default 0, i_serial in number default 0) as
v_username v$session.USERNAME%TYPE;
v_systembruger number;
begin
-- Kontroller for kombinationen SID/SERIAL og om den er killed i forvejen
begin
SELECT username
into v_username
FROM v$session
WHERE username is not null
and Status Not In ('KILLED','SNIPED')
and sid=i_sid
and serial#=i_serial;
exception
when no_data_found then
RAISE_APPLICATION_ERROR(-20001,
'Fejl i Kill_Session : Sid/Serial findes ikke eller session har status Killed/Sniped.');
end;
-- Kontroller om sessionen tilhører systembrugere
-- (CTXSYS,DBSNMP,DIP,EXFSYS,LMS,OUTLN,SYS,SYSTEM,TSMSYS,XDB)
begin
SELECT 1
into v_systembruger
from dba_users
where username=v_username
and username in ('CTXSYS','DBSNMP','DIP','EXFSYS','LMS','OUTLN','SYS','SYSTEM','TSMSYS','XDB');
RAISE_APPLICATION_ERROR(-20002,
'Fejl i Kill_Session : sessionen tilhører systembruger '||v_username||'.' );
exception
when no_data_found then
execute immediate 'alter system kill session ' || i_sid || ',' || i_serial || ';
end;
end;
/
SQL> grant execute on kill_session to PUBLIC;
SQL> create PUBLIC synonym kill_session for kill_session;
Følgende kan så udføres fra applikatioen eller fra SQL*Plus.
SQL> connect <username>
SQL> exec kill_session(<sid>,<serial#>);