All checks were successful
build-and-release / build (catering-services) (push) Successful in 1m43s
build-and-release / build (companies) (push) Successful in 1m56s
build-and-release / build (cron) (push) Successful in 2m10s
build-and-release / build (customers) (push) Successful in 2m29s
build-and-release / build (gateway) (push) Successful in 51s
build-and-release / build (fitness-trainers) (push) Successful in 1m22s
build-and-release / build (developers) (push) Successful in 1m50s
build-and-release / build (employees) (push) Successful in 2m42s
build-and-release / build (job-seekers) (push) Successful in 2m1s
build-and-release / build (jobs) (push) Successful in 2m10s
build-and-release / build (graphic-designers) (push) Successful in 2m51s
build-and-release / build (leads) (push) Successful in 2m22s
build-and-release / build (photographers) (push) Successful in 1m42s
build-and-release / build (makeup-artists) (push) Successful in 2m49s
build-and-release / build (payments) (push) Successful in 2m11s
build-and-release / build (social-media-managers) (push) Successful in 2m33s
build-and-release / build (tutors) (push) Successful in 2m36s
build-and-release / build (ugc-content-creators) (push) Successful in 2m12s
build-and-release / build (video-editors) (push) Successful in 2m38s
build-and-release / build (users) (push) Successful in 4m29s
CRITICAL: 20260402030000_strict_employee_separation.up.sql contained an unconditional DROP TABLE IF EXISTS employees CASCADE followed by a bare CREATE TABLE, written as a one-time schema transformation back when it was authored. The db-migrate tool has no applied-migrations tracking table - it replays every .sql file on every run - which turned that one-time DROP into a destructive operation that wipes every employee account (including admin accounts) on every single migration job run. This is what caused today's "db error while logging in": the phone column (never present in any tracked migration, added out-of-band in production at some point) was gone after the recreate, and every employee row - including the account in use this session - was deleted. Fix: make the table creation a plain idempotent CREATE TABLE IF NOT EXISTS (the standalone-schema transition it performed already happened in production long ago, so the drop was never needed for correctness going forward). Add a proper migration for the phone column so it's tracked instead of relying on an undocumented manual ALTER. Confirmed via kubectl-verified row count (0) and a pre-incident backup (2026-07-18T21:00:03Z, predates the destructive run) that the deleted row is recoverable; restoring it separately as a one-time data fix, not part of this schema migration. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
42 lines
2 KiB
SQL
42 lines
2 KiB
SQL
-- UP: 20260402030000_strict_employee_separation.up.sql
|
|
--
|
|
-- Originally: "Drop old employees table (was linked to users - replacing with
|
|
-- standalone auth)" - a one-time schema transformation. The db-migrate tool
|
|
-- (crates/db-migrate) has no applied-migrations tracking table; it replays
|
|
-- every .sql file on every run, which turned this one-time DROP TABLE ...
|
|
-- CASCADE into a destructive operation that wiped the live employees table
|
|
-- (and every employee account, including admin accounts) on every migration
|
|
-- run. The standalone-schema transition already happened in production long
|
|
-- ago, so this is now safely a plain idempotent create.
|
|
|
|
-- 1. EMPLOYEES (Standalone Table - Not Linked to 'users')
|
|
CREATE TABLE IF NOT EXISTS employees (
|
|
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
|
|
first_name VARCHAR(100) NOT NULL,
|
|
last_name VARCHAR(100) NOT NULL,
|
|
email VARCHAR(255) UNIQUE NOT NULL,
|
|
password_hash VARCHAR(255) NOT NULL,
|
|
employee_code VARCHAR(50) UNIQUE,
|
|
department_id UUID REFERENCES departments(id) ON DELETE SET NULL,
|
|
designation_id UUID REFERENCES designations(id) ON DELETE SET NULL,
|
|
role_code VARCHAR(50) NOT NULL DEFAULT 'STAFF',
|
|
status VARCHAR(50) NOT NULL DEFAULT 'ACTIVE',
|
|
joined_at DATE NOT NULL DEFAULT CURRENT_DATE,
|
|
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
|
|
updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW()
|
|
);
|
|
|
|
-- 2. EMPLOYEE SESSIONS (Standalone Auth)
|
|
CREATE TABLE IF NOT EXISTS employee_sessions (
|
|
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
|
|
employee_id UUID NOT NULL REFERENCES employees(id) ON DELETE CASCADE,
|
|
token_hash VARCHAR(255) UNIQUE NOT NULL,
|
|
expires_at TIMESTAMPTZ NOT NULL,
|
|
revoked BOOLEAN NOT NULL DEFAULT false,
|
|
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW()
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX IF NOT EXISTS idx_employees_email ON employees(email);
|
|
CREATE INDEX IF NOT EXISTS idx_employees_status ON employees(status);
|
|
CREATE INDEX IF NOT EXISTS idx_employee_sessions_token ON employee_sessions(token_hash);
|