diff --git a/CHANGELOG.md b/CHANGELOG.md index 78753ed7d..808cfcbcd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,7 +9,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/). ### Added - Add standard info elem fields for NVTs in get_info [#1426](https://github.com/greenbone/gvmd/pull/1426) - Add --ldap-debug option [#1439](https://github.com/greenbone/gvmd/pull/1439) -- Add check if PostgreSQL extensions are installed [#1444](https://github.com/greenbone/gvmd/pull/1444) +- Try to install PostgreSQL extensions automatically [#1444](https://github.com/greenbone/gvmd/pull/1444) [#1483](https://github.com/greenbone/gvmd/pull/1483) - Add auto retry on scanner connection lost during a running task [#1452](https://github.com/greenbone/gvmd/pull/1452) ### Changed diff --git a/INSTALL.md b/INSTALL.md index 75dadb085..552214c67 100644 --- a/INSTALL.md +++ b/INSTALL.md @@ -145,22 +145,13 @@ Certificates`. grant dba to mattm; # mattm is the user created in step 3 ``` -5. Create DB extensions (also necessary when the database got dropped). - - ```sh - sudo -u postgres bash # if you logged out after step 4 - psql gvmd - create extension "uuid-ossp"; - create extension "pgcrypto"; - ``` - -6. Make Postgres aware of the gvm libraries if not installed +5. Make Postgres aware of the gvm libraries if not installed in a ld-aware directory. For example create file `/etc/ld.so.conf.d/gvm.conf` with appropriate path and then run `ldconfig`. -7. Run Manager as usual. +6. Run Manager as usual. -8. To run SQL on the database. +7. To run SQL on the database. ```sh psql gvmd diff --git a/src/manage_pg.c b/src/manage_pg.c index 701192889..065b65fac 100644 --- a/src/manage_pg.c +++ b/src/manage_pg.c @@ -38,6 +38,16 @@ */ #define G_LOG_DOMAIN "md manage" +/** + * @brief Database superuser role + */ +#define DB_SUPERUSER_ROLE "dba" + + +/* Headers */ + int +check_db_extensions (); + /* Session. */ @@ -187,17 +197,12 @@ manage_create_sql_functions () if (created) return 0; - if (sql_int ("SELECT count (*) FROM pg_available_extensions" - " WHERE name = 'uuid-ossp' AND installed_version IS NOT NULL;") - == 0) - { - g_warning ("%s: PostgreSQL extension uuid-ossp required", __func__); - return -1; - } + if (check_db_extensions ()) + return -1; /* Functions in C. */ - sql ("SET role dba;"); + sql ("SET ROLE \"%s\";", DB_SUPERUSER_ROLE); sql ("CREATE OR REPLACE FUNCTION hosts_contains (text, text)" " RETURNS boolean" @@ -3037,47 +3042,56 @@ check_db_sequences () } /** - * @brief Check if an extension is installed. + * @brief Check if an extension is available and can be installed. * - * @param[in] extname Name of the extension to check. + * @param[in] name Name of the extension to check. * - * @return TRUE extension is installed, FALSE otherwise. + * @return TRUE extension is available, FALSE otherwise. */ static gboolean -db_extension_installed (const char *extname) +db_extension_available (const char *name) { - if (sql_int ("SELECT count(*) FROM pg_extension WHERE extname = '%s'", - extname)) + if (sql_int ("SELECT count(*) FROM pg_available_extensions" + " WHERE name = '%s'", + name)) { - g_debug ("%s: Extension '%s' is installed.", - __func__, extname); + g_debug ("%s: Extension '%s' is available.", + __func__, name); return TRUE; } else { - g_message ("%s: Extension '%s' is not installed.", - __func__, extname); + g_message ("%s: Extension '%s' is not available.", + __func__, name); return FALSE; } } /** - * @brief Check if all extensions are installed. + * @brief Ensure all extensions are installed. * * @return 0 success, 1 extension missing. */ int check_db_extensions () { - if (db_extension_installed ("uuid-ossp") - && db_extension_installed ("pgcrypto")) + if (db_extension_available ("uuid-ossp") + && db_extension_available ("pgcrypto")) { - g_debug ("%s: All required extensions are installed.", __func__); + g_debug ("%s: All required extensions are available.", __func__); + + // Switch to superuser role and try to install extensions. + sql ("SET ROLE \"%s\";", DB_SUPERUSER_ROLE); + + sql ("CREATE EXTENSION IF NOT EXISTS \"uuid-ossp\""); + sql ("CREATE EXTENSION IF NOT EXISTS \"pgcrypto\""); + + sql ("RESET ROLE;"); return 0; } else { - g_warning ("%s: A required extension is not installed.", __func__); + g_warning ("%s: A required extension is not available.", __func__); return 1; } }