171 Zeilen
5.2 KiB
PL/PgSQL
171 Zeilen
5.2 KiB
PL/PgSQL
-- Migration Script: Fix Database Field Name Inconsistencies
|
|
-- Created: 2025-06-18
|
|
-- Purpose: Standardize field names and remove duplicate columns
|
|
|
|
-- =====================================================
|
|
-- STEP 1: Create backup of affected data
|
|
-- =====================================================
|
|
|
|
-- Create backup table for sessions data
|
|
CREATE TABLE IF NOT EXISTS sessions_backup_20250618 AS
|
|
SELECT * FROM sessions;
|
|
|
|
-- =====================================================
|
|
-- STEP 2: Create compatibility views (temporary)
|
|
-- =====================================================
|
|
|
|
-- Drop existing view if exists
|
|
DROP VIEW IF EXISTS sessions_compat;
|
|
|
|
-- Create compatibility view for smooth transition
|
|
CREATE VIEW sessions_compat AS
|
|
SELECT
|
|
id,
|
|
license_id,
|
|
license_key,
|
|
session_id,
|
|
username,
|
|
computer_name,
|
|
hardware_id,
|
|
hardware_id as device_id, -- Compatibility alias
|
|
ip_address,
|
|
user_agent,
|
|
app_version,
|
|
started_at,
|
|
started_at as login_time, -- Compatibility alias
|
|
last_heartbeat,
|
|
last_heartbeat as last_activity, -- Compatibility alias
|
|
ended_at,
|
|
ended_at as logout_time, -- Compatibility alias
|
|
is_active,
|
|
is_active as active -- Compatibility alias
|
|
FROM sessions;
|
|
|
|
-- =====================================================
|
|
-- STEP 3: Update data in duplicate columns
|
|
-- =====================================================
|
|
|
|
-- Sync data from primary columns to alias columns (safety measure)
|
|
UPDATE sessions SET
|
|
login_time = COALESCE(login_time, started_at),
|
|
last_activity = COALESCE(last_activity, last_heartbeat),
|
|
logout_time = COALESCE(logout_time, ended_at),
|
|
active = COALESCE(active, is_active)
|
|
WHERE login_time IS NULL
|
|
OR last_activity IS NULL
|
|
OR logout_time IS NULL
|
|
OR active IS NULL;
|
|
|
|
-- Sync data from alias columns to primary columns (if primary is null)
|
|
UPDATE sessions SET
|
|
started_at = COALESCE(started_at, login_time),
|
|
last_heartbeat = COALESCE(last_heartbeat, last_activity),
|
|
ended_at = COALESCE(ended_at, logout_time),
|
|
is_active = COALESCE(is_active, active)
|
|
WHERE started_at IS NULL
|
|
OR last_heartbeat IS NULL
|
|
OR ended_at IS NULL
|
|
OR is_active IS NULL;
|
|
|
|
-- =====================================================
|
|
-- STEP 4: Create function to check code dependencies
|
|
-- =====================================================
|
|
|
|
CREATE OR REPLACE FUNCTION check_field_usage()
|
|
RETURNS TABLE (
|
|
query_count INTEGER,
|
|
field_name TEXT,
|
|
usage_type TEXT
|
|
) AS $$
|
|
BEGIN
|
|
-- Check for references to old field names
|
|
RETURN QUERY
|
|
SELECT
|
|
COUNT(*)::INTEGER,
|
|
'device_id'::TEXT,
|
|
'Should use hardware_id'::TEXT
|
|
FROM pg_stat_statements
|
|
WHERE query ILIKE '%device_id%'
|
|
|
|
UNION ALL
|
|
|
|
SELECT
|
|
COUNT(*)::INTEGER,
|
|
'active'::TEXT,
|
|
'Should use is_active'::TEXT
|
|
FROM pg_stat_statements
|
|
WHERE query ILIKE '%active%'
|
|
AND query NOT ILIKE '%is_active%'
|
|
|
|
UNION ALL
|
|
|
|
SELECT
|
|
COUNT(*)::INTEGER,
|
|
'login_time'::TEXT,
|
|
'Should use started_at'::TEXT
|
|
FROM pg_stat_statements
|
|
WHERE query ILIKE '%login_time%';
|
|
END;
|
|
$$ LANGUAGE plpgsql;
|
|
|
|
-- =====================================================
|
|
-- STEP 5: Migration queries for code updates
|
|
-- =====================================================
|
|
|
|
-- These queries help identify code that needs updating:
|
|
|
|
-- Find sessions queries using old field names
|
|
COMMENT ON VIEW sessions_compat IS
|
|
'Compatibility view for sessions table during field name migration.
|
|
Old fields mapped:
|
|
- device_id → hardware_id
|
|
- active → is_active
|
|
- login_time → started_at
|
|
- last_activity → last_heartbeat
|
|
- logout_time → ended_at';
|
|
|
|
-- =====================================================
|
|
-- STEP 6: Final cleanup (run after code is updated)
|
|
-- =====================================================
|
|
|
|
-- DO NOT RUN THIS UNTIL ALL CODE IS UPDATED!
|
|
/*
|
|
-- Remove duplicate columns
|
|
ALTER TABLE sessions
|
|
DROP COLUMN IF EXISTS active,
|
|
DROP COLUMN IF EXISTS login_time,
|
|
DROP COLUMN IF EXISTS last_activity,
|
|
DROP COLUMN IF EXISTS logout_time;
|
|
|
|
-- Drop compatibility view
|
|
DROP VIEW IF EXISTS sessions_compat;
|
|
|
|
-- Drop helper function
|
|
DROP FUNCTION IF EXISTS check_field_usage();
|
|
*/
|
|
|
|
-- =====================================================
|
|
-- VERIFICATION QUERIES
|
|
-- =====================================================
|
|
|
|
-- Check for null values in primary columns
|
|
SELECT
|
|
COUNT(*) FILTER (WHERE started_at IS NULL) as null_started_at,
|
|
COUNT(*) FILTER (WHERE last_heartbeat IS NULL) as null_last_heartbeat,
|
|
COUNT(*) FILTER (WHERE ended_at IS NULL AND is_active = FALSE) as null_ended_at,
|
|
COUNT(*) FILTER (WHERE is_active IS NULL) as null_is_active,
|
|
COUNT(*) as total_sessions
|
|
FROM sessions;
|
|
|
|
-- Check data consistency between duplicate columns
|
|
SELECT
|
|
COUNT(*) FILTER (WHERE started_at != login_time) as started_login_diff,
|
|
COUNT(*) FILTER (WHERE last_heartbeat != last_activity) as heartbeat_activity_diff,
|
|
COUNT(*) FILTER (WHERE ended_at != logout_time) as ended_logout_diff,
|
|
COUNT(*) FILTER (WHERE is_active != active) as active_diff,
|
|
COUNT(*) as total_sessions
|
|
FROM sessions
|
|
WHERE login_time IS NOT NULL
|
|
OR last_activity IS NOT NULL
|
|
OR logout_time IS NOT NULL
|
|
OR active IS NOT NULL; |