#!/bin/bash # Fix indicators table schema - Version 2 (Final) # Handles TimescaleDB compression constraints properly echo "Fixing indicators table schema (v2)..." # 1. Decompress chunks individually (safest method) # We fetch the list of compressed chunks and process them one by one echo "Checking for compressed chunks..." CHUNKS=$(docker exec -i btc_timescale psql -U btc_bot -d btc_data -t -c "SELECT chunk_schema || '.' || chunk_name FROM timescaledb_information.chunks WHERE hypertable_name = 'indicators' AND is_compressed = true;") for chunk in $CHUNKS; do # Trim whitespace chunk=$(echo "$chunk" | xargs) if [[ ! -z "$chunk" ]]; then echo "Decompressing chunk: $chunk" docker exec -i btc_timescale psql -U btc_bot -d btc_data -c "SELECT decompress_chunk('$chunk');" fi done # 2. Execute the schema changes docker exec -i btc_timescale psql -U btc_bot -d btc_data < true); -- Disable compression setting (REQUIRED to add unique constraint) ALTER TABLE indicators SET (timescaledb.compress = false); -- Deduplicate data (just in case duplicates exist) DELETE FROM indicators a USING indicators b WHERE a.ctid < b.ctid AND a.time = b.time AND a.symbol = b.symbol AND a.interval = b.interval AND a.indicator_name = b.indicator_name; -- Add the unique constraint ALTER TABLE indicators ADD CONSTRAINT indicators_unique UNIQUE (time, symbol, interval, indicator_name); -- Re-enable compression configuration ALTER TABLE indicators SET ( timescaledb.compress, timescaledb.compress_segmentby = 'symbol,interval,indicator_name' ); -- Re-add compression policy (7 days) SELECT add_compression_policy('indicators', INTERVAL '7 days', if_not_exists => true); COMMIT; SELECT 'Indicators schema fix v2 completed successfully' as status; EOF