DBMS_LOCK PACKAGE In Oracle
INTRODUCTION:
This package is used for managing lock operation in PLSQL:
- LOCK
- CONVERSION
- RELEASE
SUBPROGRAMS OF DBMS_LOCK PACKAGE:
- ALLOCATE_UNIQUE PROCEDURE
- REQUEST FUNCTION
- CONVERT FUNCTION
- RELEASE FUNCTION
- SLEEP PROCEDURE
ALLOCATE_UNIQUE PROCEDURE:
- The ALLOCATE_UNIQUE procedure returns a unique handle to a lock specified by the lockname parameter.
- This handle can be used to identify the locks in call to other DBMS_LOCK programs.
SYNTAX:
--DBMS_LOCK PACKAGE In Oracle: DBMS_LOCK.ALLOCATE_UNIQUE PROCEDURE DBMS_LOCK.ALLOCATE_UNIQUE(LOCKNAME IN VARCHAR2, LOCKHANDLE OUT VARCHAR2, EXPIRATION_SECS IN INTEGER DEFAULT 86400 );
- LOCKNAME –> Name of the lock for which you want to generate an unique id.
- LOCKHANDLE –> Unique handle to lock by name
- EXPIRATION_SECS –> Length of time to leave the lock allocated.
RESTRICTIONS:
- Locknames can be 128 characters long and are case-sensitive.
- Locknames must not start with "ORA$" as these are reserved for oracle
- ALLOCATE_UNIQUE procedure always perform a commit so it cannot be called from TRIGGER.
--DBMS_LOCK PACKAGE In Oracle: Example CREATE OR REPLACE PACKAGE EMPLOYEE_ACCESS IS FUNCTION GET_EMP_LOCK_HANDLE RETURN VARCHAR2; END EMPLOYEE_ACCESS; /
--DBMS_LOCK PACKAGE In Oracle: Example CREATE OR REPLACE PACKAGE BODY EMPLOYEE_ACCESS IS EMP_LOCKNAME VARCHAR2(128) := 'EMP_LOCK'; EMP_LOCKHANDLE VARCHAR2(128); -- FUNCTION GET_EMP_LOCK_HANDLE RETURN VARCHAR2 IS BEGIN IF EMP_LOCKHANDLE IS NULL THEN DBMS_LOCK.ALLOCATE_UNIQUE (LOCKNAME => EMP_LOCKNAME, LOCKHANDLE => EMP_LOCKHANDLE ); END IF; RETURN EMP_LOCKHANDLE; END GET_EMP_LOCK_HANDLE; END EMPLOYEE_ACCESS; /
REQUEST FUNCTION:
- The REQUEST function is used to acquire a lock in the mode specified by lockmode parameter.
- If the lock cannot be acquired in the requested mode within the specified time the function returns a non-zero return value.
SYNTAX:
The first parameter of REQUEST function is overloaded. The first parameter is :
- either identify the lock by an id (integer)
- or identify the lock by lockhandle (varchar2)
--DBMS_LOCK PACKAGE In Oracle: DBMS_LOCK.REQUEST DBMS_LOCK.REQUEST(ID INTEGER, LOCKMODE INTEGER DEFAULT X_MODE, TIMEOUT INTEGER DEFAULT MAXWAIT, RELEASE_ON_COMMIT BOOLEAN DEFAULT FALSE) RETURN INTEGER; DBMS_LOCK.REQUEST(LOCKHANDLE VARCHAR2, LOCKMODE INTEGER DEFAULT X_MODE, TIMEOUT INTEGER DEFAULT MAXWAIT, RELEASE_ON_COMMIT BOOLEAN DEFAULT FALSE) RETURN INTEGER;
PARAMETER DESCRIPTIONS:
- ID :-> Numeric id of the lock
- LOCKHANDLE :-> Handle for lock returned by DBMS_LOCK.ALLOCATE_UNIQUE
- LOCKMODE :-> Locking mode requested for lock
- TIMEOUT :-> Time in second to wait for successful conversion.
- RELEASE_ON_COMMIT :-> If TRUE, release lock automatically on COMMIT or ROLLBACK.
DESCRIPTION OF RETURN VALUES OF FUNCTION:
- 0 –> Success
- 1 –> Timed out
- 2 –> Dead Lock
- 3 –> Parameter error
- 4 –> Do not own lock; cannot convert
- 5 –> Illegal lock handle
--DBMS_LOCK PACKAGE In Oracle: Example CREATE OR REPLACE PACKAGE EMPLOYEE_ACCESS IS FUNCTION GET_EMP_LOCK_HANDLE RETURN VARCHAR2; PROCEDURE LOCK_EMP(P_RETURN_CODE OUT INTEGER); END EMPLOYEE_ACCESS; /
--DBMS_LOCK PACKAGE In Oracle: Example CREATE OR REPLACE PACKAGE BODY EMPLOYEE_ACCESS IS EMP_LOCKNAME VARCHAR2(128) := 'EMP_LOCK'; EMP_LOCKHANDLE VARCHAR2(128); -- FUNCTION GET_EMP_LOCK_HANDLE RETURN VARCHAR2 IS BEGIN IF EMP_LOCKHANDLE IS NULL THEN DBMS_LOCK.ALLOCATE_UNIQUE (LOCKNAME => EMP_LOCKNAME, LOCKHANDLE => EMP_LOCKHANDLE ); END IF; RETURN EMP_LOCKHANDLE; END GET_EMP_LOCK_HANDLE; PROCEDURE LOCK_EMP(P_RETURN_CODE OUT INTEGER) IS TEMP_LOCKHANDLE EMP_LOCKHANDLE%TYPE := GET_EMP_LOCK_HANDLE; CALL_STATUS INTEGER; BEGIN CALL_STATUS := DBMS_LOCK.REQUEST(LOCKHANDLE => TEMP_LOCKHANDLE, LOCKMODE => DBMS_LOCK.X_MODE, TIMEOUT => 5, RELEASE_ON_COMMIT => TRUE); P_RETURN_CODE := CALL_STATUS; END LOCK_EMP; END EMPLOYEE_ACCESS; /
CONVERT FUNCTION:
- The CONVERT function is used to convert a previously acquired lock to the mode specified by the lockmode parameter.
- If the mode conversion cannot be granted within specified time then the function returns a non-zero value.
- Just like REQUEST function, the first parameter of CONVERT function is overloaded. It is used to identify the lock either by integer or varchar2.
SYNTAX:
--DBMS_LOCK PACKAGE In Oracle: DBMS_LOCK.CONVERT FUNCTION DBMS_LOCK.CONVERT(ID INTEGER, LOCKMODE INTEGER, TIMEOUT NUMBER DEFAULT MAXWAIT ) RETURN INTEGER; FUNCTION DBMS_LOCK.CONVERT(LOCKHANDLE VARCHAR2, LOCKMODE INTEGER, TIMEOUT NUMBER DEFAULT MAXWAIT ) RETURN INTEGER;
PARAMETER DESCRIPTIONS:
- ID :–> Numeric id of the lock
- LOCKHANDLE :-> Handle for lock returned by DBMS_LOCK.ALLOCATE_UNIQUE
- LOCKMODE :-> Locking mode to which to convert the lock
- TIMEOUT :-> Time in second to wait for successful conversion.
DESCRIPTION OF RETURN VALUES OF FUNCTION:
- 0 –> Success
- 1 –> Timed out
- 2 –> Dead Lock
- 3 –> Parameter error
- 4 –> Do not own lock; cannot convert
- 5 –> Illegal lock handle
--DBMS_LOCK PACKAGE In Oracle: Example DECLARE CALL_STATUS INTEGER; BEGIN CALL_STATUS := DBMS_LOCK.CONVERT(9999, DBMS_LOCK.NL_MODE, 0); IF CALL_STATUS = 0 THEN DBMS_OUTPUT.PUT_LINE('SUCCESS'); ELSE IF CALL_STATUS = 1 THEN DBMS_OUTPUT.PUT_LINE('FAIL DUE TO TIME OUT'); ELSIF CALL_STATUS = 2 THEN DBMS_OUTPUT.PUT_LINE('FAIL DUE TO DEAD LOCK'); ELSIF CALL_STATUS = 3 THEN DBMS_OUTPUT.PUT_LINE('FAIL DUE TO PARAMETER ERROR'); ELSIF CALL_STATUS = 4 THEN DBMS_OUTPUT.PUT_LINE('FAIL DUE TO DO NOT OWN LOCK OR UNABLE TO CONVERT'); ELSIF CALL_STATUS = 5 THEN DBMS_OUTPUT.PUT_LINE('FAIL DUE TO ILLEGAL LOCK HANDLE'); END IF; END IF; END; /
RELEASE FUNCTION:
- RELEASE function releases a previously acquired lock.
- Only parameter of RELEASE function is overloaded. Its used to identify the lock either by integer or varchar2.
SYNTAX:
FUNCTION DBMS_LOCK.RELEASE(ID INTEGER) RETURN INTEGER;
FUNCTION DBMS_LOCK.RELEASE(LOCKHANDLE VARCHAR2) RETURN INTEGER;
PARAMETER DESCRIPTION:
- ID :–> Numeric id of the lock
- LOCKHANDLE :–> Handle for lock returned by ALLOCATE_UNIQUE
DESCRIPTION OF RETURN VALUES OF FUNCTION:
- 0 –> Success
- 3 –> Parameter error
- 4 –> Do not own lock; cannot release
- 5 –> Illegal lock handle
--DBMS_LOCK PACKAGE In Oracle: Example CREATE OR REPLACE PACKAGE EMPLOYEE_ACCESS IS FUNCTION GET_EMP_LOCK_HANDLE RETURN VARCHAR2; PROCEDURE LOCK_EMP(P_RETURN_CODE OUT INTEGER); PROCEDURE RELEASE_EMP(P_RETURN_CODE OUT INTEGER); END EMPLOYEE_ACCESS; /
--DBMS_LOCK PACKAGE In Oracle: Example CREATE OR REPLACE PACKAGE BODY EMPLOYEE_ACCESS IS EMP_LOCKNAME VARCHAR2(128) := 'EMP_LOCK'; EMP_LOCKHANDLE VARCHAR2(128); TEMP_LOCKHANDLE EMP_LOCKHANDLE%TYPE := GET_EMP_LOCK_HANDLE; CALL_STATUS INTEGER; -- FUNCTION GET_EMP_LOCK_HANDLE RETURN VARCHAR2 IS BEGIN IF EMP_LOCKHANDLE IS NULL THEN DBMS_LOCK.ALLOCATE_UNIQUE (LOCKNAME => EMP_LOCKNAME, LOCKHANDLE => EMP_LOCKHANDLE ); END IF; RETURN EMP_LOCKHANDLE; END GET_EMP_LOCK_HANDLE; PROCEDURE LOCK_EMP(P_RETURN_CODE OUT INTEGER) IS BEGIN CALL_STATUS := DBMS_LOCK.REQUEST(LOCKHANDLE => TEMP_LOCKHANDLE, LOCKMODE => DBMS_LOCK.X_MODE, TIMEOUT => 5, RELEASE_ON_COMMIT => TRUE); P_RETURN_CODE := CALL_STATUS; END LOCK_EMP; PROCEDURE RELEASE_EMP(P_RETURN_CODE OUT INTEGER) IS BEGIN CALL_STATUS := DBMS_LOCK.RELEASE(LOCKHANDLE => TEMP_LOCKHANDLE); P_RETURN_CODE := CALL_STATUS; END RELEASE_EMP; END EMPLOYEE_ACCESS; /
SLEEP PROCEDURE:
- SLEEP procedure suspends the session for the no of seconds specified in seconds parameter.
- This procedure can be specified in hundredth part of a second e.g. 1.25, 1.49 etc.
SYNTAX:
PROCEDURE DBMS_LOCK.SLEEP(SECONDS NUMBER);
- Do not specify a null value for seconds parameter. It will raise ORA-00600 error.
BEGIN DBMS_LOCK.SLEEP(10); END; /