Sandro Bonazzola has uploaded a new change for review. Change subject: packaging: setup: database module refactoring ......................................................................
packaging: setup: database module refactoring Refactored the database module for allowing to reuse code for DWH database setup. Moved SchemaTransaction class from db/schema plugin to database module for the same reason. Change-Id: I8f03195ed2d474e0f60ca93ced4755b3b4869c2d Related-To: https://bugzilla.redhat.com/967350 Related-To: https://bugzilla.redhat.com/863757 Signed-off-by: Sandro Bonazzola <sbona...@redhat.com> --- M packaging/setup/ovirt_engine_setup/database.py M packaging/setup/plugins/ovirt-engine-setup/db/schema.py 2 files changed, 199 insertions(+), 80 deletions(-) git pull ssh://gerrit.ovirt.org:29418/ovirt-engine refs/changes/01/21301/1 diff --git a/packaging/setup/ovirt_engine_setup/database.py b/packaging/setup/ovirt_engine_setup/database.py index 76999b3..6329286 100644 --- a/packaging/setup/ovirt_engine_setup/database.py +++ b/packaging/setup/ovirt_engine_setup/database.py @@ -33,6 +33,7 @@ from otopi import base from otopi import util +from otopi import transaction as otopitransaction from ovirt_engine_setup import constants as osetupcons @@ -42,12 +43,56 @@ class Statement(base.Base): @property + def credentials(self): + return self._credentials + + @property def environment(self): return self._environment - def __init__(self, environment): + def __init__( + self, + environment, + credentials=None, + secured=None, + securedHostValidation=None, + connection=None, + ): super(Statement, self).__init__() self._environment = environment + defaults = dict( + user=self.environment[osetupcons.DBEnv.USER], + host=self.environment[osetupcons.DBEnv.HOST], + port=self.environment[osetupcons.DBEnv.PORT], + database=self.environment[osetupcons.DBEnv.DATABASE], + password=self.environment[osetupcons.DBEnv.PASSWORD], + pgpassfile=None, + ) + if osetupcons.DBEnv.PGPASS_FILE in self.environment: + defaults['pgpassfile'] = self.environment[ + osetupcons.DBEnv.PGPASS_FILE + ] + if credentials is None: + credentials = defaults + else: + for key in credentials: + if credentials[key] is None: + credentials[key] = defaults[key] + self._credentials = credentials + if secured is None: + secured = self.environment[osetupcons.DBEnv.SECURED] + self._secured = secured + if securedHostValidation is None: + securedHostValidation = environment[ + osetupcons.DBEnv.SECURED_HOST_VALIDATION + ] + self._securedHostValidation = securedHostValidation + if ( + connection is None and + osetupcons.DBEnv.CONNECTION in self.environment + ): + connection = self.environment[osetupcons.DBEnv.CONNECTION] + self._connection = connection def execute( self, @@ -89,21 +134,19 @@ ret = [] if host is None: - host = self.environment[osetupcons.DBEnv.HOST] + host = self.credentials['host'] if port is None: - port = self.environment[osetupcons.DBEnv.PORT] + port = self.credentials['port'] if secured is None: - secured = self.environment[osetupcons.DBEnv.SECURED] + secured = self._secured if securedHostValidation is None: - securedHostValidation = self.environment[ - osetupcons.DBEnv.SECURED_HOST_VALIDATION - ] + securedHostValidation = self._securedHostValidation if user is None: - user = self.environment[osetupcons.DBEnv.USER] + user = self.credentials['user'] if password is None: - password = self.environment[osetupcons.DBEnv.PASSWORD] + password = self.credentials['password'] if database is None: - database = self.environment[osetupcons.DBEnv.DATABASE] + database = self.credentials['database'] sslmode = 'allow' if secured: @@ -123,7 +166,7 @@ args, ) if not ownConnection: - connection = self.environment[osetupcons.DBEnv.CONNECTION] + connection = self._connection else: self.logger.debug('Creating own connection') @@ -257,6 +300,10 @@ class OvirtUtils(base.Base): @property + def credentials(self): + return self._credentials + + @property def environment(self): return self._environment @@ -264,7 +311,7 @@ def command(self): return self._plugin.command - def __init__(self, plugin, environment=None): + def __init__(self, plugin, environment=None, credentials=None): super(OvirtUtils, self).__init__() self._plugin = plugin self._environment = ( @@ -272,18 +319,38 @@ if environment is None else environment ) + defaults = dict( + user=self.environment[osetupcons.DBEnv.USER], + host=self.environment[osetupcons.DBEnv.HOST], + port=self.environment[osetupcons.DBEnv.PORT], + database=self.environment[osetupcons.DBEnv.DATABASE], + password=self.environment[osetupcons.DBEnv.PASSWORD], + pgpassfile=self.environment[osetupcons.DBEnv.PGPASS_FILE], + ) + if credentials is None: + credentials = defaults + else: + for key in credentials: + if credentials[key] is None: + credentials[key] = defaults[key] + + self._credentials = credentials def detectCommands(self): self.command.detect('pg_dump') self.command.detect('psql') - def tryDatabaseConnect(self, environment=None): - + def tryDatabaseConnect(self, environment=None, credentials=None): if environment is None: environment = self.environment + if credentials is None: + credentials = self.credentials try: - statement = Statement(environment=environment) + statement = Statement( + environment=environment, + credentials=credentials, + ) statement.execute( statement=""" select 1 @@ -308,9 +375,21 @@ user=None, password=None, database=None, + table=None, ): + if table is None: + table = 'schema_version' statement = Statement( environment=self.environment, + credentials=dict( + user=user, + host=host, + port=port, + database=database, + password=password, + pgpassfile=None, + ), + secured=secured, ) ret = statement.execute( statement=""" @@ -319,7 +398,7 @@ where table_name=%(table)s """, args=dict( - table='schema_version', + table=table, ), host=host, port=port, @@ -336,7 +415,9 @@ statement = Statement( environment=self.environment, ) + self.clearDatabase(statement) + def clearDatabase(self, statement): statement.execute( statement=""" create or replace @@ -462,7 +543,10 @@ def backup( self, prefix='engine', + credentials=None, ): + if credentials is None: + credentials = self.credentials fd, backupFile = tempfile.mkstemp( prefix='%s-%s.' % ( prefix, @@ -485,17 +569,15 @@ '--disable-dollar-quoting', '--disable-triggers', '--format=p', - '-U', self.environment[osetupcons.DBEnv.USER], - '-h', self.environment[osetupcons.DBEnv.HOST], - '-p', str(self.environment[osetupcons.DBEnv.PORT]), + '-U', credentials['user'], + '-h', credentials['host'], + '-p', str(credentials['port']), '-f', backupFile, - self.environment[osetupcons.DBEnv.DATABASE], + credentials['database'], ), envAppend={ 'PGPASSWORD': '', - 'PGPASSFILE': self.environment[ - osetupcons.DBEnv.PGPASS_FILE - ] + 'PGPASSFILE': credentials['pgpassfile'] }, ) @@ -504,15 +586,18 @@ def restore( self, backupFile, + credentials=None, ): + if credentials is None: + credentials = self.credentials self._plugin.execute( ( self.command.get('psql'), '-w', - '-h', self.environment[osetupcons.DBEnv.HOST], - '-p', str(self.environment[osetupcons.DBEnv.PORT]), - '-U', self.environment[osetupcons.DBEnv.USER], - '-d', self.environment[osetupcons.DBEnv.DATABASE], + '-U', credentials['user'], + '-h', credentials['host'], + '-p', str(credentials['port']), + '-d', credentials['database'], '-f', backupFile, ), envAppend={ @@ -523,4 +608,63 @@ }, ) + +class SchemaTransaction(otopitransaction.TransactionElement): + """Schema transaction element.""" + + def __init__(self, parent, credentials, backup=None): + super(SchemaTransaction, self).__init__() + self._parent = parent + self._credentials = credentials + self._backup = backup + + def __str__(self): + return _("Schema Transaction") + + def prepare(self): + pass + + def abort(self): + self._parent.logger.info( + _('Rolling back {database} database schema') + ).format( + database=self._credentials['database'], + ) + try: + dbovirtutils = OvirtUtils( + plugin=self._parent, + credentials=self._credentials, + ) + self._parent.logger.info( + _('Clearing database {database}').format( + database=self._credentials['database'], + ) + ) + statement = Statement( + environment=self._parent.environment, + credentials=self._credentials, + ) + dbovirtutils.clearDatabase(statement) + if self._backup is not None and os.path.exists(self._backup): + self._parent.logger.info( + _('Restoring database {database}').format( + database=self._credentials['database'], + ) + ) + dbovirtutils.restore(backupFile=self._backup) + except Exception as e: + self._parent.logger.debug( + 'Exception during database restore', + exc_info=True, + ) + self._parent.logger.error( + _('Database rollback failed: {error}').format( + error=e, + ) + ) + + def commit(self): + pass + + # vim: expandtab tabstop=4 shiftwidth=4 diff --git a/packaging/setup/plugins/ovirt-engine-setup/db/schema.py b/packaging/setup/plugins/ovirt-engine-setup/db/schema.py index 3e5cf74..0036f59 100644 --- a/packaging/setup/plugins/ovirt-engine-setup/db/schema.py +++ b/packaging/setup/plugins/ovirt-engine-setup/db/schema.py @@ -27,7 +27,6 @@ from otopi import constants as otopicons from otopi import util from otopi import plugin -from otopi import transaction from ovirt_engine_setup import constants as osetupcons @@ -37,54 +36,6 @@ @util.export class Plugin(plugin.PluginBase): """Schema plugin.""" - - class SchemaTransaction(transaction.TransactionElement): - """yum transaction element.""" - - def __init__(self, parent, backup=None): - self._parent = parent - self._backup = backup - - def __str__(self): - return _("Schema Transaction") - - def prepare(self): - pass - - def abort(self): - self._parent.logger.info(_('Rolling back database schema')) - try: - dbovirtutils = database.OvirtUtils(plugin=self._parent) - self._parent.logger.info( - _('Clearing database {database}').format( - database=self._parent.environment[ - osetupcons.DBEnv.DATABASE - ], - ) - ) - dbovirtutils.clearOvirtEngineDatabase() - if self._backup is not None and os.path.exists(self._backup): - self._parent.logger.info( - _('Restoring database {database}').format( - database=self._parent.environment[ - osetupcons.DBEnv.DATABASE - ], - ) - ) - dbovirtutils.restore(backupFile=self._backup) - except Exception as e: - self._parent.logger.debug( - 'Exception during database restore', - exc_info=True, - ) - self._parent.logger.error( - _('Database rollback failed: {error}').format( - error=e, - ) - ) - - def commit(self): - pass def __init__(self, context): super(Plugin, self).__init__(context=context) @@ -215,12 +166,24 @@ ) def _miscInstall(self): self.environment[otopicons.CoreEnv.MAIN_TRANSACTION].append( - self.SchemaTransaction( + database.SchemaTransaction( parent=self, + credentials=dict( + host=self.environment[osetupcons.DBEnv.HOST], + port=self.environment[osetupcons.DBEnv.PORT], + database=self.environment[osetupcons.DBEnv.DATABASE], + user=self.environment[osetupcons.DBEnv.USER], + password=self.environment[osetupcons.DBEnv.PASSWORD], + pgpassfile=self.environment[osetupcons.DBEnv.PGPASS_FILE], + ) ) ) - self.logger.info(_('Creating database schema')) + self.logger.info( + _('Creating {database} database schema').format( + database=self.environment[osetupcons.DBEnv.DATABASE], + ) + ) args = [ os.path.join( osetupcons.FileLocations.OVIRT_ENGINE_DB_DIR, @@ -282,8 +245,16 @@ backupFile = dbovirtutils.backup() self.environment[otopicons.CoreEnv.MAIN_TRANSACTION].append( - self.SchemaTransaction( + database.SchemaTransaction( parent=self, + credentials=dict( + host=self.environment[osetupcons.DBEnv.HOST], + port=self.environment[osetupcons.DBEnv.PORT], + database=self.environment[osetupcons.DBEnv.DATABASE], + user=self.environment[osetupcons.DBEnv.USER], + password=self.environment[osetupcons.DBEnv.PASSWORD], + pgpassfile=self.environment[osetupcons.DBEnv.PGPASS_FILE], + ), backup=backupFile, ) ) @@ -295,7 +266,11 @@ # consider doing that via python # - self.logger.info(_('Updating database schema')) + self.logger.info( + _('Updating {database} database schema').format( + database=self.environment[osetupcons.DBEnv.DATABASE], + ) + ) args = [ osetupcons.FileLocations.OVIRT_ENGINE_DB_UPGRADE, '-s', self.environment[osetupcons.DBEnv.HOST], -- To view, visit http://gerrit.ovirt.org/21301 To unsubscribe, visit http://gerrit.ovirt.org/settings Gerrit-MessageType: newchange Gerrit-Change-Id: I8f03195ed2d474e0f60ca93ced4755b3b4869c2d Gerrit-PatchSet: 1 Gerrit-Project: ovirt-engine Gerrit-Branch: master Gerrit-Owner: Sandro Bonazzola <sbona...@redhat.com> _______________________________________________ Engine-patches mailing list Engine-patches@ovirt.org http://lists.ovirt.org/mailman/listinfo/engine-patches