diff --git a/auto_backup/README.rst b/auto_backup/README.rst index 1b5485c70c3..e79d8b98c35 100644 --- a/auto_backup/README.rst +++ b/auto_backup/README.rst @@ -113,7 +113,6 @@ Known issues / Roadmap changing settings, you need to run the backup from outside of the main Odoo instance. How to do this is outlined in `this blog post `__. -- Backups won't work if list_db=False is configured in the instance. Bug Tracker =========== diff --git a/auto_backup/__manifest__.py b/auto_backup/__manifest__.py index 3c7ab7471ac..36e8c5ea86a 100644 --- a/auto_backup/__manifest__.py +++ b/auto_backup/__manifest__.py @@ -6,7 +6,7 @@ { "name": "Database Auto-Backup", "summary": "Backups database", - "version": "18.0.1.0.1", + "version": "18.0.1.0.2", "author": "Yenthe Van Ginneken, " "Agile Business Group, " "Grupo ESOC Ingenieria de Servicios, " diff --git a/auto_backup/models/db_backup.py b/auto_backup/models/db_backup.py index 042038e6183..7dd8f71d373 100644 --- a/auto_backup/models/db_backup.py +++ b/auto_backup/models/db_backup.py @@ -158,9 +158,12 @@ def action_backup(self): shutil.copyfileobj(cached, destiny) # Generate new backup else: - db.dump_db( - self.env.cr.dbname, destiny, backup_format=rec.backup_format - ) + with self._db_management_enabled(): + db.dump_db( + self.env.cr.dbname, + destiny, + backup_format=rec.backup_format, + ) backup = backup or destiny.name successful |= rec @@ -170,9 +173,10 @@ def action_backup(self): for rec in sftp: filename = self.filename(datetime.now(), ext=rec.backup_format) with rec.backup_log(): - cached = db.dump_db( - self.env.cr.dbname, None, backup_format=rec.backup_format - ) + with self._db_management_enabled(): + cached = db.dump_db( + self.env.cr.dbname, None, backup_format=rec.backup_format + ) with cached: with rec.sftp_connection() as remote: @@ -196,6 +200,25 @@ def action_backup_all(self): """Run all scheduled backups.""" return self.search([]).action_backup() + @contextmanager + def _db_management_enabled(self): + """Temporarily allow database management functions during a backup. + + ``odoo.service.db.dump_db`` is protected by + ``check_db_management_enabled``, which raises ``AccessDenied`` when + ``list_db = False`` is set in the Odoo configuration. That option only + aims at hiding database management from the web interface; a scheduled + backup is a trusted server-side operation, so we re-enable the flag for + the duration of the dump and always restore its original value + afterwards. + """ + list_db = tools.config["list_db"] + tools.config["list_db"] = True + try: + yield + finally: + tools.config["list_db"] = list_db + @contextmanager def backup_log(self): """Log a backup result.""" diff --git a/auto_backup/readme/ROADMAP.md b/auto_backup/readme/ROADMAP.md index 93e7ad75415..79625b7c1e9 100644 --- a/auto_backup/readme/ROADMAP.md +++ b/auto_backup/readme/ROADMAP.md @@ -3,4 +3,3 @@ changing settings, you need to run the backup from outside of the main Odoo instance. How to do this is outlined in [this blog post](https://blog.laslabs.com/2016/10/running-python-scripts-within-odoos-environment/). -- Backups won't work if list_db=False is configured in the instance. diff --git a/auto_backup/static/description/index.html b/auto_backup/static/description/index.html index 997ce0aa76c..7f102ee6389 100644 --- a/auto_backup/static/description/index.html +++ b/auto_backup/static/description/index.html @@ -469,7 +469,6 @@

Known issues / Roadmap

changing settings, you need to run the backup from outside of the main Odoo instance. How to do this is outlined in this blog post. -
  • Backups won’t work if list_db=False is configured in the instance.
  • diff --git a/auto_backup/tests/test_db_backup.py b/auto_backup/tests/test_db_backup.py index 6ab7236ebfa..27fad0508af 100644 --- a/auto_backup/tests/test_db_backup.py +++ b/auto_backup/tests/test_db_backup.py @@ -119,6 +119,15 @@ def test_action_backup_local(self): generated_backup = [f for f in os.listdir(rec_id.folder) if f >= filename] self.assertEqual(1, len(generated_backup)) + def test_action_backup_local_list_db_disabled(self): + """It should backup locally even when list_db is disabled""" + rec_id = self.new_record("local") + filename = rec_id.filename(datetime.now()) + with patch.dict(tools.config.options, {"list_db": False}): + rec_id.action_backup() + generated_backup = [f for f in os.listdir(rec_id.folder) if f >= filename] + self.assertEqual(1, len(generated_backup)) + def test_action_backup_local_cleanup(self): """Backup local database and cleanup old databases""" rec_id = self.new_record("local")