Database DevOps for Oracle

Database build

Analogous to checking that code compiles, a database build will check that the database can be created from scratch. Failures should be rare as changes have in theory originated from a working development instance linked to version control using Source Control for Oracle. However, SQL errors could be introduced in specific circumstances.

  1. A user chooses to make a change "offline" by editing the SQL creation scripts directly, rather than making a "connected" change on their development instance and using Source Control for Oracle to do the check-in.
  2. A poorly executed code merge could result in invalid SQL.

Note that Oracle will not prevent a database from building if it contains invalid objects. These need to be detected independently.

Other benefits

Other than failing fast when either of the above scenarios occurs, running a database build has additional benefits:

  1. It builds a database on which further testing can happen, such as unit testing and static analysis checks.
  2. A report of all objects in the database can be generated as a build artifact for documentation or audit purposes.
  3. A database creation script can be generated as a build artifact, which is can be run to easily provision dev and test instances.

Worked example:

  1. Runs DropAllObjects.sql (code included below) to empty the TEST schema, which is a schema whose sole function is to serve the Build and Test continuous integration process.
  2. Runs the Schema Compare for Oracle command line, sco.exe, to build the database from the State folder, where the creation scripts are stored.
  3. As part of the same command line invocation we also output the .sql creation script and the changes report to save as build artifacts.
  4. We output a warning to the console if there are no changes, which probably means the schema has no objects
  5. If, as expected, we detect differences (sco.exe exit code 61) we set the ERRORLEVEL to 0 to prevent the build from recognizing this as a failure.


CI Build Toggle source code

  1. rem First we run a previously saved script Tools/DropAllObjects.sql to drop all objects from the TEST schema
  2.  
  3. echo on
  4. Call exit | sqlplus SOCO_TEST/demopassword@(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)(Host=localhost)(Port=1521))(CONNECT_DATA=(SID=XE))) @Tools/DropAllObjects.sql
  5. echo off
  6.  
  7. rem Build the database with the objects and generate a creation script and a report listing all objects.
  8. "C:\Program Files\Red Gate\Schema Compare for Oracle 4\sco.exe" /deploy /i:sdwgvac /source State{SOCO_DEV} /target SOCO_TEST/demopassword@localhost/XE{SOCO_TEST} /sf:Artifacts/database_creation_script.sql /report:Artifacts/all_objects_report.html
  9.  
  10. echo Build database from state:%ERRORLEVEL%
  11.  
  12. rem IF ERRORLEVEL is 0 then there are no changes.
  13. IF %ERRORLEVEL% EQU 0 (
  14. echo ========================================================================================================
  15. echo == Warning - No schema changes detected. Does the database have any schema objects?
  16. echo ========================================================================================================
  17. )
  18.  
  19. rem IF ERRORLEVEL is 61 there are differences, which we expect.
  20. IF %ERRORLEVEL% EQU 61 (
  21. echo ========================================================================================================
  22. echo == Objects were found and built. Change report all_objects_report.html saved as an artifact
  23. echo ========================================================================================================
  24. rem Reset the ERRORLEVEL to 0 so the build doesn't fail
  25. SET ERRORLEVEL=0
  26. )
  27.  


DropAllObjects.sql Toggle source code

  1. SET SERVEROUTPUT ON SIZE 1000000
  2. BEGIN
  3. FOR cur_rec IN (SELECT object_name, object_type
  4. FROM user_objects
  5. WHERE object_type IN ('TABLE', 'VIEW', 'PACKAGE', 'PROCEDURE', 'FUNCTION', 'SEQUENCE')) LOOP
  6. BEGIN
  7. IF cur_rec.object_type = 'TABLE' THEN
  8. EXECUTE IMMEDIATE 'DROP ' || cur_rec.object_type || ' "' || cur_rec.object_name || '" CASCADE CONSTRAINTS';
  9. ELSE
  10. EXECUTE IMMEDIATE 'DROP ' || cur_rec.object_type || ' "' || cur_rec.object_name || '"';
  11. END IF;
  12. EXCEPTION
  13. WHEN OTHERS THEN
  14. DBMS_OUTPUT.put_line('FAILED: DROP ' || cur_rec.object_type || ' "' || cur_rec.object_name || '"');
  15. END;
  16. END LOOP;
  17. END;
  18. /




Didn't find what you were looking for?