Ausgangslage:
Eine Tabelle hat einen Index (id), der den Sektionsnamen (section) und den zugehörigen Key (idx) in etwas ungewöhnlicher Notation enthält:
section[idx]. Der Sinn sollte wohl sein, die Spalte „id“ direkt als Variablenname (hier für ein Array) zu übernehmen ($$row[id] = $value).
Abfragen nach einer Sektion (zB common) müssen dann aber mit LIKE durchgeführt werden (SELECT de FROM language WHERE id LIKE ‚common[%‘).
Das geht zu Lasten der Performance.
Auftrag:
Splitten der id in section und idx. Dazu neue Spalten anlegen und aus der id-Spalte die beiden neuen Spalten befüllen.
Das SQL soll bei konvertierten (2 neue Spalten, plus Indizes) genauso funktionieren, wie bei den nicht knonvertierten Spalten.
Lösung:
-- add column section DO $$ BEGIN BEGIN ALTER TABLE language ADD COLUMN section character varying (100); EXCEPTION WHEN duplicate_column THEN RAISE NOTICE 'column section already exists in table language.'; END; END; $$; DROP INDEX IF EXISTS idx_language_section; CREATE INDEX idx_language_section ON language USING btree (section); -- add column idx DO $$ BEGIN BEGIN ALTER TABLE language ADD COLUMN idx character varying (100); EXCEPTION WHEN duplicate_column THEN RAISE NOTICE 'column idx already exists in table language.'; END; END; $$; DROP INDEX IF EXISTS idx_language_idx; CREATE INDEX idx_language_idx ON language USING btree (section); -- update UPDATE language SET section=split_part(id, '[', 1), idx=rtrim(split_part(id, '[',2),']');
Anmerkung:
Ab Postgresql 9.6 kann auch auf Spalten mit IF EXISTS untersucht werden.