feat: Add VEX Status Chip component and integration tests for reachability drift detection

- Introduced `VexStatusChipComponent` to display VEX status with color coding and tooltips.
- Implemented integration tests for reachability drift detection, covering various scenarios including drift detection, determinism, and error handling.
- Enhanced `ScannerToSignalsReachabilityTests` with a null implementation of `ICallGraphSyncService` for better test isolation.
- Updated project references to include the new Reachability Drift library.
This commit is contained in:
StellaOps Bot
2025-12-20 01:26:42 +02:00
parent edc91ea96f
commit 5fc469ad98
159 changed files with 41116 additions and 2305 deletions

View File

@@ -0,0 +1,147 @@
-- Excititor Schema Migration 005b: Complete timeline_events Partition Migration
-- Sprint: SPRINT_3422_0001_0001 - Time-Based Partitioning
-- Task: 4.2 - Migrate data from existing table
-- Category: C (data migration, requires maintenance window)
--
-- IMPORTANT: Run this during maintenance window AFTER 005_partition_timeline_events.sql
-- Prerequisites:
-- 1. Stop application writes to vex.timeline_events
-- 2. Verify partitioned table exists: \d+ vex.timeline_events_partitioned
--
-- Execution time depends on data volume. For large tables (>1M rows), consider
-- batched migration (see bottom of file).
BEGIN;
-- ============================================================================
-- Step 1: Verify partitioned table exists
-- ============================================================================
DO $$
BEGIN
IF NOT EXISTS (
SELECT 1 FROM pg_class c
JOIN pg_namespace n ON c.relnamespace = n.oid
WHERE n.nspname = 'vex' AND c.relname = 'timeline_events_partitioned'
) THEN
RAISE EXCEPTION 'Partitioned table vex.timeline_events_partitioned does not exist. Run 005_partition_timeline_events.sql first.';
END IF;
END
$$;
-- ============================================================================
-- Step 2: Record row counts for verification
-- ============================================================================
DO $$
DECLARE
v_source_count BIGINT;
BEGIN
SELECT COUNT(*) INTO v_source_count FROM vex.timeline_events;
RAISE NOTICE 'Source table row count: %', v_source_count;
END
$$;
-- ============================================================================
-- Step 3: Migrate data from old table to partitioned table
-- ============================================================================
INSERT INTO vex.timeline_events_partitioned (
id, tenant_id, project_id, event_type, entity_type, entity_id,
actor, details, occurred_at
)
SELECT
id, tenant_id, project_id, event_type, entity_type, entity_id,
actor, details, occurred_at
FROM vex.timeline_events
ON CONFLICT DO NOTHING;
-- ============================================================================
-- Step 4: Verify row counts match
-- ============================================================================
DO $$
DECLARE
v_source_count BIGINT;
v_target_count BIGINT;
BEGIN
SELECT COUNT(*) INTO v_source_count FROM vex.timeline_events;
SELECT COUNT(*) INTO v_target_count FROM vex.timeline_events_partitioned;
IF v_source_count <> v_target_count THEN
RAISE WARNING 'Row count mismatch: source=% target=%. Check for conflicts.', v_source_count, v_target_count;
ELSE
RAISE NOTICE 'Row counts match: % rows migrated successfully', v_target_count;
END IF;
END
$$;
-- ============================================================================
-- Step 5: Swap tables
-- ============================================================================
-- Rename old table to backup
ALTER TABLE vex.timeline_events RENAME TO timeline_events_old;
-- Rename partitioned table to production name
ALTER TABLE vex.timeline_events_partitioned RENAME TO timeline_events;
-- ============================================================================
-- Step 6: Enable RLS on new table (if applicable)
-- ============================================================================
ALTER TABLE vex.timeline_events ENABLE ROW LEVEL SECURITY;
-- ============================================================================
-- Step 7: Add comment about partitioning
-- ============================================================================
COMMENT ON TABLE vex.timeline_events IS
'VEX timeline events. Partitioned monthly by occurred_at. Migrated on ' || NOW()::TEXT;
COMMIT;
-- ============================================================================
-- Post-migration verification (run manually)
-- ============================================================================
--
-- Verify partition structure:
-- SELECT tableoid::regclass, count(*) FROM vex.timeline_events GROUP BY 1;
--
-- Verify BRIN index is being used:
-- EXPLAIN (ANALYZE, BUFFERS) SELECT * FROM vex.timeline_events
-- WHERE occurred_at > NOW() - INTERVAL '1 day';
--
-- After verification, drop old table:
-- DROP TABLE IF EXISTS vex.timeline_events_old;
-- ============================================================================
-- Batched migration alternative (for very large tables)
-- ============================================================================
--
-- If the table is very large (>10M rows), use this batched approach instead:
--
-- DO $$
-- DECLARE
-- v_batch_size INT := 100000;
-- v_offset INT := 0;
-- v_inserted INT;
-- BEGIN
-- LOOP
-- INSERT INTO vex.timeline_events_partitioned
-- SELECT * FROM vex.timeline_events
-- ORDER BY occurred_at
-- LIMIT v_batch_size OFFSET v_offset;
--
-- GET DIAGNOSTICS v_inserted = ROW_COUNT;
-- v_offset := v_offset + v_batch_size;
--
-- RAISE NOTICE 'Migrated % rows (offset: %)', v_inserted, v_offset;
--
-- EXIT WHEN v_inserted < v_batch_size;
--
-- -- Allow checkpoint between batches
-- PERFORM pg_sleep(0.1);
-- END LOOP;
-- END
-- $$;