From 31c5746e5bb83a611fc7bb9f9201b08c367e010a Mon Sep 17 00:00:00 2001 From: Scott Pouliot Date: Tue, 19 May 2026 17:43:30 -0400 Subject: [PATCH] Guard ShopWorker drops in AddAppointmentReminderSentAt migration with IF EXISTS Prod and dev databases diverged on whether ShopWorker tables and indexes exist, causing unconditional DROP statements to fail on prod. Replaced all individual DropForeignKey/DropTable/DropIndex/DropColumn calls with a single SQL block using IF EXISTS guards so the migration runs safely regardless of DB state. Co-Authored-By: Claude Sonnet 4.6 --- ...0519151303_AddAppointmentReminderSentAt.cs | 67 +++++++------------ 1 file changed, 26 insertions(+), 41 deletions(-) diff --git a/src/PowderCoating.Infrastructure/Migrations/20260519151303_AddAppointmentReminderSentAt.cs b/src/PowderCoating.Infrastructure/Migrations/20260519151303_AddAppointmentReminderSentAt.cs index 94915cc..aba4627 100644 --- a/src/PowderCoating.Infrastructure/Migrations/20260519151303_AddAppointmentReminderSentAt.cs +++ b/src/PowderCoating.Infrastructure/Migrations/20260519151303_AddAppointmentReminderSentAt.cs @@ -11,47 +11,32 @@ namespace PowderCoating.Infrastructure.Migrations /// protected override void Up(MigrationBuilder migrationBuilder) { - migrationBuilder.DropForeignKey( - name: "FK_Jobs_ShopWorkers_ShopWorkerId", - table: "Jobs"); - - migrationBuilder.DropForeignKey( - name: "FK_JobTimeEntries_ShopWorkers_ShopWorkerId", - table: "JobTimeEntries"); - - migrationBuilder.DropForeignKey( - name: "FK_MaintenanceRecords_ShopWorkers_ShopWorkerId", - table: "MaintenanceRecords"); - - migrationBuilder.DropTable( - name: "ShopWorkerRoleCosts"); - - migrationBuilder.DropTable( - name: "ShopWorkers"); - - migrationBuilder.DropIndex( - name: "IX_MaintenanceRecords_ShopWorkerId", - table: "MaintenanceRecords"); - - migrationBuilder.DropIndex( - name: "IX_JobTimeEntries_ShopWorkerId", - table: "JobTimeEntries"); - - migrationBuilder.DropIndex( - name: "IX_Jobs_ShopWorkerId", - table: "Jobs"); - - migrationBuilder.DropColumn( - name: "ShopWorkerId", - table: "MaintenanceRecords"); - - migrationBuilder.DropColumn( - name: "ShopWorkerId", - table: "JobTimeEntries"); - - migrationBuilder.DropColumn( - name: "ShopWorkerId", - table: "Jobs"); + // Use IF EXISTS guards for all ShopWorker drops — prod and dev diverged on whether + // these objects exist, so unconditional drops would fail on whichever DB is missing them. + migrationBuilder.Sql(@" + IF EXISTS (SELECT 1 FROM sys.foreign_keys WHERE name = 'FK_Jobs_ShopWorkers_ShopWorkerId') + ALTER TABLE [Jobs] DROP CONSTRAINT [FK_Jobs_ShopWorkers_ShopWorkerId]; + IF EXISTS (SELECT 1 FROM sys.foreign_keys WHERE name = 'FK_JobTimeEntries_ShopWorkers_ShopWorkerId') + ALTER TABLE [JobTimeEntries] DROP CONSTRAINT [FK_JobTimeEntries_ShopWorkers_ShopWorkerId]; + IF EXISTS (SELECT 1 FROM sys.foreign_keys WHERE name = 'FK_MaintenanceRecords_ShopWorkers_ShopWorkerId') + ALTER TABLE [MaintenanceRecords] DROP CONSTRAINT [FK_MaintenanceRecords_ShopWorkers_ShopWorkerId]; + IF EXISTS (SELECT 1 FROM sys.tables WHERE name = 'ShopWorkerRoleCosts') + DROP TABLE [ShopWorkerRoleCosts]; + IF EXISTS (SELECT 1 FROM sys.tables WHERE name = 'ShopWorkers') + DROP TABLE [ShopWorkers]; + IF EXISTS (SELECT 1 FROM sys.indexes WHERE name = 'IX_MaintenanceRecords_ShopWorkerId' AND object_id = OBJECT_ID('MaintenanceRecords')) + DROP INDEX [IX_MaintenanceRecords_ShopWorkerId] ON [MaintenanceRecords]; + IF EXISTS (SELECT 1 FROM sys.indexes WHERE name = 'IX_JobTimeEntries_ShopWorkerId' AND object_id = OBJECT_ID('JobTimeEntries')) + DROP INDEX [IX_JobTimeEntries_ShopWorkerId] ON [JobTimeEntries]; + IF EXISTS (SELECT 1 FROM sys.indexes WHERE name = 'IX_Jobs_ShopWorkerId' AND object_id = OBJECT_ID('Jobs')) + DROP INDEX [IX_Jobs_ShopWorkerId] ON [Jobs]; + IF EXISTS (SELECT 1 FROM sys.columns WHERE name = 'ShopWorkerId' AND object_id = OBJECT_ID('MaintenanceRecords')) + ALTER TABLE [MaintenanceRecords] DROP COLUMN [ShopWorkerId]; + IF EXISTS (SELECT 1 FROM sys.columns WHERE name = 'ShopWorkerId' AND object_id = OBJECT_ID('JobTimeEntries')) + ALTER TABLE [JobTimeEntries] DROP COLUMN [ShopWorkerId]; + IF EXISTS (SELECT 1 FROM sys.columns WHERE name = 'ShopWorkerId' AND object_id = OBJECT_ID('Jobs')) + ALTER TABLE [Jobs] DROP COLUMN [ShopWorkerId]; + "); migrationBuilder.AddColumn( name: "ReminderSentAt",