Oracle Stored Procedure that copies and compiles database objects between schemasWe have a single ORACLE server that contains production as well as development environments, each one uses two schemas - SCHEMA_1 / SCHEMA_2 and SCHEMA_1_DEV / SCHEMA_2_DEV respectively. First we design everything in _DEV environment and then copy all database structure to production. The problem is that the development stored procedures point to tables and other procedures in schema ending with "_DEV". However, in production all schema calls should have no "_DEV". The following procedure copies (and compiles) any object from development environment to production after removing the "_DEV" call from everywhere. This way we save time and avoid any human error on doing such replacements by hand. Note: We are using DBMS_SQL so that package or procedure of any size can be compiled. EXECUTE IMMEDIATE cannot run queries whose length is greater than 32 KB
Call to procedure: EXEC MIGRATE_OBJECT_TO_PRODUCTION ('NEW_SCHEMA', 'PKG_TO_COPY', 'PACKAGE') Procedure Source Code: CREATE OR REPLACE PROCEDURE MIGRATE_OBJECT_TO_PRODUCTION ( IN_SCHEMA_TO IN VARCHAR2, IN_OBJECT_NAME IN VARCHAR2, IN_OBJECT_TYPE IN VARCHAR2 ) IS -- LOCAL STORED PROCEDURE PROCEDURE PRC_CREATE_OBJECT ( IN_SCHEMA_TO IN VARCHAR2, IN_OBJECT_NAME IN VARCHAR2, IN_OBJECT_TYPE IN VARCHAR2 ) IS L_SQL_TABLE DBMS_SQL.VARCHAR2A; -- COLLECTION OF VARCHAR2(32767) INDEX BY BINARY_INTEGER L_CURRENT_ROW BINARY_INTEGER := 0; L_CUR PLS_INTEGER; L_ROWS_PROCESSED PLS_INTEGER; CURSOR CRS_OBJECT_SCRIPT ( IN_OBJECT_NAME IN VARCHAR2, IN_OBJECT_TYPE IN VARCHAR2 ) IS -- CURSOR RETRIEVES ALL LINES OF CODE TO CREATE THE OBJECT -- REPLACE ALL CALLS TO SCHEMA NAME ENDING WITH _DEV SELECT REPLACE (UPPER (TEXT), '_DEV.', '.') AS TEXT, LINE FROM USER_SOURCE WHERE UPPER (NAME) = UPPER (IN_OBJECT_NAME) AND UPPER (TYPE) = UPPER (IN_OBJECT_TYPE) ORDER BY LINE; BEGIN FOR CODE_LINE IN CRS_OBJECT_SCRIPT (IN_OBJECT_NAME, IN_OBJECT_TYPE) LOOP IF CODE_LINE.LINE = 1 THEN -- ADD NEW SCHEMA NAME AND CREATE OR REPLACE COMMAND CODE_LINE.TEXT := ' CREATE OR REPLACE ' || REPLACE (CODE_LINE.TEXT, IN_OBJECT_NAME, IN_SCHEMA_TO || '.' || IN_OBJECT_NAME ); END IF; L_CURRENT_ROW := NVL (L_SQL_TABLE.LAST, 0) + 1; L_SQL_TABLE (L_CURRENT_ROW) := CODE_LINE.TEXT; END LOOP; IF L_CURRENT_ROW = 0 THEN RAISE NO_DATA_FOUND; END IF; -- PARSE THE PL/SQL AND EXECUTE IT L_CUR := DBMS_SQL.OPEN_CURSOR; DBMS_SQL.PARSE (L_CUR, L_SQL_TABLE, L_SQL_TABLE.FIRST, L_SQL_TABLE.LAST, FALSE, DBMS_SQL.NATIVE ); L_ROWS_PROCESSED := DBMS_SQL.EXECUTE (L_CUR); DBMS_SQL.CLOSE_CURSOR (L_CUR); L_SQL_TABLE.DELETE (0, L_CURRENT_ROW); -- CLEAR THE COLLECTION OF QUERY LINES DBMS_OUTPUT.PUT_LINE ( IN_OBJECT_TYPE || ' ' || IN_OBJECT_NAME || ' successfully created.' ); EXCEPTION -- EXCEPTION HANDLERS BEGIN WHEN NO_DATA_FOUND THEN DBMS_OUTPUT.PUT_LINE ( 'There is no ' || IN_OBJECT_TYPE || ' ' || IN_OBJECT_NAME || '.' ); WHEN OTHERS THEN -- HANDLES ALL OTHER ERRORS DBMS_OUTPUT.PUT_LINE (DBMS_UTILITY.FORMAT_ERROR_STACK); ROLLBACK; END PRC_CREATE_OBJECT; BEGIN DBMS_OUTPUT.ENABLE (1000000); IF IN_OBJECT_TYPE = 'PACKAGE' THEN -- PACKAGE NEEDS PACKAGE AND PACKAGE BODY DECLARATIONS PRC_CREATE_OBJECT (IN_SCHEMA_TO, IN_OBJECT_NAME, 'PACKAGE'); PRC_CREATE_OBJECT (IN_SCHEMA_TO, IN_OBJECT_NAME, 'PACKAGE BODY'); ELSE -- FOR ALL OTHER OBJECTS PRC_CREATE_OBJECT (IN_SCHEMA_TO, IN_OBJECT_NAME, IN_OBJECT_TYPE); END IF; COMMIT; END MIGRATE_OBJECT_TO_PRODUCTION; To copy the source code, click inside the textbox => Ctrl-A => Ctrl-C |
|||
| ^ Top ^ | |||
| List of all ORACLE Codes |