← ClaudeAtlas

managing-azure-sql-migrationslisted

Manages versioned, idempotent Azure SQL migrations that run on every deployment via sqlcmd in GitHub Actions. Provides the migration-history tracking table, the guard-clause template every migration uses, and the workflow step that installs sqlcmd on ubuntu-24.04, manages the SQL firewall with trap cleanup, and runs all files in alphabetical order. Use when adding a new SQL migration, setting up the migration system on a new project, or fixing CI failures like "sqlcmd not found", "gpg cannot open /dev/tty", or "Multiple files found matching pattern *.sql".
alexpizarro/azure-lean-stack-skills · ★ 1 · DevOps & Infrastructure · score 72
Install: claude install-skill alexpizarro/azure-lean-stack-skills
# Managing Azure SQL Migrations Idempotent, roll-forward SQL migrations run on every deploy via `sqlcmd`. The migration system uses a `__MigrationHistory` table for tracking, guard-clause migrations to make every run safe, and a workflow step that handles the operational quirks of running `sqlcmd` on ubuntu-24.04 in GitHub Actions. ## When to invoke - Adding a new migration file - Bootstrapping the migration system on a new project - Fixing a CI failure related to SQL migrations ## File naming ``` infra/sql/migrations/ ├── 000_migration_history.sql # tracking table — always runs first ├── 001_create_items_table.sql # initial schema (pre-tracking guard ok) ├── 002_add_user_id_to_items.sql # guarded by __MigrationHistory ├── 003_seed_demo_data.sql # also guarded └── ... ``` Pattern: `{NNN}_{snake_case_description}.sql`. Zero-padded, alphabetical order = execution order. ## Guard clause template Every migration from `002` onward MUST use this pattern: ```sql IF NOT EXISTS ( SELECT 1 FROM dbo.__MigrationHistory WHERE MigrationId = 'NNN_describe_change' ) BEGIN -- DDL here (CREATE TABLE, ALTER TABLE, INSERT, MERGE, etc.) INSERT INTO dbo.__MigrationHistory (MigrationId) VALUES ('NNN_describe_change'); PRINT 'Migration NNN_describe_change applied.'; END ELSE BEGIN PRINT 'Migration NNN_describe_change already applied — skipping.'; END ``` The exception is `001_create_items_table.sql`, which uses `IF NOT EXISTS (SELECT * FROM sys.t