2029 lines
70 KiB
Markdown
2029 lines
70 KiB
Markdown
# Package Deployment Guide - Developer Instructions
|
|
|
|
## Overview
|
|
|
|
This guide provides step-by-step instructions for developers on how to properly deploy new package versions using the integrated version tracking and hash-based change detection system.
|
|
|
|
**Target Audience:** Database developers working with CT_MRDS packages
|
|
**System:** Oracle Database 23ai with ENV_MANAGER v3.1.0+
|
|
**Last Updated:** 2025-10-22
|
|
|
|
---
|
|
|
|
## MANDATORY STANDARDS (NEVER SKIP!)
|
|
|
|
### 🔴 Critical: Author Field
|
|
|
|
**ALL scripts MUST have:**
|
|
```sql
|
|
-- Author: Grzegorz Michalski
|
|
```
|
|
|
|
**❌ WRONG:**
|
|
```sql
|
|
-- Author: System
|
|
-- Author: Developer
|
|
-- Author: [your name here]
|
|
```
|
|
|
|
**✅ CORRECT:**
|
|
```sql
|
|
-- Author: Grzegorz Michalski
|
|
```
|
|
|
|
### 📅 Date Format Standard
|
|
|
|
**ISO 8601 format only:**
|
|
```sql
|
|
-- Date: 2026-02-03 (YYYY-MM-DD)
|
|
```
|
|
|
|
### 📝 Script Header Template
|
|
|
|
**Copy-paste this template for ALL scripts:**
|
|
```sql
|
|
-- =====================================================================
|
|
-- Script: XX_MARS_XXX_description.sql
|
|
-- MARS Issue: MARS-XXX
|
|
-- Purpose: Brief description of what this script does
|
|
-- Author: Grzegorz Michalski
|
|
-- Date: YYYY-MM-DD
|
|
-- =====================================================================
|
|
```
|
|
|
|
### 🔐 Database User Requirements
|
|
|
|
**Execute installations as ADMIN:**
|
|
```powershell
|
|
# ✅ CORRECT
|
|
Get-Content "install_marsXXX.sql" | sql "ADMIN/password@service"
|
|
|
|
# ❌ WRONG
|
|
Get-Content "install_marsXXX.sql" | sql "CT_MRDS/password@service"
|
|
```
|
|
|
|
### 🔍 Data Dictionary Views
|
|
|
|
**Use ALL_* views when installing as ADMIN:**
|
|
```sql
|
|
-- ✅ CORRECT (ADMIN user)
|
|
SELECT * FROM ALL_ERRORS WHERE OWNER = 'CT_MRDS' AND NAME = 'PACKAGE_NAME';
|
|
|
|
-- ❌ WRONG (shows ADMIN schema, not CT_MRDS)
|
|
SELECT * FROM USER_ERRORS WHERE NAME = 'PACKAGE_NAME';
|
|
```
|
|
|
|
### 📂 Log Directory Management
|
|
|
|
**MANDATORY in all master scripts:**
|
|
```sql
|
|
-- Create log/ directory before SPOOL (prevents failures)
|
|
host mkdir log 2>nul
|
|
|
|
-- Then configure dynamic SPOOL filename
|
|
var filename VARCHAR2(100)
|
|
BEGIN
|
|
:filename := 'log/INSTALL_MARS_XXX_' || SYS_CONTEXT('USERENV', 'CON_NAME') || '_' || TO_CHAR(SYSDATE,'YYYYMMDD_HH24MISS') || '.log';
|
|
END;
|
|
/
|
|
```
|
|
|
|
### ✋ User Confirmation
|
|
|
|
**MANDATORY ACCEPT validation in master scripts:**
|
|
```sql
|
|
ACCEPT continue CHAR PROMPT 'Type YES to continue with installation, or Ctrl+C to abort: '
|
|
WHENEVER SQLERROR EXIT SQL.SQLCODE
|
|
BEGIN
|
|
IF '&continue' IS NULL OR TRIM('&continue') IS NULL OR UPPER(TRIM('&continue')) != 'YES' THEN
|
|
RAISE_APPLICATION_ERROR(-20001, 'Installation aborted by user');
|
|
END IF;
|
|
END;
|
|
/
|
|
WHENEVER SQLERROR CONTINUE
|
|
```
|
|
|
|
### 🚪 Clean Exit
|
|
|
|
**End all master scripts with:**
|
|
```sql
|
|
spool off
|
|
quit; -- ← MANDATORY for clean SQLcl/SQL*Plus exit
|
|
```
|
|
|
|
### 📋 Quick Compliance Checklist
|
|
|
|
Before committing any script, verify:
|
|
- [ ] `Author: Grzegorz Michalski` in header
|
|
- [ ] Date in ISO 8601 format (YYYY-MM-DD)
|
|
- [ ] Master scripts use `host mkdir log 2>nul`
|
|
- [ ] Master scripts require ACCEPT validation
|
|
- [ ] Master scripts end with `quit;`
|
|
- [ ] Verification queries use ALL_* views with OWNER filter
|
|
- [ ] Installation instructions specify ADMIN user
|
|
|
|
**💡 Remember:** These standards prevent common mistakes and ensure consistency across all MARS packages!
|
|
|
|
---
|
|
|
|
## Table of Contents
|
|
|
|
1. [Before You Start](#before-you-start)
|
|
2. [Standard Deployment Workflow](#standard-deployment-workflow)
|
|
3. [Version Update Guidelines](#version-update-guidelines)
|
|
4. [Deployment Scenarios](#deployment-scenarios)
|
|
5. [Creating MARS Installation Packages](#creating-mars-installation-packages)
|
|
6. [Troubleshooting](#troubleshooting)
|
|
7. [Best Practices](#best-practices)
|
|
8. [Quick Reference](#quick-reference)
|
|
|
|
---
|
|
|
|
## Before You Start
|
|
|
|
### Step 0: Prepare Dedicated Working Directory and Git Branch
|
|
|
|
**CRITICAL:** Before starting work on any MARS package, create a dedicated working directory with its own feature branch:
|
|
|
|
```powershell
|
|
# Navigate to your Git repository parent directory
|
|
cd c:\_git\_local_rep
|
|
|
|
# Clone main repository to new working directory for MARS issue
|
|
# This creates complete isolation for the feature branch
|
|
git clone working_dir_02 working_dir_02_MARS-XXXX
|
|
|
|
# Navigate to new working directory
|
|
cd working_dir_02_MARS-XXXX
|
|
|
|
# Ensure you're on main branch and it's up to date
|
|
git checkout main
|
|
git pull origin main
|
|
|
|
# Create new feature branch for MARS issue
|
|
git checkout -b feature/MARS-XXXX
|
|
|
|
# Verify you're on the new branch
|
|
git branch
|
|
# You should see: * feature/MARS-XXXX (asterisk indicates current branch)
|
|
```
|
|
|
|
**Alternative: Git Worktree (Recommended for Advanced Users):**
|
|
```powershell
|
|
# Navigate to your main Git repository
|
|
cd c:\_git\_local_rep\working_dir_02
|
|
|
|
# Create new worktree with dedicated directory for feature branch
|
|
git worktree add ..\working_dir_02_MARS-XXXX feature/MARS-XXXX
|
|
|
|
# Navigate to new working directory
|
|
cd ..\working_dir_02_MARS-XXXX
|
|
|
|
# Verify you're on the new branch
|
|
git branch
|
|
```
|
|
|
|
**Branch and Directory Naming Convention:**
|
|
- **Branch Format**: `feature/MARS-XXXX` (e.g., `feature/MARS-1057`)
|
|
- **Directory Format**: `working_dir_02_MARS-XXXX` (e.g., `working_dir_02_MARS-1057`)
|
|
- Always branch from `main` to ensure clean starting point
|
|
- One working directory per MARS issue for complete isolation
|
|
|
|
**Working Directory Structure (isolated per MARS issue):**
|
|
```
|
|
c:\_git\_local_rep\
|
|
├── working_dir_02\ # Main working directory (main branch)
|
|
│ ├── MARS_Packages\
|
|
│ ├── database\
|
|
│ └── .git\
|
|
├── working_dir_02_MARS-1057\ # Dedicated directory for MARS-1057
|
|
│ ├── MARS_Packages\
|
|
│ │ └── REL01\
|
|
│ │ └── MARS-1057\ # New package folder
|
|
│ │ ├── rollback_version\
|
|
│ │ ├── new_version\
|
|
│ │ └── *.sql files
|
|
│ ├── database\
|
|
│ └── .git\ # Tracks feature/MARS-1057 branch
|
|
└── working_dir_02_MARS-1058\ # Dedicated directory for MARS-1058 (parallel work)
|
|
└── ...
|
|
```
|
|
|
|
**Git Status Check:**
|
|
```powershell
|
|
# Always verify which branch and directory you're working in
|
|
pwd
|
|
# Output should show: c:\_git\_local_rep\working_dir_02_MARS-XXXX
|
|
|
|
git status
|
|
# Output should show: On branch feature/MARS-XXXX
|
|
|
|
# View all changes in current branch
|
|
git status --short
|
|
```
|
|
|
|
**Why dedicated working directories are mandatory:**
|
|
- **Complete Isolation**: Each MARS issue has its own physical directory
|
|
- **Parallel Work**: Work on multiple MARS issues simultaneously without conflicts
|
|
- **Clean Separation**: No risk of mixing changes from different features
|
|
- **Testing Safety**: Test different features independently in separate environments
|
|
- **Rollback Simplicity**: Delete entire directory to abandon feature
|
|
- **Code Review**: Clear separation for pull request workflow
|
|
- **Deployment Control**: Deploy from specific working directory with confidence
|
|
|
|
**Git Worktree Benefits:**
|
|
- Shares `.git` repository (saves disk space)
|
|
- Faster than full clone
|
|
- Automatic branch tracking
|
|
- Recommended for experienced Git users
|
|
|
|
**Cleanup After Merge:**
|
|
```powershell
|
|
# After feature branch is merged to main, clean up working directory
|
|
cd c:\_git\_local_rep
|
|
|
|
# If using git worktree
|
|
git worktree remove working_dir_02_MARS-XXXX
|
|
|
|
# If using clone, simply delete directory
|
|
Remove-Item -Recurse -Force working_dir_02_MARS-XXXX
|
|
```
|
|
|
|
---
|
|
|
|
### Prerequisites
|
|
|
|
- **ADMIN user access** - MARS package installations require ADMIN privileges for schema operations
|
|
- Access to CT_MRDS schema (or appropriate schema)
|
|
- SQLcl or SQL*Plus installed
|
|
- Understanding of Semantic Versioning (MAJOR.MINOR.PATCH)
|
|
- Package source files available locally
|
|
- **Git installed and configured** - Required for version control workflow
|
|
|
|
**CRITICAL - Data Dictionary Views:**
|
|
|
|
When installing as ADMIN user, you MUST use `ALL_*` views instead of `USER_*` views for verification queries:
|
|
|
|
| ❌ WRONG (USER_*) | ✅ CORRECT (ALL_* with OWNER filter) |
|
|
|-------------------|--------------------------------------|
|
|
| `SELECT * FROM USER_ERRORS WHERE NAME = 'PKG'` | `SELECT * FROM ALL_ERRORS WHERE OWNER = 'CT_MRDS' AND NAME = 'PKG'` |
|
|
| `SELECT * FROM USER_OBJECTS WHERE OBJECT_NAME = 'X'` | `SELECT * FROM ALL_OBJECTS WHERE OWNER = 'CT_MRDS' AND OBJECT_NAME = 'X'` |
|
|
| `SELECT * FROM USER_TAB_COLUMNS WHERE TABLE_NAME = 'T'` | `SELECT * FROM ALL_TAB_COLUMNS WHERE OWNER = 'CT_MRDS' AND TABLE_NAME = 'T'` |
|
|
| `SELECT * FROM USER_TABLES WHERE TABLE_NAME = 'T'` | `SELECT * FROM ALL_TABLES WHERE OWNER = 'CT_MRDS' AND TABLE_NAME = 'T'` |
|
|
|
|
**Why this matters:** `USER_*` views show objects in the **current schema** (ADMIN). When creating objects in other schemas (ODS, CT_MRDS), you must query `ALL_*` views with explicit OWNER filter to verify the changes.
|
|
|
|
### System Components
|
|
|
|
The deployment system uses these key components:
|
|
|
|
- **ENV_MANAGER** - Centralized version management and hash tracking
|
|
- **A_PACKAGE_VERSION_TRACKING** - History table for all package versions
|
|
- **CALCULATE_PACKAGE_HASH** - SHA256 hash calculation for change detection
|
|
- **TRACK_PACKAGE_VERSION** - Records package versions with automatic change detection
|
|
- **CHECK_PACKAGE_CHANGES** - Validates if package was modified
|
|
|
|
---
|
|
|
|
## Universal Tracking and Verification Scripts
|
|
|
|
### MANDATORY: Use Standard Template Files
|
|
|
|
**CRITICAL:** Every MARS package MUST include two universal scripts for tracking and verification. These scripts are reusable across all MARS issues and provide consistent version management.
|
|
|
|
#### Required Files Structure
|
|
|
|
```
|
|
MARS_Packages/
|
|
└── REL0X/
|
|
└── MARS-XXXX/
|
|
├── 01_MARS_XXXX_install_*.sql
|
|
├── 02_MARS_XXXX_install_*.sql
|
|
├── track_package_versions.sql # ✅ MANDATORY - Universal tracking
|
|
├── verify_packages_version.sql # ✅ MANDATORY - Universal verification
|
|
├── install_marsXXXX.sql # Master script
|
|
└── rollback_marsXXXX.sql
|
|
```
|
|
|
|
### track_package_versions.sql
|
|
|
|
**Purpose:** Universal script for tracking multiple package versions with editable package list.
|
|
|
|
**Key Features:**
|
|
- ✅ **Reusable** - Same file for all MARS issues
|
|
- ✅ **Configurable** - Edit package list array to specify which packages to track
|
|
- ✅ **Automatic** - Calls ENV_MANAGER.TRACK_PACKAGE_VERSION for each package
|
|
- ✅ **Summary Output** - Shows tracked packages count and versions
|
|
|
|
**Template:**
|
|
```sql
|
|
-- ===================================================================
|
|
-- PACKAGE LIST - Edit this array to specify packages to track
|
|
-- ===================================================================
|
|
vPackageList t_string_array := t_string_array(
|
|
'CT_MRDS.DATA_EXPORTER',
|
|
'CT_MRDS.FILE_MANAGER',
|
|
'ODS.FILE_MANAGER_ODS'
|
|
);
|
|
-- ===================================================================
|
|
```
|
|
|
|
**Usage in Install Script:**
|
|
```sql
|
|
PROMPT Step 4: Track Package Versions
|
|
PROMPT =========================================================================
|
|
@@track_package_versions.sql
|
|
```
|
|
|
|
**Benefits over custom tracking scripts:**
|
|
- No hardcoded package names in multiple places
|
|
- Single point of configuration
|
|
- Consistent error handling
|
|
- Standardized output format
|
|
- Copy-paste ready for new MARS issues
|
|
|
|
### verify_packages_version.sql
|
|
|
|
**Purpose:** Universal script for verifying ALL tracked packages for code changes.
|
|
|
|
**Key Features:**
|
|
- ✅ **Automatic Discovery** - Queries A_PACKAGE_VERSION_TRACKING to find all tracked packages
|
|
- ✅ **Hash Validation** - Calls CHECK_PACKAGE_CHANGES for each package
|
|
- ✅ **Status Report** - Shows OK or WARNING for each package
|
|
- ✅ **Zero Configuration** - No editing needed, works automatically
|
|
|
|
**Usage in Install Script:**
|
|
```sql
|
|
PROMPT Final Step: Verify All Package Versions
|
|
PROMPT =========================================================================
|
|
@@verify_packages_version.sql
|
|
```
|
|
|
|
**Output Example:**
|
|
```
|
|
PACKAGE_OWNER PACKAGE_NAME VERSION STATUS
|
|
--------------- ------------------- ---------- -------------------------------
|
|
CT_MRDS DATA_EXPORTER 2.2.0 OK: Package has not changed
|
|
CT_MRDS FILE_MANAGER 3.3.0 OK: Package has not changed
|
|
ODS FILE_MANAGER_ODS 2.1.0 OK: Package has not changed
|
|
```
|
|
|
|
### Master Install Script Structure (MANDATORY)
|
|
|
|
Every `install_marsXXXX.sql` MUST follow this exact structure:
|
|
|
|
```sql
|
|
-- ===================================================================
|
|
-- MARS-XXXX INSTALL SCRIPT
|
|
-- ===================================================================
|
|
|
|
-- Dynamic spool file generation
|
|
host mkdir log 2>nul
|
|
-- ... spool setup ...
|
|
|
|
PROMPT Step 1: Deploy Package Specification
|
|
@@01_MARS_XXXX_install_PACKAGE_SPEC.sql
|
|
|
|
PROMPT Step 2: Deploy Package Body
|
|
@@02_MARS_XXXX_install_PACKAGE_BODY.sql
|
|
|
|
PROMPT Step 3: Track Package Versions
|
|
@@track_package_versions.sql -- ✅ MANDATORY universal script
|
|
|
|
PROMPT Step 4: Verify Package Versions
|
|
@@verify_packages_version.sql -- ✅ MANDATORY universal script
|
|
|
|
spool off
|
|
quit;
|
|
```
|
|
|
|
### DO NOT Create Custom Track/Verify Scripts
|
|
|
|
**❌ WRONG (Custom tracking per MARS issue):**
|
|
```sql
|
|
@@04_MARS_XXXX_track_version.sql -- DON'T DO THIS
|
|
@@05_MARS_XXXX_verify_installation.sql -- DON'T DO THIS
|
|
```
|
|
|
|
**✅ CORRECT (Universal scripts):**
|
|
```sql
|
|
@@track_package_versions.sql -- Always use this
|
|
@@verify_packages_version.sql -- Always use this
|
|
```
|
|
|
|
**Why universal scripts are mandatory:**
|
|
- **Consistency** - Same behavior across all MARS packages
|
|
- **Maintainability** - Bug fixes propagate to all packages
|
|
- **Simplicity** - No need to create custom scripts for each issue
|
|
- **Compliance** - Ensures all packages follow same standard
|
|
- **Code Review** - Easier to review when structure is identical
|
|
|
|
### Copying Template Files
|
|
|
|
**For each new MARS package, copy from reference implementation:**
|
|
|
|
```powershell
|
|
# Copy universal scripts from MARS-826-PREHOOK (reference implementation)
|
|
Copy-Item "MARS_Packages\REL01_POST_DEACTIVATION\MARS-826-PREHOOK\track_package_versions.sql" `
|
|
"MARS_Packages\RELXX\MARS-YYYY\track_package_versions.sql"
|
|
|
|
Copy-Item "MARS_Packages\REL01_POST_DEACTIVATION\MARS-826-PREHOOK\verify_packages_version.sql" `
|
|
"MARS_Packages\RELXX\MARS-YYYY\verify_packages_version.sql"
|
|
|
|
# Edit package list in track_package_versions.sql
|
|
# No changes needed to verify_packages_version.sql (works automatically)
|
|
```
|
|
|
|
---
|
|
|
|
## Standard Deployment Workflow
|
|
|
|
### Step 1: Check Current Package Status
|
|
|
|
Before making any changes, verify the current state:
|
|
|
|
```sql
|
|
-- Connect to database
|
|
sql CT_MRDS/password@service_name
|
|
|
|
-- Check current version
|
|
SELECT FILE_MANAGER.GET_VERSION() FROM DUAL;
|
|
|
|
-- Check for any untracked changes
|
|
SELECT ENV_MANAGER.CHECK_PACKAGE_CHANGES('CT_MRDS', 'FILE_MANAGER') FROM DUAL;
|
|
```
|
|
|
|
**Expected Output:** `OK: Package CT_MRDS.FILE_MANAGER has not changed.`
|
|
|
|
If you see **WARNING**, it means there are untracked modifications. See [Handling Untracked Changes](#handling-untracked-changes).
|
|
|
|
---
|
|
|
|
### Step 2: Make Your Code Changes
|
|
|
|
Edit the package SPEC and/or BODY files in your local workspace:
|
|
|
|
```
|
|
database/CT_MRDS/packages/FILE_MANAGER.pkg
|
|
database/CT_MRDS/packages/FILE_MANAGER.pkb
|
|
```
|
|
|
|
**Important:** Do not modify version constants yet.
|
|
|
|
---
|
|
|
|
### Step 3: Update Version Information
|
|
|
|
Based on the type of changes, update version constants in the **SPEC** file:
|
|
|
|
#### A. Determine Version Increment
|
|
|
|
Follow Semantic Versioning rules:
|
|
|
|
- **MAJOR (X.0.0)** - Breaking changes, incompatible API modifications
|
|
- **MINOR (x.Y.0)** - New features, backward-compatible additions
|
|
- **PATCH (x.y.Z)** - Bug fixes, backward-compatible corrections
|
|
|
|
#### B. Update Package Constants
|
|
|
|
Edit the package SPEC file and update three constants:
|
|
|
|
```sql
|
|
-- Package Version Information (Semantic Versioning: MAJOR.MINOR.PATCH)
|
|
PACKAGE_VERSION CONSTANT VARCHAR2(10) := '3.3.0'; -- INCREMENT THIS
|
|
PACKAGE_BUILD_DATE CONSTANT VARCHAR2(20) := '2025-10-22 21:00:00'; -- UPDATE THIS
|
|
PACKAGE_AUTHOR CONSTANT VARCHAR2(100) := 'Your Name'; -- YOUR NAME
|
|
|
|
-- Version History (Latest changes first)
|
|
VERSION_HISTORY CONSTANT VARCHAR2(4000) :=
|
|
'3.3.0 (2025-10-22): Added new export procedure for historical data' || CHR(13)||CHR(10) || -- ADD THIS LINE
|
|
'3.2.0 (2025-10-15): Enhanced validation with column mismatch detection' || CHR(13)||CHR(10) ||
|
|
'3.1.0 (2025-10-01): Initial release with file processing capabilities';
|
|
```
|
|
|
|
**Version History Format:**
|
|
```
|
|
'VERSION (DATE): Brief description of changes' || CHR(13)||CHR(10) ||
|
|
```
|
|
|
|
---
|
|
|
|
### Step 4: Deploy to Database
|
|
|
|
Deploy SPEC first, then BODY:
|
|
|
|
```powershell
|
|
# Using PowerShell and SQLcl
|
|
Get-Content "database\CT_MRDS\packages\FILE_MANAGER.pkg" | sql "CT_MRDS/password@service_name"
|
|
Get-Content "database\CT_MRDS\packages\FILE_MANAGER.pkb" | sql "CT_MRDS/password@service_name"
|
|
```
|
|
|
|
Or using SQL*Plus:
|
|
|
|
```sql
|
|
@database/CT_MRDS/packages/FILE_MANAGER.pkg
|
|
@database/CT_MRDS/packages/FILE_MANAGER.pkb
|
|
```
|
|
|
|
**Check for compilation errors:**
|
|
|
|
```sql
|
|
-- When installing as ADMIN, check specific schema
|
|
SELECT * FROM ALL_ERRORS
|
|
WHERE OWNER = 'CT_MRDS'
|
|
AND TYPE IN ('PACKAGE', 'PACKAGE BODY')
|
|
AND NAME = 'FILE_MANAGER'
|
|
ORDER BY SEQUENCE;
|
|
```
|
|
|
|
---
|
|
|
|
### Step 5: Track the New Version
|
|
|
|
After successful deployment, register the new version in the tracking system:
|
|
|
|
```sql
|
|
BEGIN
|
|
ENV_MANAGER.TRACK_PACKAGE_VERSION(
|
|
pPackageOwner => 'CT_MRDS',
|
|
pPackageName => 'FILE_MANAGER',
|
|
pPackageVersion => FILE_MANAGER.PACKAGE_VERSION,
|
|
pPackageBuildDate => FILE_MANAGER.PACKAGE_BUILD_DATE,
|
|
pPackageAuthor => FILE_MANAGER.PACKAGE_AUTHOR
|
|
);
|
|
END;
|
|
/
|
|
```
|
|
|
|
**System Response:**
|
|
- If version updated correctly: `First tracking record` or `End TRACK_PACKAGE_VERSION - Record inserted`
|
|
- If version NOT updated: `WARNING: Source code changed without version update!`
|
|
|
|
---
|
|
|
|
### Step 6: Verify Deployment
|
|
|
|
Confirm the deployment was successful:
|
|
|
|
```sql
|
|
-- 1. Check deployed version
|
|
SELECT FILE_MANAGER.GET_BUILD_INFO() FROM DUAL;
|
|
|
|
-- 2. Verify no untracked changes
|
|
SELECT ENV_MANAGER.CHECK_PACKAGE_CHANGES('CT_MRDS', 'FILE_MANAGER') FROM DUAL;
|
|
|
|
-- 3. Review tracking history
|
|
SELECT
|
|
PACKAGE_VERSION,
|
|
PACKAGE_BUILD_DATE,
|
|
DETECTED_CHANGE_WITHOUT_VERSION,
|
|
TO_CHAR(TRACKING_DATE, 'YYYY-MM-DD HH24:MI:SS') AS TRACKED_AT
|
|
FROM A_PACKAGE_VERSION_TRACKING
|
|
WHERE PACKAGE_OWNER = 'CT_MRDS'
|
|
AND PACKAGE_NAME = 'FILE_MANAGER'
|
|
ORDER BY TRACKING_DATE DESC
|
|
FETCH FIRST 5 ROWS ONLY;
|
|
```
|
|
|
|
---
|
|
|
|
### Step 7: Update Source Repository (CODE-FIRST Compliance)
|
|
|
|
**CRITICAL:** After successful database deployment, updated packages MUST be copied back to the main source repository to maintain version control integrity.
|
|
|
|
```powershell
|
|
# Copy updated packages to source repository
|
|
# Replace PACKAGE_NAME with actual package name (e.g., FILE_MANAGER)
|
|
|
|
Copy-Item "database\CT_MRDS\packages\PACKAGE_NAME.pkg" `
|
|
"MARS_Packages\mrds_elt-dev-database\mrds_elt-dev-database\database\CT_MRDS\SCHEMA\packages\PACKAGE_NAME.pkg"
|
|
|
|
Copy-Item "database\CT_MRDS\packages\PACKAGE_NAME.pkb" `
|
|
"MARS_Packages\mrds_elt-dev-database\mrds_elt-dev-database\database\CT_MRDS\SCHEMA\packages\PACKAGE_NAME.pkb"
|
|
```
|
|
|
|
**Why this is mandatory:**
|
|
- **CODE-FIRST PRINCIPLE**: Source files are the single source of truth
|
|
- **Version Control**: Git tracks changes in source repository
|
|
- **Team Collaboration**: Other developers need access to latest code
|
|
- **Deployment Reproducibility**: Enables clean deployments to other environments
|
|
- **Rollback Capability**: Source repository serves as backup
|
|
|
|
**Directory Structure:**
|
|
```
|
|
MARS_Packages/
|
|
└── mrds_elt-dev-database/
|
|
└── mrds_elt-dev-database/
|
|
└── database/
|
|
├── CT_MRDS/
|
|
│ └── SCHEMA/
|
|
│ ├── packages/
|
|
│ │ ├── FILE_MANAGER.pkg # ← Specification
|
|
│ │ ├── FILE_MANAGER.pkb # ← Body
|
|
│ │ ├── DATA_EXPORTER.pkg
|
|
│ │ ├── DATA_EXPORTER.pkb
|
|
│ │ ├── ENV_MANAGER.pkg
|
|
│ │ └── ENV_MANAGER.pkb
|
|
│ ├── tables/
|
|
│ ├── views/
|
|
│ └── triggers/
|
|
├── ODS/
|
|
│ └── SCHEMA/
|
|
│ └── packages/
|
|
│ ├── FILE_MANAGER_ODS.pkg # ← Specification
|
|
│ └── FILE_MANAGER_ODS.pkb # ← Body
|
|
└── CT_ET_TEMPLATES/
|
|
└── SCHEMA/
|
|
└── tables/
|
|
```
|
|
|
|
**Verification:**
|
|
```powershell
|
|
# Verify files were updated
|
|
Get-ChildItem "MARS_Packages\mrds_elt-dev-database\mrds_elt-dev-database\database\CT_MRDS\SCHEMA\packages\*.pkg", `
|
|
"MARS_Packages\mrds_elt-dev-database\mrds_elt-dev-database\database\CT_MRDS\SCHEMA\packages\*.pkb" |
|
|
Select-Object Name, LastWriteTime |
|
|
Sort-Object LastWriteTime -Descending
|
|
```
|
|
|
|
---
|
|
|
|
## Version Update Guidelines
|
|
|
|
### Semantic Versioning Rules
|
|
|
|
| Change Type | Version Impact | Example | Description |
|
|
|-------------|---------------|---------|-------------|
|
|
| **Breaking Change** | MAJOR (3.0.0 → 4.0.0) | Changed procedure signature, removed parameter | Requires code changes in calling applications |
|
|
| **New Feature** | MINOR (3.2.0 → 3.3.0) | Added new procedure, new optional parameter | Backward compatible, adds functionality |
|
|
| **Bug Fix** | PATCH (3.2.1 → 3.2.2) | Fixed calculation error, corrected validation | No API changes, fixes existing functionality |
|
|
| **Refactoring** | PATCH (3.2.1 → 3.2.2) | Code cleanup, performance optimization | Internal changes only, no behavior change |
|
|
|
|
### Build Date Format
|
|
|
|
Always use ISO 8601 format with time:
|
|
|
|
```sql
|
|
PACKAGE_BUILD_DATE CONSTANT VARCHAR2(20) := 'YYYY-MM-DD HH24:MI:SS';
|
|
```
|
|
|
|
**Example:** `'2025-10-22 21:00:00'`
|
|
|
|
---
|
|
|
|
## Deployment Scenarios
|
|
|
|
### Scenario 1: New Feature Addition (MINOR Version)
|
|
|
|
**Example:** Adding new export procedure to FILE_MANAGER
|
|
|
|
1. **Current Version:** 3.2.0
|
|
2. **New Version:** 3.3.0
|
|
3. **Changes:**
|
|
- Add new procedure `EXPORT_HISTORICAL_DATA` to SPEC
|
|
- Implement procedure in BODY
|
|
- Update `PACKAGE_VERSION` from `'3.2.0'` to `'3.3.0'`
|
|
- Update `PACKAGE_BUILD_DATE` to current timestamp
|
|
- Add entry to `VERSION_HISTORY`
|
|
|
|
4. **Deploy & Track:**
|
|
```sql
|
|
-- Deploy files
|
|
@database/CT_MRDS/packages/FILE_MANAGER.pkg
|
|
@database/CT_MRDS/packages/FILE_MANAGER.pkb
|
|
|
|
-- Track new version
|
|
BEGIN
|
|
ENV_MANAGER.TRACK_PACKAGE_VERSION(
|
|
pPackageOwner => 'CT_MRDS',
|
|
pPackageName => 'FILE_MANAGER',
|
|
pPackageVersion => FILE_MANAGER.PACKAGE_VERSION,
|
|
pPackageBuildDate => FILE_MANAGER.PACKAGE_BUILD_DATE,
|
|
pPackageAuthor => FILE_MANAGER.PACKAGE_AUTHOR
|
|
);
|
|
END;
|
|
/
|
|
```
|
|
|
|
---
|
|
|
|
### Scenario 2: Bug Fix (PATCH Version)
|
|
|
|
**Example:** Fixing date format validation in DATA_EXPORTER
|
|
|
|
1. **Current Version:** 2.1.0
|
|
2. **New Version:** 2.1.1
|
|
3. **Changes:**
|
|
- Fix validation logic in BODY (no SPEC changes)
|
|
- Update `PACKAGE_VERSION` from `'2.1.0'` to `'2.1.1'`
|
|
- Update `PACKAGE_BUILD_DATE`
|
|
- Add entry to `VERSION_HISTORY`
|
|
|
|
4. **Deploy & Track:** Same as Scenario 1
|
|
|
|
---
|
|
|
|
### Scenario 3: Breaking Change (MAJOR Version)
|
|
|
|
**Example:** Removing deprecated parameter from FILE_ARCHIVER
|
|
|
|
1. **Current Version:** 2.5.3
|
|
2. **New Version:** 3.0.0
|
|
3. **Changes:**
|
|
- Remove old parameter from procedure signature in SPEC
|
|
- Update BODY implementation
|
|
- Update `PACKAGE_VERSION` from `'2.5.3'` to `'3.0.0'`
|
|
- Update `PACKAGE_BUILD_DATE`
|
|
- Add detailed migration notes to `VERSION_HISTORY`
|
|
|
|
4. **Additional Steps:**
|
|
- Document breaking changes
|
|
- Notify dependent application teams
|
|
- Update API documentation
|
|
|
|
---
|
|
|
|
### Scenario 4: Emergency Hotfix
|
|
|
|
When urgent fix is needed in production:
|
|
|
|
1. **Identify Issue:** Document the problem clearly
|
|
2. **Create Fix:** Make minimal changes to address the issue
|
|
3. **Increment PATCH:** Update to next patch version (e.g., 3.2.5 → 3.2.6)
|
|
4. **Fast Track Deployment:**
|
|
|
|
```powershell
|
|
# Quick deployment script
|
|
Get-Content "database\CT_MRDS\packages\PACKAGE_NAME.pkg" | sql "CT_MRDS/password@service_name"
|
|
Get-Content "database\CT_MRDS\packages\PACKAGE_NAME.pkb" | sql "CT_MRDS/password@service_name"
|
|
|
|
# Track immediately
|
|
echo "BEGIN ENV_MANAGER.TRACK_PACKAGE_VERSION('CT_MRDS', 'PACKAGE_NAME', 'VERSION', 'BUILD_DATE', 'AUTHOR'); END;" | sql "CT_MRDS/password@service_name"
|
|
```
|
|
|
|
5. **Verify & Document:** Record hotfix details in change log
|
|
|
|
---
|
|
|
|
## Troubleshooting
|
|
|
|
### Issue 1: Warning - Untracked Changes Detected
|
|
|
|
**Symptom:**
|
|
```
|
|
WARNING: Source code changed without version update!
|
|
Last Version: 3.2.0
|
|
Current Version: 3.2.0
|
|
SPECIFICATION Changed: Hash mismatch detected
|
|
```
|
|
|
|
**Cause:** Code was modified but version constants were not updated.
|
|
|
|
**Solution:**
|
|
1. Update `PACKAGE_VERSION` to next appropriate version
|
|
2. Update `PACKAGE_BUILD_DATE` to current timestamp
|
|
3. Add entry to `VERSION_HISTORY`
|
|
4. Redeploy package
|
|
5. Call `TRACK_PACKAGE_VERSION` again
|
|
|
|
---
|
|
|
|
### Issue 2: Compilation Errors After Deployment
|
|
|
|
**Symptom:**
|
|
```
|
|
Package Body compiled with errors
|
|
LINE/COL ERROR
|
|
-------- -------------
|
|
42/10 PLS-00201: identifier 'PROCEDURE_NAME' must be declared
|
|
```
|
|
|
|
**Solution:**
|
|
1. Check `ALL_ERRORS` for detailed error information:
|
|
```sql
|
|
-- Check specific schema when installing as ADMIN
|
|
SELECT LINE, POSITION, TEXT
|
|
FROM ALL_ERRORS
|
|
WHERE OWNER = 'CT_MRDS' -- Replace with target schema
|
|
AND NAME = 'PACKAGE_NAME'
|
|
AND TYPE = 'PACKAGE BODY'
|
|
ORDER BY SEQUENCE;
|
|
```
|
|
|
|
2. Fix errors in source file
|
|
3. Redeploy package
|
|
4. Verify compilation: `SELECT * FROM ALL_ERRORS WHERE OWNER = 'CT_MRDS' AND NAME = 'PACKAGE_NAME';`
|
|
|
|
---
|
|
|
|
### Issue 3: Package State Discarded Error
|
|
|
|
**Symptom:**
|
|
```
|
|
ORA-04068: existing state of packages has been discarded
|
|
ORA-04061: existing state of package body has been invalidated
|
|
```
|
|
|
|
**Cause:** Package was recently recompiled, session state needs refresh.
|
|
|
|
**Solution:** Simply retry the command. This is a transient error that resolves after first execution.
|
|
|
|
---
|
|
|
|
### Issue 4: Cannot Track Package - Not Found
|
|
|
|
**Symptom:**
|
|
```
|
|
ERROR tracking PACKAGE_NAME: Package not found in database
|
|
```
|
|
|
|
**Solution:**
|
|
1. Verify package exists:
|
|
```sql
|
|
-- Check specific schema when installing as ADMIN
|
|
SELECT OBJECT_NAME, OBJECT_TYPE, STATUS
|
|
FROM ALL_OBJECTS
|
|
WHERE OWNER = 'CT_MRDS' -- Replace with target schema
|
|
AND OBJECT_NAME = 'PACKAGE_NAME';
|
|
```
|
|
|
|
2. If not found, deploy package first
|
|
3. If status = INVALID, recompile package
|
|
4. Retry tracking
|
|
|
|
---
|
|
|
|
## Creating MARS Installation Packages
|
|
|
|
### Overview
|
|
|
|
MARS packages (e.g., MARS-1049, MARS-1011) are deployment packages that bundle database changes for specific features or fixes. They follow a standardized structure with logging, version tracking, and rollback capabilities.
|
|
|
|
**CRITICAL:** All MARS package installations MUST be executed as **ADMIN user** to ensure proper schema creation, privilege management, and cross-schema operations.
|
|
|
|
**Installation User Requirements:**
|
|
- **User:** ADMIN (required for all MARS installations)
|
|
- **Privileges:** Full DBA privileges, CREATE ANY TABLE, ALTER ANY TABLE, EXECUTE on DBMS_CLOUD
|
|
- **Connection:** `sql ADMIN/password@service_name`
|
|
|
|
### Package Structure
|
|
|
|
**IMPORTANT:** Currently, all new MARS packages are being created in the **REL01** directory. This is the active release folder for ongoing development.
|
|
|
|
**CRITICAL - .gitignore Configuration:**
|
|
|
|
Before starting MARS package development, create `.gitignore` file in package root directory to exclude temporary folders from version control:
|
|
|
|
**File Location:** `MARS_Packages/REL01/MARS-XXXX/.gitignore`
|
|
|
|
**Required Content:**
|
|
```gitignore
|
|
# Exclude temporary folders from version control
|
|
confluence/
|
|
log/
|
|
test/
|
|
mock_data/
|
|
```
|
|
|
|
**Why exclude these folders:**
|
|
- **confluence/**: Working documentation files (may contain drafts, not final versions)
|
|
- **log/**: SPOOL log files (generated during installation, environment-specific)
|
|
- **test/**: Test artifacts, temporary test data, and test execution logs
|
|
- **mock_data/**: Test data files for development and validation (environment-specific)
|
|
|
|
**What SHOULD be committed:**
|
|
- Installation scripts (01_*, 02_*, 91_*, 92_*)
|
|
- Master scripts (install_*.sql, rollback_*.sql)
|
|
- track_package_versions.sql and verify_packages_version.sql
|
|
- README.md
|
|
- .gitignore (with standardized exclusions)
|
|
- rollback_version/ and new_version/ folders (if package modifications)
|
|
- Core deployment files only
|
|
|
|
Standard MARS package directory structure:
|
|
|
|
```
|
|
MARS_Packages/REL01/MARS-XXXX/
|
|
├── .gitignore # Git exclusions (REQUIRED)
|
|
├── install_marsXXXX.sql # Master installation script (with SPOOL to log/)
|
|
├── rollback_marsXXXX.sql # Master rollback script (with SPOOL to log/)
|
|
├── 01_MARS_XXXX_install_*.sql # Individual installation scripts
|
|
├── 02_MARS_XXXX_install_*.sql
|
|
├── ...
|
|
├── 91_MARS_XXXX_rollback_*.sql # Individual rollback scripts (91-99 range)
|
|
├── 92_MARS_XXXX_rollback_*.sql
|
|
├── track_package_versions.sql # Version tracking script
|
|
├── verify_packages_version.sql # Package verification script
|
|
├── ...
|
|
├── README.md # Package documentation
|
|
├── rollback_version/ # Backup of objects BEFORE changes (for rollback)
|
|
│ ├── PACKAGE_NAME.pkg # Previous package specification
|
|
│ └── PACKAGE_NAME.pkb # Previous package body
|
|
├── new_version/ # Updated objects AFTER changes (for installation)
|
|
│ ├── PACKAGE_NAME.pkg # New package specification
|
|
│ └── PACKAGE_NAME.pkb # New package body
|
|
├── test/ # Test files and verification scripts
|
|
│ ├── test_marsXXXX.sql # Unit tests
|
|
│ ├── TEST_RESULTS.md # Test documentation
|
|
│ └── test_data_*.csv # Test data files
|
|
├── log/ # SPOOL log files (REQUIRED - auto-created)
|
|
│ ├── INSTALL_MARS_XXXX_*.log # Installation logs from SPOOL
|
|
│ └── ROLLBACK_MARS_XXXX_*.log # Rollback logs from SPOOL
|
|
└── mock_data/ # Mock data for testing (optional)
|
|
├── 00_LOAD_ALL_MOCK_DATA.sql # Master data loader
|
|
├── 01_load_*.sql # Individual table loaders
|
|
└── README.md # Mock data documentation
|
|
```
|
|
|
|
**Naming Conventions:**
|
|
- **Installation scripts**: `01-89` range, executed in numerical order
|
|
- **Rollback scripts**: `91-99` range, executed in reverse order
|
|
- **Verification scripts**: Any number, typically after main scripts
|
|
- **Master scripts**: `install_marsXXXX.sql` and `rollback_marsXXXX.sql`
|
|
|
|
**Version Management Folders (for Database Object Modifications):**
|
|
- **`rollback_version/`** - Contains backup of database objects BEFORE changes (for rollback)
|
|
- **`new_version/`** - Contains updated database objects AFTER changes (for installation)
|
|
|
|
**When to use version folders:**
|
|
- Required when MARS package modifies ANY existing database objects (packages, tables, views, indexes, triggers, etc.)
|
|
- Copy original object definitions to `rollback_version/` before making changes
|
|
- Place modified object definitions in `new_version/` after changes
|
|
- Examples: FILE_MANAGER.pkg/pkb, A_SOURCE_FILE_CONFIG.sql (table), V_STATUS.sql (view), IDX_CONFIG.sql (index)
|
|
|
|
**Test Files Organization:**
|
|
- **`test/`** - Contains ALL test-related files (unit tests, test data, verification scripts)
|
|
- **`log/`** - Contains ALL SPOOL log files from installation/rollback executions (REQUIRED directory)
|
|
- **`mock_data/`** - Contains mock data files for development and testing (optional)
|
|
- Keep deployment scripts clean - move test artifacts to test/ subfolder after validation
|
|
- Include track_package_versions.sql and verify_packages_version.sql in test/ subfolder
|
|
- SPOOL log files automatically created in log/ directory by master scripts
|
|
- Benefits: Clean deployment structure, easy test replication, organized documentation
|
|
|
|
---
|
|
|
|
### Master Install Script Template
|
|
|
|
All MARS packages MUST include SPOOL logging for audit trail and debugging:
|
|
|
|
```sql
|
|
-- ===================================================================
|
|
-- MARS-XXXX INSTALL SCRIPT: Brief Description
|
|
-- ===================================================================
|
|
-- Purpose: Detailed description of what this package does
|
|
-- Author: Grzegorz Michalski
|
|
-- Date: YYYY-MM-DD
|
|
-- Version: X.Y.Z
|
|
|
|
-- Dynamic spool file generation (using SYS_CONTEXT - no DBA privileges required)
|
|
-- Log files are automatically created in log/ subdirectory
|
|
-- IMPORTANT: Ensure log/ directory exists before SPOOL (use host mkdir)
|
|
host mkdir log 2>nul
|
|
|
|
var filename VARCHAR2(100)
|
|
BEGIN
|
|
:filename := 'log/INSTALL_MARS_XXXX_' || SYS_CONTEXT('USERENV', 'CON_NAME') || '_' || TO_CHAR(SYSDATE,'YYYYMMDD_HH24MISS') || '.log';
|
|
END;
|
|
/
|
|
column filename new_value _filename
|
|
select :filename filename from dual;
|
|
spool &_filename
|
|
|
|
SET ECHO OFF
|
|
SET TIMING ON
|
|
SET SERVEROUTPUT ON SIZE UNLIMITED
|
|
SET PAUSE OFF
|
|
|
|
-- Set current schema context (optional - use when modifying packages in specific schema)
|
|
-- ALTER SESSION SET CURRENT_SCHEMA = CT_MRDS;
|
|
|
|
PROMPT =========================================================================
|
|
PROMPT MARS-XXXX: Package Description
|
|
PROMPT =========================================================================
|
|
PROMPT
|
|
PROMPT This script will:
|
|
PROMPT - Change 1
|
|
PROMPT - Change 2
|
|
PROMPT - Change 3
|
|
PROMPT
|
|
PROMPT Expected Duration: X-Y minutes
|
|
PROMPT =========================================================================
|
|
|
|
-- Confirm installation with user
|
|
ACCEPT continue CHAR PROMPT 'Type YES to continue with installation, or Ctrl+C to abort: '
|
|
WHENEVER SQLERROR EXIT SQL.SQLCODE
|
|
BEGIN
|
|
IF '&continue' IS NULL OR TRIM('&continue') IS NULL OR UPPER(TRIM('&continue')) != 'YES' THEN
|
|
RAISE_APPLICATION_ERROR(-20001, 'Installation aborted by user');
|
|
END IF;
|
|
END;
|
|
/
|
|
WHENEVER SQLERROR CONTINUE
|
|
|
|
PROMPT
|
|
PROMPT =========================================================================
|
|
PROMPT Step 1: First Installation Step
|
|
PROMPT =========================================================================
|
|
@@01_MARS_XXXX_install_step1.sql
|
|
|
|
PROMPT
|
|
PROMPT =========================================================================
|
|
PROMPT Step 2: Second Installation Step
|
|
PROMPT =========================================================================
|
|
@@02_MARS_XXXX_install_step2.sql
|
|
|
|
-- ... more deployment steps ...
|
|
|
|
PROMPT
|
|
PROMPT =========================================================================
|
|
PROMPT Step N: Track Package Versions
|
|
PROMPT =========================================================================
|
|
@@track_package_versions.sql
|
|
|
|
PROMPT
|
|
PROMPT =========================================================================
|
|
PROMPT Final Step: Verify Package Versions
|
|
PROMPT =========================================================================
|
|
@@verify_packages_version.sql
|
|
|
|
PROMPT
|
|
PROMPT =========================================================================
|
|
PROMPT MARS-XXXX Installation - COMPLETED
|
|
PROMPT =========================================================================
|
|
PROMPT Check the log file for complete installation details.
|
|
PROMPT =========================================================================
|
|
|
|
spool off
|
|
|
|
quit;
|
|
```
|
|
|
|
**Key Elements:**
|
|
1. **Log Directory Creation**: `host mkdir log 2>nul` - Creates log/ directory before SPOOL (suppresses error if exists)
|
|
2. **Dynamic Log Name**: `log/INSTALL_MARS_XXXX_<PDB_NAME>_YYYYMMDD_HH24MISS.log` (stored in log/ subdirectory)
|
|
3. **SYS_CONTEXT Usage**: Uses `SYS_CONTEXT('USERENV', 'CON_NAME')` instead of `DBA_PDBS` - no DBA privileges required
|
|
4. **SPOOL START**: After filename generation, before first PROMPT
|
|
5. **SPOOL OFF**: At the very end of the script
|
|
6. **SET ECHO OFF**: Prevents double output of PROMPT commands (shows only results, not the SQL commands themselves)
|
|
7. **ACCEPT Validation**: User confirmation required before execution (safety feature)
|
|
8. **ALTER SESSION SET CURRENT_SCHEMA** (optional): Sets working schema for package operations
|
|
9. **@@ Includes**: All sub-scripts executed via `@@` command
|
|
10. **track_package_versions.sql**: MANDATORY universal tracking script (must be included before verify)
|
|
11. **verify_packages_version.sql**: MANDATORY universal verification script (must be last step before completion)
|
|
12. **quit;**: Exits SQLcl/SQL*Plus after completion (important for automated deployments)
|
|
|
|
**SET ECHO OFF Benefits:**
|
|
- **Clean Output**: PROMPT messages appear only once in console and log files
|
|
- **Readability**: Log files are easier to read without SQL command echo
|
|
- **Professional**: Produces cleaner, more professional-looking installation logs
|
|
- **Consistency**: Works the same in both SQLcl and SQL*Plus
|
|
- **Sub-Scripts**: Must NOT include `SET ECHO ON` - they inherit setting from master script
|
|
|
|
**ACCEPT Validation Benefits:**
|
|
- **Safety Check**: Prevents accidental execution - requires explicit "YES" confirmation
|
|
- **User Control**: User must type YES (case-insensitive) to proceed with changes
|
|
- **Abort Capability**: Any other input or Ctrl+C safely aborts before database modifications
|
|
- **SQLcl & SQL*Plus Compatible**: Works identically in both tools, unlike PAUSE
|
|
- **Best Practice**: Mandatory for both installation and rollback master scripts
|
|
|
|
**Log File Storage:**
|
|
- **Directory**: All SPOOL logs automatically created in `log/` subdirectory
|
|
- **Naming Convention**: `log/INSTALL_MARS_XXXX_<PDB>_<timestamp>.log` or `log/ROLLBACK_MARS_XXXX_<PDB>_<timestamp>.log`
|
|
- **Auto-Creation**: Directory created by `host mkdir log 2>nul` command before SPOOL (MANDATORY)
|
|
- **Error Suppression**: `2>nul` suppresses "directory already exists" errors in PowerShell/Windows
|
|
- **Version Control**: Excluded via .gitignore (environment-specific files)
|
|
- **Importance**: Without `host mkdir`, SPOOL may fail if log/ directory doesn't exist
|
|
|
|
**Why `host mkdir log 2>nul` is mandatory:**
|
|
- **Reliability**: Ensures log/ directory exists before SPOOL attempts to write
|
|
- **Cross-Environment**: Works on fresh Git clones where log/ doesn't exist yet
|
|
- **No Errors**: Silently succeeds whether directory exists or not
|
|
- **Best Practice**: Prevents installation failures due to missing log directory
|
|
- **PowerShell Compatible**: Works in both PowerShell (pwsh.exe) and Windows CMD
|
|
|
|
---
|
|
9. **quit;**: Exits SQLcl/SQL*Plus after completion (important for automated deployments)
|
|
|
|
**SET ECHO OFF Benefits:**
|
|
- **Clean Output**: PROMPT messages appear only once in console and log files
|
|
- **Readability**: Log files are easier to read without SQL command echo
|
|
- **Professional**: Produces cleaner, more professional-looking installation logs
|
|
- **Consistency**: Works the same in both SQLcl and SQL*Plus
|
|
- **Sub-Scripts**: Must NOT include `SET ECHO ON` - they inherit setting from master script
|
|
|
|
**ACCEPT Validation Benefits:**
|
|
- **Safety Check**: Prevents accidental execution - requires explicit "YES" confirmation
|
|
- **User Control**: User must type YES (case-insensitive) to proceed with changes
|
|
- **Abort Capability**: Any other input or Ctrl+C safely aborts before database modifications
|
|
- **SQLcl & SQL*Plus Compatible**: Works identically in both tools, unlike PAUSE
|
|
- **Best Practice**: Mandatory for both installation and rollback master scripts
|
|
|
|
---
|
|
|
|
### Complete MARS Package Example
|
|
|
|
**MARS-835-PREHOOK** - Real-world example following all standards:
|
|
|
|
**File Structure:**
|
|
```
|
|
MARS_Packages/REL01_POST_DEACTIVATION/MARS-835-PREHOOK/
|
|
├── .gitignore
|
|
├── install_mars835_prehook.sql # Master install (uses universal scripts)
|
|
├── rollback_mars835_prehook.sql # Master rollback
|
|
├── 01_MARS_835_install_DATA_EXPORTER_SPEC.sql
|
|
├── 02_MARS_835_install_DATA_EXPORTER_BODY.sql
|
|
├── 91_MARS_835_rollback_DATA_EXPORTER_BODY.sql
|
|
├── 92_MARS_835_rollback_DATA_EXPORTER_SPEC.sql
|
|
├── track_package_versions.sql # ✅ Universal tracking
|
|
├── verify_packages_version.sql # ✅ Universal verification
|
|
├── README.md
|
|
├── rollback_version/
|
|
│ ├── DATA_EXPORTER.pkg # v2.1.1 (before changes)
|
|
│ └── DATA_EXPORTER.pkb
|
|
├── new_version/
|
|
│ ├── DATA_EXPORTER.pkg # v2.2.0 (after changes)
|
|
│ └── DATA_EXPORTER.pkb
|
|
└── log/ # Auto-created by install script
|
|
```
|
|
|
|
**track_package_versions.sql** (edited for this MARS issue):
|
|
```sql
|
|
-- ===================================================================
|
|
-- PACKAGE LIST - Edit this array to specify packages to track
|
|
-- ===================================================================
|
|
vPackageList t_string_array := t_string_array(
|
|
'CT_MRDS.DATA_EXPORTER' -- Only package modified in MARS-835
|
|
);
|
|
-- ===================================================================
|
|
```
|
|
|
|
**install_mars835_prehook.sql** (master script):
|
|
```sql
|
|
-- ===================================================================
|
|
-- MARS-835-PREHOOK INSTALL SCRIPT
|
|
-- ===================================================================
|
|
|
|
host mkdir log 2>nul
|
|
|
|
var filename VARCHAR2(100)
|
|
BEGIN
|
|
:filename := 'log/INSTALL_MARS_835_PREHOOK_' || SYS_CONTEXT('USERENV', 'CON_NAME') || '_' || TO_CHAR(SYSDATE,'YYYYMMDD_HH24MISS') || '.log';
|
|
END;
|
|
/
|
|
column filename new_value _filename
|
|
select :filename filename from dual;
|
|
spool &_filename
|
|
|
|
SET ECHO OFF
|
|
SET TIMING ON
|
|
SET SERVEROUTPUT ON SIZE UNLIMITED
|
|
|
|
PROMPT =========================================================================
|
|
PROMPT MARS-835-PREHOOK: DRY Refactoring for DATA_EXPORTER
|
|
PROMPT =========================================================================
|
|
|
|
ACCEPT continue CHAR PROMPT 'Type YES to continue: '
|
|
WHENEVER SQLERROR EXIT SQL.SQLCODE
|
|
BEGIN
|
|
IF UPPER(TRIM('&continue')) != 'YES' THEN
|
|
RAISE_APPLICATION_ERROR(-20001, 'Installation aborted');
|
|
END IF;
|
|
END;
|
|
/
|
|
WHENEVER SQLERROR CONTINUE
|
|
|
|
PROMPT
|
|
PROMPT Step 1: Deploy DATA_EXPORTER Package Specification (v2.2.0)
|
|
@@01_MARS_835_install_DATA_EXPORTER_SPEC.sql
|
|
|
|
PROMPT
|
|
PROMPT Step 2: Deploy DATA_EXPORTER Package Body (v2.2.0)
|
|
@@02_MARS_835_install_DATA_EXPORTER_BODY.sql
|
|
|
|
PROMPT
|
|
PROMPT Step 3: Track Package Versions
|
|
@@track_package_versions.sql
|
|
|
|
PROMPT
|
|
PROMPT Step 4: Verify Package Versions
|
|
@@verify_packages_version.sql
|
|
|
|
PROMPT
|
|
PROMPT =========================================================================
|
|
PROMPT MARS-835-PREHOOK Installation - COMPLETED
|
|
PROMPT =========================================================================
|
|
|
|
spool off
|
|
quit;
|
|
```
|
|
|
|
**Why this is the correct pattern:**
|
|
- ✅ Uses universal `track_package_versions.sql` (no custom 04_MARS_835_track_version.sql)
|
|
- ✅ Uses universal `verify_packages_version.sql` (no custom 03_MARS_835_verify_installation.sql)
|
|
- ✅ Tracking happens AFTER deployment (Step 3)
|
|
- ✅ Verification happens LAST (Step 4) to confirm everything is correct
|
|
- ✅ Single configuration point (edit package list in track_package_versions.sql)
|
|
- ✅ Consistent with ALL other MARS packages
|
|
- ✅ Easy to copy/paste for new MARS issues
|
|
|
|
---
|
|
|
|
### SPOOL Logging Benefits
|
|
|
|
**Why SPOOL is mandatory:**
|
|
|
|
1. **Audit Trail** - Complete record of all installation activities
|
|
2. **Debugging** - Capture errors, warnings, and execution details
|
|
3. **Compliance** - Required for production deployments
|
|
4. **Troubleshooting** - Review what actually happened during installation
|
|
5. **Documentation** - Proof of successful deployment
|
|
|
|
**Log File Contains:**
|
|
- All PROMPT messages
|
|
- SQL execution results
|
|
- Error messages (ORA-XXXXX)
|
|
- Timing information
|
|
- Package compilation status
|
|
- Version tracking confirmations
|
|
|
|
**Example Log File Name:**
|
|
```
|
|
log/INSTALL_MARS_1049_ggmichalski_20251126_143052.log
|
|
```
|
|
|
|
**Log Location:** `log/` subdirectory in MARS package root (auto-created by SPOOL)
|
|
|
|
---
|
|
|
|
### Creating Individual Installation Scripts
|
|
|
|
Each numbered script should be self-contained and focused:
|
|
|
|
**Example: `01_MARS_1049_install_CT_MRDS_ADD_ENCODING_COLUMN.sql`**
|
|
|
|
```sql
|
|
--=============================================================================================================================
|
|
-- MARS-1049: Add ENCODING Column to A_SOURCE_FILE_CONFIG Table
|
|
--=============================================================================================================================
|
|
-- Purpose: Add VARCHAR2(50) ENCODING column with UTF8 default
|
|
-- Author: Grzegorz Michalski
|
|
-- Date: 2025-11-24
|
|
-- Related: MARS-1049 CSV Encoding Support
|
|
--=============================================================================================================================
|
|
|
|
SET SERVEROUTPUT ON
|
|
|
|
PROMPT ========================================================================
|
|
PROMPT Adding ENCODING column to CT_MRDS.A_SOURCE_FILE_CONFIG
|
|
PROMPT ========================================================================
|
|
|
|
-- Add column
|
|
ALTER TABLE CT_MRDS.A_SOURCE_FILE_CONFIG
|
|
ADD (ENCODING VARCHAR2(50) DEFAULT 'UTF8');
|
|
|
|
-- Add comment
|
|
COMMENT ON COLUMN CT_MRDS.A_SOURCE_FILE_CONFIG.ENCODING IS
|
|
'Character encoding for CSV files (e.g., UTF8, WE8MSWIN1252)';
|
|
|
|
-- Verify change (check specific schema when installing as ADMIN)
|
|
SELECT COUNT(*) AS ENCODING_COLUMN_EXISTS
|
|
FROM ALL_TAB_COLUMNS
|
|
WHERE OWNER = 'CT_MRDS'
|
|
AND TABLE_NAME = 'A_SOURCE_FILE_CONFIG'
|
|
AND COLUMN_NAME = 'ENCODING';
|
|
|
|
PROMPT SUCCESS: ENCODING column added to A_SOURCE_FILE_CONFIG
|
|
|
|
--=============================================================================================================================
|
|
-- End of Script
|
|
--=============================================================================================================================
|
|
```
|
|
|
|
**Script Best Practices:**
|
|
- Clear header with purpose and metadata
|
|
- `SET SERVEROUTPUT ON` for debugging
|
|
- Descriptive PROMPT messages
|
|
- Verification queries after changes
|
|
- Success confirmation message
|
|
|
|
---
|
|
|
|
### Rollback Script Template
|
|
|
|
Always provide rollback capability:
|
|
|
|
```sql
|
|
-- ===================================================================
|
|
-- MARS-XXXX ROLLBACK SCRIPT: Brief Description
|
|
-- ===================================================================
|
|
-- Purpose: Rollback all changes from MARS-XXXX installation
|
|
-- Author: Grzegorz Michalski
|
|
-- Date: YYYY-MM-DD
|
|
|
|
-- Dynamic spool file generation (using SYS_CONTEXT - no DBA privileges required)
|
|
-- IMPORTANT: Ensure log/ directory exists before SPOOL (use host mkdir)
|
|
host mkdir log 2>nul
|
|
|
|
var filename VARCHAR2(100)
|
|
BEGIN
|
|
:filename := 'log/ROLLBACK_MARS_XXXX_' || SYS_CONTEXT('USERENV', 'CON_NAME') || '_' || TO_CHAR(SYSDATE,'YYYYMMDD_HH24MISS') || '.log';
|
|
END;
|
|
/
|
|
column filename new_value _filename
|
|
select :filename filename from dual;
|
|
spool &_filename
|
|
|
|
SET ECHO OFF
|
|
SET TIMING ON
|
|
SET SERVEROUTPUT ON SIZE UNLIMITED
|
|
SET PAUSE OFF
|
|
|
|
PROMPT =========================================================================
|
|
PROMPT MARS-XXXX: Rollback Package
|
|
PROMPT =========================================================================
|
|
PROMPT This will reverse all changes from MARS-XXXX installation
|
|
PROMPT
|
|
PROMPT Rollback steps:
|
|
PROMPT 1. Restore previous package version
|
|
PROMPT 2. Remove added columns/tables
|
|
PROMPT 3. Revert configuration changes
|
|
PROMPT =========================================================================
|
|
|
|
-- Confirm rollback with user
|
|
ACCEPT continue CHAR PROMPT 'Type YES to continue with rollback, or Ctrl+C to abort: '
|
|
WHENEVER SQLERROR EXIT SQL.SQLCODE
|
|
BEGIN
|
|
IF '&continue' IS NULL OR TRIM('&continue') IS NULL OR UPPER(TRIM('&continue')) != 'YES' THEN
|
|
RAISE_APPLICATION_ERROR(-20001, 'Rollback aborted by user');
|
|
END IF;
|
|
END;
|
|
/
|
|
WHENEVER SQLERROR CONTINUE
|
|
|
|
-- Execute rollback scripts in REVERSE order
|
|
@@92_MARS_XXXX_rollback_step2.sql
|
|
@@91_MARS_XXXX_rollback_step1.sql
|
|
|
|
PROMPT
|
|
PROMPT =========================================================================
|
|
PROMPT MARS-XXXX Rollback - COMPLETED
|
|
PROMPT =========================================================================
|
|
|
|
spool off
|
|
```
|
|
|
|
**Rollback Principles:**
|
|
- Execute scripts in **REVERSE order** (92, 91, not 91, 92)
|
|
- Undo changes from newest to oldest
|
|
- Restore previous package versions
|
|
- Remove added columns/tables
|
|
- Revert configuration changes
|
|
- Include verification step after rollback (@@verify_packages_version.sql)
|
|
|
|
**Rollback Communication Style:**
|
|
- ✅ **DO**: Use calm, professional tone describing what will be done
|
|
- ✅ **DO**: List specific rollback steps clearly
|
|
- ❌ **DON'T**: Use dramatic words like "WARNING", "CRITICAL IMPACT", "DANGER"
|
|
- ❌ **DON'T**: Create panic - rollback is a normal part of deployment process
|
|
- **Rationale**: Rollbacks happen when installations fail or need to be reversed. This is a standard procedure, not an emergency.
|
|
|
|
**Example - Professional vs. Dramatic:**
|
|
|
|
```sql
|
|
-- ✅ CORRECT - Professional and Clear
|
|
PROMPT This will reverse all changes from MARS-828 installation
|
|
PROMPT
|
|
PROMPT Rollback steps:
|
|
PROMPT 1. Remove validation trigger
|
|
PROMPT 2. Drop ARCHIVAL_STRATEGY and MINIMUM_AGE_MONTHS columns
|
|
PROMPT 3. Restore FILE_ARCHIVER package to v2.0.0
|
|
|
|
-- ❌ WRONG - Unnecessarily Dramatic
|
|
PROMPT WARNING: This will restore FILE_ARCHIVER to v2.0.0
|
|
PROMPT
|
|
PROMPT CRITICAL IMPACT:
|
|
PROMPT 1. All archival strategies revert to THRESHOLD_BASED
|
|
PROMPT 2. ARCHIVAL_STRATEGY and MINIMUM_AGE_MONTHS columns will be dropped
|
|
```
|
|
|
|
---
|
|
|
|
### Version Tracking Integration
|
|
|
|
Every MARS package should track package versions using the universal tracking script:
|
|
|
|
**Recommended Approach: Universal Tracking Script**
|
|
|
|
```sql
|
|
-- ===================================================================
|
|
-- Simple Package Version Tracking Script
|
|
-- ===================================================================
|
|
-- Purpose: Track specified Oracle package versions
|
|
-- Author: Grzegorz Michalski
|
|
-- Date: 2025-11-26
|
|
-- Version: 3.1.0 - List-Based Edition
|
|
--
|
|
-- USAGE:
|
|
-- 1. Edit package list below (add/remove packages as needed)
|
|
-- 2. Include in your install/rollback script: @@track_package_versions.sql
|
|
-- ===================================================================
|
|
|
|
SET SERVEROUTPUT ON;
|
|
|
|
DECLARE
|
|
TYPE t_package_rec IS RECORD (
|
|
owner VARCHAR2(50),
|
|
package_name VARCHAR2(50),
|
|
version VARCHAR2(50)
|
|
);
|
|
TYPE t_packages IS TABLE OF t_package_rec;
|
|
TYPE t_string_array IS TABLE OF VARCHAR2(100);
|
|
|
|
-- ===================================================================
|
|
-- PACKAGE LIST - Edit this array to specify packages to track
|
|
-- ===================================================================
|
|
-- Add or remove entries as needed for your MARS issue
|
|
-- Format: 'SCHEMA.PACKAGE_NAME'
|
|
-- ===================================================================
|
|
vPackageList t_string_array := t_string_array(
|
|
'CT_MRDS.FILE_MANAGER',
|
|
'ODS.FILE_MANAGER_ODS'
|
|
);
|
|
-- ===================================================================
|
|
|
|
vPackages t_packages := t_packages();
|
|
vVersion VARCHAR2(50);
|
|
vCount NUMBER := 0;
|
|
vOwner VARCHAR2(50);
|
|
vPackageName VARCHAR2(50);
|
|
vDotPos NUMBER;
|
|
BEGIN
|
|
DBMS_OUTPUT.PUT_LINE('========================================');
|
|
DBMS_OUTPUT.PUT_LINE('Package Version Tracking');
|
|
DBMS_OUTPUT.PUT_LINE('========================================');
|
|
|
|
-- Process each package in the list
|
|
FOR i IN 1..vPackageList.COUNT LOOP
|
|
vDotPos := INSTR(vPackageList(i), '.');
|
|
IF vDotPos > 0 THEN
|
|
vOwner := SUBSTR(vPackageList(i), 1, vDotPos - 1);
|
|
vPackageName := SUBSTR(vPackageList(i), vDotPos + 1);
|
|
|
|
-- Get package version
|
|
BEGIN
|
|
EXECUTE IMMEDIATE 'SELECT ' || vOwner || '.' || vPackageName || '.GET_VERSION() FROM DUAL' INTO vVersion;
|
|
vPackages.EXTEND;
|
|
vPackages(vPackages.COUNT).owner := vOwner;
|
|
vPackages(vPackages.COUNT).package_name := vPackageName;
|
|
vPackages(vPackages.COUNT).version := vVersion;
|
|
|
|
-- Track in ENV_MANAGER
|
|
BEGIN
|
|
CT_MRDS.ENV_MANAGER.TRACK_PACKAGE_VERSION(
|
|
pPackageOwner => vOwner,
|
|
pPackageName => vPackageName,
|
|
pPackageVersion => vVersion,
|
|
pPackageBuildDate => TO_CHAR(SYSDATE, 'YYYY-MM-DD HH24:MI:SS'),
|
|
pPackageAuthor => 'Grzegorz Michalski'
|
|
);
|
|
vCount := vCount + 1;
|
|
EXCEPTION
|
|
WHEN OTHERS THEN NULL; -- Continue even if tracking fails
|
|
END;
|
|
EXCEPTION
|
|
WHEN OTHERS THEN NULL; -- Skip packages that fail
|
|
END;
|
|
END IF;
|
|
END LOOP;
|
|
|
|
-- Display results
|
|
IF vPackages.COUNT > 0 THEN
|
|
DBMS_OUTPUT.PUT_LINE('Packages tracked: ' || vCount || ' of ' || vPackages.COUNT);
|
|
DBMS_OUTPUT.PUT_LINE('');
|
|
|
|
FOR i IN 1..vPackages.COUNT LOOP
|
|
DBMS_OUTPUT.PUT_LINE(vPackages(i).owner || '.' || vPackages(i).package_name || ' = ' || vPackages(i).version);
|
|
END LOOP;
|
|
ELSE
|
|
DBMS_OUTPUT.PUT_LINE('No packages found in list');
|
|
END IF;
|
|
|
|
DBMS_OUTPUT.PUT_LINE('========================================');
|
|
END;
|
|
/
|
|
```
|
|
|
|
**Key Benefits:**
|
|
- **List-Based**: Simply edit the `vPackageList` array to add/remove packages
|
|
- **Automatic Version Detection**: Calls `GET_VERSION()` for each package
|
|
- **Error Tolerant**: Continues even if individual packages fail
|
|
- **Summary Output**: Shows which packages were successfully tracked
|
|
- **Reusable**: Same script can be used across all MARS packages
|
|
|
|
---
|
|
|
|
### Package Verification Script
|
|
|
|
Every MARS package should include a universal verification script to check all tracked packages for untracked changes:
|
|
|
|
**Recommended: `verify_packages_version.sql`**
|
|
|
|
```sql
|
|
-- ===================================================================
|
|
-- Universal Package Version Verification Script
|
|
-- ===================================================================
|
|
-- Purpose: Verify all tracked Oracle packages for code changes
|
|
-- Author: Grzegorz Michalski
|
|
-- Date: 2025-11-25
|
|
-- Version: 1.0.0
|
|
--
|
|
-- USAGE:
|
|
-- Include at the end of install/rollback scripts: @@verify_packages_version.sql
|
|
--
|
|
-- OUTPUT:
|
|
-- - List of all tracked packages with their current status
|
|
-- - OK: Package has not changed since last tracking
|
|
-- - WARNING: Package code changed without version update
|
|
-- ===================================================================
|
|
|
|
SET LINESIZE 200
|
|
SET PAGESIZE 1000
|
|
SET FEEDBACK OFF
|
|
|
|
PROMPT
|
|
PROMPT ========================================
|
|
PROMPT Package Version Verification
|
|
PROMPT ========================================
|
|
PROMPT
|
|
|
|
COLUMN PACKAGE_OWNER FORMAT A15
|
|
COLUMN PACKAGE_NAME FORMAT A20
|
|
COLUMN VERSION FORMAT A10
|
|
COLUMN STATUS FORMAT A80
|
|
|
|
SELECT
|
|
PACKAGE_OWNER,
|
|
PACKAGE_NAME,
|
|
PACKAGE_VERSION AS VERSION,
|
|
CT_MRDS.ENV_MANAGER.CHECK_PACKAGE_CHANGES(PACKAGE_OWNER, PACKAGE_NAME) AS STATUS
|
|
FROM (
|
|
SELECT
|
|
PACKAGE_OWNER,
|
|
PACKAGE_NAME,
|
|
PACKAGE_VERSION,
|
|
ROW_NUMBER() OVER (PARTITION BY PACKAGE_OWNER, PACKAGE_NAME ORDER BY TRACKING_DATE DESC) AS RN
|
|
FROM CT_MRDS.A_PACKAGE_VERSION_TRACKING
|
|
)
|
|
WHERE RN = 1
|
|
ORDER BY PACKAGE_OWNER, PACKAGE_NAME;
|
|
|
|
PROMPT
|
|
PROMPT ========================================
|
|
PROMPT Verification Complete
|
|
PROMPT ========================================
|
|
PROMPT
|
|
PROMPT Legend:
|
|
PROMPT OK - Package has not changed since last tracking
|
|
PROMPT WARNING - Package code changed without version update
|
|
PROMPT
|
|
PROMPT For detailed hash information, use:
|
|
PROMPT SELECT ENV_MANAGER.GET_PACKAGE_HASH_INFO('OWNER', 'PACKAGE') FROM DUAL;
|
|
PROMPT ========================================
|
|
|
|
SET FEEDBACK ON
|
|
```
|
|
|
|
**Key Features:**
|
|
- **Universal**: Checks ALL packages in A_PACKAGE_VERSION_TRACKING table
|
|
- **Latest Version**: Uses ROW_NUMBER() to get most recent tracking record for each package
|
|
- **Status Display**: Shows OK or WARNING for each package
|
|
- **Formatted Output**: Clean, readable table format with column alignment
|
|
- **Reusable**: Same script works for all MARS packages without modification
|
|
- **Legend**: Includes helpful legend explaining OK vs WARNING status
|
|
|
|
**Usage in Master Scripts:**
|
|
```sql
|
|
PROMPT
|
|
PROMPT === Step 3: Verify all tracked packages ===
|
|
@@verify_packages_version.sql
|
|
```
|
|
|
|
**Benefits over Package-Specific Verification:**
|
|
- No need to edit script for each MARS package
|
|
- Automatically detects all tracked packages
|
|
- Consistent verification across all installations
|
|
- Easier to maintain (single script for all packages)
|
|
|
|
---
|
|
|
|
### Package README Template
|
|
|
|
Every MARS package MUST include README.md:
|
|
|
|
```markdown
|
|
# MARS-XXXX: Brief Description
|
|
|
|
## Overview
|
|
Detailed description of what this package does and why it's needed.
|
|
|
|
## Contents
|
|
- `install_marsXXXX.sql` - Master installation script with SPOOL logging
|
|
- `rollback_marsXXXX.sql` - Master rollback script
|
|
- `01_MARS_XXXX_*.sql` - Individual installation scripts
|
|
- `91_MARS_XXXX_*.sql` - Individual rollback scripts
|
|
|
|
## Prerequisites
|
|
- Oracle Database 23ai
|
|
- Required package versions (e.g., ENV_MANAGER v3.1.0+)
|
|
- Schema privileges needed
|
|
|
|
## Installation
|
|
|
|
### Option 1: Master Script (Recommended)
|
|
```powershell
|
|
# IMPORTANT: Execute as ADMIN user for proper privilege management
|
|
Get-Content "MARS_Packages/REL01/MARS-XXXX/install_marsXXXX.sql" | sql "ADMIN/password@service"
|
|
|
|
# Log file created: INSTALL_MARS_XXXX_<PDB>_<timestamp>.log
|
|
```
|
|
|
|
### Option 2: Individual Scripts
|
|
```powershell
|
|
# IMPORTANT: Execute as ADMIN user
|
|
Get-Content "01_MARS_XXXX_*.sql" | sql "ADMIN/password@service"
|
|
Get-Content "02_MARS_XXXX_*.sql" | sql "ADMIN/password@service"
|
|
# ... etc
|
|
```
|
|
|
|
## Verification
|
|
```sql
|
|
-- Verify package versions
|
|
SELECT PACKAGE_NAME.GET_VERSION() FROM DUAL;
|
|
|
|
-- Check for errors (ADMIN user checks specific schema)
|
|
SELECT * FROM ALL_ERRORS
|
|
WHERE OWNER = 'CT_MRDS' -- Replace with target schema
|
|
AND NAME = 'PACKAGE_NAME';
|
|
```
|
|
|
|
## Rollback
|
|
```powershell
|
|
# IMPORTANT: Execute as ADMIN user
|
|
Get-Content "MARS_Packages/REL01/MARS-XXXX/rollback_marsXXXX.sql" | sql "ADMIN/password@service"
|
|
```
|
|
|
|
## Expected Changes
|
|
- Package X: v1.0.0 → v1.1.0
|
|
- Table Y: Added COLUMN_Z
|
|
- Configuration: Updated DEFAULT_VALUE
|
|
|
|
## Testing
|
|
Describe how to test the changes after installation.
|
|
|
|
## Known Issues
|
|
List any known limitations or issues.
|
|
|
|
## Related
|
|
- MARS-YYYY: Related package
|
|
- Confluence: Link to detailed documentation
|
|
```
|
|
|
|
---
|
|
|
|
### MARS Package Checklist
|
|
|
|
Before creating a MARS package, ensure:
|
|
|
|
- [ ] **Directory Structure**: Created `log/` and `mock_data/` subdirectories (if needed)
|
|
- [ ] **.gitignore file**: Created with standardized exclusions (confluence/, log/, test/, mock_data/)
|
|
- [ ] **Author field**: All scripts have `Author: Grzegorz Michalski`
|
|
- [ ] **ADMIN user**: All installation instructions specify ADMIN user connection
|
|
- [ ] All individual scripts numbered correctly (01-89, 91-99)
|
|
- [ ] Master install script includes SPOOL logging to `log/` directory
|
|
- [ ] Master rollback script includes SPOOL logging to `log/` directory
|
|
- [ ] SPOOL filenames use dynamic PDB name and timestamp with `log/` prefix
|
|
- [ ] **ACCEPT validation**: Master scripts require explicit "YES" confirmation
|
|
- [ ] **quit; command**: Master scripts end with quit; for clean exit
|
|
- [ ] All scripts have proper headers with metadata
|
|
- [ ] Version tracking scripts included (in test/ subfolder)
|
|
- [ ] Verification scripts confirm changes (in test/ subfolder)
|
|
- [ ] README.md documents installation process
|
|
- [ ] Rollback scripts reverse all changes
|
|
- [ ] Rollback includes verification step (@@test/verify_packages_version.sql)
|
|
- [ ] **rollback_version/ folder**: Contains backup of objects before changes (if modifying packages)
|
|
- [ ] **new_version/ folder**: Contains updated objects after changes (if modifying packages)
|
|
- [ ] **test/ folder**: All test files and verification scripts organized in subfolder
|
|
- [ ] **log/ folder**: SPOOL log files automatically created by master scripts
|
|
- [ ] **mock_data/ folder**: Mock data files organized (if applicable)
|
|
- [ ] Tested in DEV environment
|
|
- [ ] Log files reviewed for errors (in log/ subdirectory)
|
|
- [ ] **Source repository updated**: Changed packages copied to `MARS_Packages/mrds_elt-dev-database/mrds_elt-dev-database/database/`
|
|
- [ ] Git commit with descriptive message (log/, mock_data/ excluded via .gitignore)
|
|
|
|
---
|
|
|
|
### Example 1: Complete MARS-1046 Package (Package Modification)
|
|
|
|
Real-world example from MARS-1046 (ISO 8601 Date Format Fix):
|
|
|
|
**Structure:**
|
|
```
|
|
MARS_Packages/REL01/MARS-1046/
|
|
├── install_mars1046.sql # Master with SPOOL, ACCEPT, quit;
|
|
├── rollback_mars1046.sql # Master rollback with ACCEPT, quit;
|
|
├── 01_MARS_1046_install_CT_MRDS_FILE_MANAGER_SPEC.sql
|
|
├── 02_MARS_1046_install_CT_MRDS_FILE_MANAGER_BODY.sql
|
|
├── 91_MARS_1046_rollback_CT_MRDS_FILE_MANAGER_BODY.sql
|
|
├── 92_MARS_1046_rollback_CT_MRDS_FILE_MANAGER_SPEC.sql
|
|
├── track_package_versions.sql # Version tracking
|
|
├── verify_packages_version.sql # Package verification
|
|
├── README.md # Comprehensive documentation
|
|
├── rollback_version/ # v3.3.0 backup for rollback
|
|
│ ├── FILE_MANAGER.pkg
|
|
│ └── FILE_MANAGER.pkb
|
|
├── new_version/ # v3.3.1 updated packages
|
|
│ ├── FILE_MANAGER.pkg
|
|
│ └── FILE_MANAGER.pkb
|
|
├── test/ # All test artifacts
|
|
│ ├── test_mars1046.sql # Unit tests (7/7 passed)
|
|
│ ├── TEST_RESULTS.md # Test documentation
|
|
│ ├── iso8601_test_data.csv # Test data (full format)
|
|
│ ├── iso8601_test_data_simple.csv # Test data (simple format)
|
|
│ ├── create_iso8601_test_template.sql # Template table creation
|
|
│ ├── configure_iso8601_test.sql # Date format configuration
|
|
│ ├── process_iso8601_test.sql # E2E test
|
|
│ └── INSTALL_MARS_1046_*.log # Log files (3 iterations)
|
|
└── log/ # Optional log storage
|
|
```
|
|
|
|
**Key Features:**
|
|
- SPOOL logging: `INSTALL_MARS_1046_<PDB>_<timestamp>.log`
|
|
- ACCEPT validation: Requires explicit "YES" to proceed (both install & rollback)
|
|
- quit; command: Clean SQLcl exit after completion
|
|
- Version folders: rollback_version/ (v3.3.0) and new_version/ (v3.3.1)
|
|
- Test subfolder: All test files organized separately
|
|
- 4-step workflow: Install packages → Track version → Verify packages → quit
|
|
- Full rollback: Restore to previous version with verification
|
|
- Comprehensive README: Problem, solution, testing, verification
|
|
- Track & verify scripts: Universal scripts work for any package
|
|
|
|
---
|
|
|
|
### Example 2: Complete MARS-1049-ADHOC Package (Configuration Change)
|
|
|
|
Real-world example from MARS-1049-ADHOC (CSDB External Tables):
|
|
|
|
**Structure:**
|
|
```
|
|
MARS_Packages/REL01/MARS-1049-ADHOC/
|
|
├── install_mars1049_adhoc.sql # Master with SPOOL
|
|
├── 00_MARS_1049_ADHOC_update_encoding.sql # Update config
|
|
├── 01_MARS_1049_ADHOC_drop_external_tables.sql # Drop tables
|
|
├── 02_MARS_1049_ADHOC_recreate_external_tables.sql # Recreate with encoding
|
|
├── 03_MARS_1049_ADHOC_verify_external_tables.sql # Verify creation
|
|
└── README.md # Documentation
|
|
```
|
|
|
|
**Key Features:**
|
|
- SPOOL logging: `INSTALL_MARS_1049_ADHOC_<PDB>_<timestamp>.log`
|
|
- Numbered sequence: 00 → 01 → 02 → 03
|
|
- No rollback (external tables are metadata-only)
|
|
- No version folders (no package modifications)
|
|
- Verification included
|
|
- Clear README with installation options
|
|
|
|
---
|
|
|
|
## Post-Installation File Organization
|
|
|
|
### Organizing Test Files and Logs
|
|
|
|
After successful installation and verification, organize files for clean Git commit:
|
|
|
|
**Step 1: Create test/ subfolder**
|
|
```powershell
|
|
# Create test directory if it doesn't exist
|
|
New-Item -ItemType Directory -Force -Path "test" | Out-Null
|
|
```
|
|
|
|
**Step 2: Move test-related files**
|
|
```powershell
|
|
# Move test scripts and data
|
|
Move-Item -Path "test_*.sql" -Destination "test" -Force
|
|
Move-Item -Path "*_test_*.csv" -Destination "test" -Force
|
|
Move-Item -Path "TEST_RESULTS.md" -Destination "test" -Force
|
|
```
|
|
|
|
**Step 3: Move log files**
|
|
```powershell
|
|
# Option 1: Move to test/ subfolder
|
|
Move-Item -Path "*.log" -Destination "test" -Force
|
|
|
|
# Option 2: Create dedicated log/ subfolder
|
|
New-Item -ItemType Directory -Force -Path "log" | Out-Null
|
|
Move-Item -Path "*.log" -Destination "log" -Force
|
|
```
|
|
|
|
**Step 4: Verify clean structure**
|
|
```powershell
|
|
# Check root directory - should only have deployment scripts and README
|
|
Get-ChildItem | Where-Object { $_.Name -notmatch "^(01|02|91|92|install|rollback|README|rollback_version|new_version|test|log)" }
|
|
# Expected: No output (all non-deployment files moved)
|
|
```
|
|
|
|
**Final MARS Package Structure:**
|
|
```
|
|
MARS_Packages/REL01/MARS-XXXX/
|
|
├── install_marsXXXX.sql # Master installation
|
|
├── rollback_marsXXXX.sql # Master rollback
|
|
├── 01_MARS_XXXX_*.sql # Installation scripts
|
|
├── 02_MARS_XXXX_*.sql
|
|
├── 91_MARS_XXXX_*.sql # Rollback scripts
|
|
├── 92_MARS_XXXX_*.sql
|
|
├── track_package_versions.sql
|
|
├── verify_packages_version.sql
|
|
├── README.md # Documentation
|
|
├── rollback_version/ # Backup packages
|
|
├── new_version/ # Updated packages
|
|
└── test/ # ALL test artifacts
|
|
├── test_marsXXXX.sql
|
|
├── TEST_RESULTS.md
|
|
├── *.csv (test data)
|
|
```
|
|
|
|
**Benefits:**
|
|
- **Clean Git commits**: Only deployment-relevant files in root
|
|
- **Easy testing**: All test materials in one place
|
|
- **Reproducibility**: Test setup can be recreated from test/ folder
|
|
- **Documentation**: Log files preserved for troubleshooting
|
|
- **Professional**: Organized structure for code review
|
|
|
|
---
|
|
|
|
## Best Practices
|
|
|
|
### 1. Always Update Version Before Deployment
|
|
|
|
**DO:**
|
|
```sql
|
|
-- Update version first, then deploy
|
|
PACKAGE_VERSION := '3.3.0'; -- Updated
|
|
PACKAGE_BUILD_DATE := '2025-10-22 21:00:00'; -- Updated
|
|
VERSION_HISTORY := '3.3.0 (2025-10-22): New feature...' || CHR(13)||CHR(10) || ...
|
|
```
|
|
|
|
**DON'T:**
|
|
```sql
|
|
-- Deploy changes without updating version
|
|
-- This triggers "untracked changes" warning
|
|
```
|
|
|
|
---
|
|
|
|
### 2. Use Descriptive Version History
|
|
|
|
**DO:**
|
|
```sql
|
|
'3.3.0 (2025-10-22): Added EXPORT_HISTORICAL_DATA procedure for Parquet exports with Hive partitioning'
|
|
```
|
|
|
|
**DON'T:**
|
|
```sql
|
|
'3.3.0 (2025-10-22): Updates' -- Too vague
|
|
```
|
|
|
|
---
|
|
|
|
### 3. Deploy SPEC Before BODY
|
|
|
|
**Correct Order:**
|
|
1. Deploy PACKAGE.pkg (specification)
|
|
2. Deploy PACKAGE.pkb (body)
|
|
3. Track version
|
|
|
|
**Rationale:** BODY depends on SPEC, deploying SPEC first ensures clean compilation.
|
|
|
|
---
|
|
|
|
### 4. Test Before Production Deployment
|
|
|
|
1. Deploy to DEV environment first
|
|
2. Run unit tests
|
|
3. Verify functionality
|
|
4. Check for performance issues
|
|
5. Deploy to PROD only after validation
|
|
|
|
---
|
|
|
|
### 5. Document Breaking Changes
|
|
|
|
For MAJOR version increments, always document:
|
|
- What changed
|
|
- Why it changed
|
|
- Migration path for existing code
|
|
- Example of old vs new usage
|
|
|
|
---
|
|
|
|
### 6. Use Batch Deployment Scripts
|
|
|
|
For multiple packages, create deployment script:
|
|
|
|
```powershell
|
|
# deploy_all_packages.ps1
|
|
$packages = @('ENV_MANAGER', 'FILE_MANAGER', 'DATA_EXPORTER', 'FILE_ARCHIVER')
|
|
|
|
foreach ($pkg in $packages) {
|
|
Write-Host "Deploying $pkg..."
|
|
Get-Content "database\CT_MRDS\packages\${pkg}.pkg" | sql "CT_MRDS/password@service"
|
|
Get-Content "database\CT_MRDS\packages\${pkg}.pkb" | sql "CT_MRDS/password@service"
|
|
}
|
|
|
|
# Track all packages
|
|
Get-Content "database\scripts\track_all_packages.sql" | sql "CT_MRDS/password@service"
|
|
```
|
|
|
|
---
|
|
|
|
### 7. Regular Change Detection Audits
|
|
|
|
Run periodic checks to catch untracked modifications:
|
|
|
|
```sql
|
|
-- Check all packages for changes
|
|
@database/scripts/check_package_changes_all.sql
|
|
```
|
|
|
|
Schedule this as part of weekly code review process.
|
|
|
|
---
|
|
|
|
## Quick Reference
|
|
|
|
### Essential Commands
|
|
|
|
| Task | Command |
|
|
|------|---------|
|
|
| **Check current version** | `SELECT PACKAGE_NAME.GET_VERSION() FROM DUAL;` |
|
|
| **Check build info** | `SELECT PACKAGE_NAME.GET_BUILD_INFO() FROM DUAL;` |
|
|
| **Check for changes** | `SELECT ENV_MANAGER.CHECK_PACKAGE_CHANGES('OWNER', 'PACKAGE') FROM DUAL;` |
|
|
| **Get hash info** | `SELECT ENV_MANAGER.GET_PACKAGE_HASH_INFO('OWNER', 'PACKAGE') FROM DUAL;` |
|
|
| **Track version** | `CALL ENV_MANAGER.TRACK_PACKAGE_VERSION('OWNER', 'PKG', 'VER', 'DATE', 'AUTHOR');` |
|
|
| **Check errors** | `SELECT * FROM ALL_ERRORS WHERE OWNER = 'CT_MRDS' AND NAME = 'PACKAGE_NAME';` |
|
|
| **View tracking history** | `SELECT * FROM A_PACKAGE_VERSION_TRACKING WHERE PACKAGE_NAME = 'X' ORDER BY TRACKING_DATE DESC;` |
|
|
|
|
---
|
|
|
|
### Version Number Examples
|
|
|
|
| Current | Bug Fix | Feature | Breaking |
|
|
|---------|---------|---------|----------|
|
|
| 1.0.0 | 1.0.1 | 1.1.0 | 2.0.0 |
|
|
| 2.5.3 | 2.5.4 | 2.6.0 | 3.0.0 |
|
|
| 3.2.0 | 3.2.1 | 3.3.0 | 4.0.0 |
|
|
|
|
---
|
|
|
|
### Deployment Checklist
|
|
|
|
- [ ] Check current package status (`CHECK_PACKAGE_CHANGES`)
|
|
- [ ] Make code changes in local files
|
|
- [ ] Update `PACKAGE_VERSION` constant (increment appropriately)
|
|
- [ ] Update `PACKAGE_BUILD_DATE` constant (current timestamp)
|
|
- [ ] Add entry to `VERSION_HISTORY` constant
|
|
- [ ] Deploy SPEC file
|
|
- [ ] Deploy BODY file
|
|
- [ ] Check for compilation errors (`ALL_ERRORS` with OWNER filter when using ADMIN)
|
|
- [ ] Track new version (`TRACK_PACKAGE_VERSION`)
|
|
- [ ] Verify deployment (`GET_BUILD_INFO`, `CHECK_PACKAGE_CHANGES`)
|
|
- [ ] **Update source repository** - Copy updated packages to `MARS_Packages/mrds_elt-dev-database/mrds_elt-dev-database/database/`
|
|
- [ ] Update documentation (if API changed)
|
|
- [ ] Commit changes to Git
|
|
- [ ] Notify team (if breaking changes)
|
|
|
|
---
|
|
|
|
## Related Documentation
|
|
|
|
- [Package Versioning Guide](PACKAGE_VERSIONING_README.md) - Overview of versioning system
|
|
- [Package Hash Tracking Guide](PACKAGE_HASH_TRACKING_GUIDE.md) - Technical details of hash system
|
|
- [Package Hash Quick Guide](PACKAGE_HASH_QUICK_GUIDE.md) - Quick reference for hash commands
|
|
- [Developer Quick Guide](../database/DEVELOPER_QUICK_GUIDE.md) - General development guidelines
|
|
|
|
---
|
|
|
|
## Support
|
|
|
|
For questions or issues with the deployment process:
|
|
|
|
1. Check [Troubleshooting](#troubleshooting) section above
|
|
2. Review package documentation: `SELECT GET_PACKAGE_DOCUMENTATION('PACKAGE_NAME', 'SCHEMA') FROM DUAL;`
|
|
3. Check process logs: `SELECT * FROM A_PROCESS_LOG WHERE LOG_TIMESTAMP > SYSDATE - 1 ORDER BY LOG_TIMESTAMP DESC;`
|
|
4. Contact database team lead
|
|
|
|
---
|
|
|
|
**Last Updated:** 2025-10-22
|
|
**Document Version:** 1.0.0
|
|
**System Version:** ENV_MANAGER 3.1.0+
|