miércoles, 21 de agosto de 2013

Ejemplos Sencillos de PL/SQL: LOOP y END LOOP

Se puede ejecutar un comando PL/SQL o una serie de comandos PL/SQL una vez o muchas veces con LOOP y END LOOP. Es necesario proporcionar una manera de salir del círculo. Si no haces esto, el círculo pueda continuar indefinidamente. En el ejemplo siguiente muestro dos maneras de emplear EXIT para salir de un círculo:

SQL> SET SERVEROUTPUT ON
SQL> DECLARE
  2   M NUMBER;
  3   N NUMBER;
  4  BEGIN
  5   M := 1;
  6   LOOP
  7    DBMS_OUTPUT.PUT_LINE('M = '||M);
  8    M := M + 1;
  9    EXIT WHEN M > 2;
 10   END LOOP;
 11   N := M;
 12   LOOP
 13    DBMS_OUTPUT.PUT_LINE('N = '||N);
 14    N := N + 1;
 15    IF N > 4 THEN
 16     EXIT;
 17    END IF;
 18   END LOOP;
 19  END;
 20  /
M = 1
M = 2
N = 3
N = 4
 
Procedimiento PL/SQL terminado correctamente.
 
SQL>

viernes, 9 de agosto de 2013

Como se Puede Limitar la Duración de una Sesión Oracle

Tenía que limitar la duración de una sesión Oracle mientras preparaba un entorno nuevo. Así decidí documentar lo que hice. Probé el ejemplo bajo estas líneas en una base de datos Oracle 11.2.0.2.7. Para empezar conecté como SYS y limité CONNECT_TIME a un minuto el el perfil DEFAULT: 

SQL> conn / as sysdba
Conectado.
SQL> alter profile default
  2  limit connect_time 1
  3  /
 
Perfil modificado.

SQL>

Luego cambié RESOURCE_LIMIT a TRUE para hacer cumplir los límites: 

SQL> alter system set resource_limit = true
  2  /
 
Sistema modificado.

SQL>

Creé un usuario con el perfil DEFAULT. Entonces me conecté a la base de datos como este usuario, miré CONNECT_TIME en USER_RESOURCE_LIMITS y comprobé la hora cada diez segundos:

SQL> create user andrew
  2  identified by reid
  3  profile default
  4  /
 
Usuario creado.
 
SQL> grant create session to andrew
  2  /
 
Concesion terminada correctamente.
 
SQL> conn andrew/reid
Conectado.
SQL> select limit from user_resource_limits
  2  where resource_name = 'CONNECT_TIME'
  3  /
 
LIMIT
----------------------------------------
1
 
SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
 
TIME_NOW
--------
18:29:42
 
SQL> host sleep 10
 
SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
 
TIME_NOW
--------
18:29:52
 
SQL> host sleep 10
 
SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
 
TIME_NOW
--------
18:30:02
 
SQL> host sleep 10
 
SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
 
TIME_NOW
--------
18:30:12
 
SQL> host sleep 10
 
SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
 
TIME_NOW
--------
18:30:22
 
SQL> host sleep 10
 
SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
 
TIME_NOW
--------
18:30:32
 
SQL> host sleep 10

Después de un minuto, la consulta siguiente fracasó y la sesión terminó con un ORA-02399:

SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
select to_char(sysdate,'hh24:mi:ss')
*
ERROR en linea 1:
ORA-00604: se ha producido un error a nivel 1 de SQL
recursivo
ORA-02399: ha excedido el tiempo maximo de conexion,
desconectando
ORA-02399: ha excedido el tiempo maximo de conexion,
desconectando

SQL>

... y una nueva tentativa a emplear la consulta probó que la sesión no estaba conectada a la base de datos: 

SQL> select to_char(sysdate,'hh24:mi:ss')
  2  time_now from dual
  3  /
select to_char(sysdate,'hh24:mi:ss')
*
ERROR en linea 1:
ORA-01012: no esta conectado
Identificador de Proceso: 6736
Identificador de Sesion: 36 Numero de Serie: 9