I’m trying to write a command that will delete all functions in a namespace. I’ve already found a command that will generate the drop functions script:
SELECT 'DROP FUNCTION ' || ns.nspname || '.' || proname || '('
|| oidvectortypes(proargtypes) || ');'
FROM pg_proc INNER JOIN pg_namespace ns ON (pg_proc.pronamespace = ns.oid)
WHERE ns.nspname = 'public' order by proname;
Source: http://www.postgresonline.com/journal/archives/74-How-to-delete-many-functions.html
This will generate something like:
?column?
------------------------------------------
DROP FUNCTION public.function1(bigint);
DROP FUNCTION public.function2();
DROP FUNCTION public.function3(text);
However, I can’t figure out how to change the code, so that the functions are actually deleted – as opposed to only generating the commands.
Any ideas?
The system catalogs changed in Postgres 11! (
prokindinstead ofproisagg) See:Could look like this:
Call to show:
Call to delete:
Major points
You need dynamic SQL for that. Use a plpgsql function or a DO statement (PostgreSQL 9.0+) with
EXECUTE.Note the use of the functions
pg_get_function_identity_arguments()andpg_function_is_visible. The latter can be omitted. It’s a safeguard so you don’t delete functions outside of the current user’ssearch_path.I added a “safe mode”. Only delete if
$2 = 'del'. Else only show generated SQL.Be aware that the function will delete itself if it lives in the schema you delete from.
I also added
quote_ident()to safeguard against SQLi. Consider the following:CASCADE, but I did not do that here, since it makes the function more dangerous, yet.Related: