-- complain if script is sourced in psql, rather than via CREATE EXTENSION \echo Use "CREATE EXTENSION config_log" to load this file. \quit CREATE TABLE pg_settings_log AS SELECT name, setting, unit, sourcefile, sourceline, CAST('INSERT' AS VARCHAR(6)) AS op, CURRENT_TIMESTAMP AS recorded_ts FROM pg_settings WHERE source='configuration file'; CREATE OR REPLACE VIEW pg_settings_log_current AS SELECT psl.* FROM pg_settings_log psl LEFT JOIN pg_settings_log psl_ref ON (psl.name = psl_ref.name AND psl.recorded_ts < psl_ref.recorded_ts) WHERE psl_ref.name IS NULL; CREATE OR REPLACE FUNCTION pg_settings_logger() RETURNS BOOLEAN LANGUAGE plpgsql AS $$ DECLARE changed BOOLEAN := FALSE; settings_rec RECORD; BEGIN FOR settings_rec IN WITH pg_settings_log_current AS ( SELECT * FROM pg_settings_log_current ORDER BY name ) SELECT 'UPDATE' AS op, ps.name, ps.setting, ps.unit, ps.sourcefile, ps.sourceline FROM pg_settings ps INNER JOIN pg_settings_log_current psl ON (psl.name=ps.name AND psl.setting != ps.setting) WHERE ps.source ='configuration file' UNION SELECT 'INSERT' AS op, ps.name, ps.setting, ps.unit, ps.sourcefile, ps.sourceline FROM pg_settings ps WHERE ps.source ='configuration file' AND NOT EXISTS (SELECT NULL FROM pg_settings_log_current psl WHERE psl.name = ps.name ) UNION SELECT 'DELETE' AS op, psl.name, psl.setting, psl.unit, psl.sourcefile, psl.sourceline FROM pg_settings_log_current psl WHERE EXISTS (SELECT NULL FROM pg_settings ps WHERE ps.name = psl.name AND ps.source ='default' ) AND psl.op != 'DELETE' LOOP INSERT INTO pg_settings_log (name, setting, unit, sourcefile, sourceline, op, recorded_ts ) VALUES(settings_rec.name, settings_rec.setting, settings_rec.unit, settings_rec.sourcefile, settings_rec.sourceline, settings_rec.op, CURRENT_TIMESTAMP ); changed = TRUE; END LOOP; RETURN changed; END; $$; REVOKE ALL ON pg_settings_log FROM public; REVOKE ALL ON pg_settings_log_current FROM public; REVOKE ALL ON FUNCTION pg_settings_logger() FROM public;