MerginMaps / MerginMaps/qgis-plugin

Sync blocked after deleting local .gpkg (Python error until QGIS restart)

Open
#869 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

bug
Dominant language
Python
Stars
44
Forks
20
Avg merge
3d 12h
Merged PRs (30d)
5

Description

Description

If a user deletes a GeoPackage layer file from the project directory on disk (e.g. Survey_points.gpkg) and then clicks Sync in Mergin Maps plugin, sync fails with a Python error and the UI cannot proceed. User must restart QGIS, reopen the project, and then the sync works.

Environment
Staging/PROD

Application (+ app version, build, operating system)

  • QGIS version: 3.44.7
  • Plugin build: MM Plugin d-129011
  • macOS: Tahoe 26.2

Steps to reproduce

  1. In Mergin Maps plugin create new basic project, save and sync the project
  2. In mobile app download and open project from step 1
  3. Add record to the project in mobile app, save and sync
  4. Go to MM plugin and sync project
  5. In plugin right click on project and select Open Directory... option
  6. Delete Survey_points.gpkg file from file system
  7. Click Sync in the plugin

Actual results

  • Sync fails with a Python error.
  • User is unable to proceed with sync (project stuck until restart).
  • Workaround: restart QGIS → reopen the project → sync is successful.

Expected results

  • Plugin should handle missing local layer file gracefully:
    • either restore/checkout the missing file automatically (if possible), or
    • show a clear actionable error and allow the user to recover without restarting QGIS.

Screenshots or logs

An error has occurred while executing Python code: 

Mergin.mergin.deps.pygeodiff.geodifflib.GeoDiffLibError: Error in schema: Missing 'base' file when opening sqlite driver: /Users/rastoh/Documents/1_Projects/SSO_plugin_regression/aaa_test_sync_120226/point.gpkg 
Traceback (most recent call last):
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/plugin.py", line 481, in current_project_sync
    self.manager.project_status(self.mergin_proj_dir)
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/projects_manager.py", line 249, in project_status
    dlg = ProjectStatusDialog(
          ^^^^^^^^^^^^^^^^^^^^
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/project_status_dialog.py", line 109, in __init__
    self.validate_project()
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/project_status_dialog.py", line 267, in validate_project
    results = validator.run_checks()
              ^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/validation.py", line 125, in run_checks
    self.check_db_schema()
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/validation.py", line 287, in check_db_schema
    has_change, msg = has_schema_change(self.mp, layer)
                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/utils.py", line 1125, in has_schema_change
    local_schema = get_schema(local_path)
                   ^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/utils.py", line 1101, in get_schema
    geodiff.schema("sqlite", "", layer_path, tmp_file.name)
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/mergin/deps/pygeodiff/main.py", line 368, in schema
    return self.clib.schema(driver, driver_info, src, json)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/mergin/deps/pygeodiff/geodifflib.py", line 567, in schema
    self._parse_return_code(res, "schema")
  File "/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins/Mergin/mergin/deps/pygeodiff/geodifflib.py", line 172, in _parse_return_code
    raise GeoDiffLibError(msg)
Mergin.mergin.deps.pygeodiff.geodifflib.GeoDiffLibError: Error in schema:
Missing 'base' file when opening sqlite driver: /Users/rastoh/Documents/1_Projects/SSO_plugin_regression/aaa_test_sync_120226/point.gpkg


Python version: 3.12.11 (main, Dec 18 2025, 07:47:48) [Clang 16.0.0 (clang-1600.0.26.6)] 
QGIS version: 3.44.7-Solothurn Solothurn, 4edb1325 

Python Path:
/Applications/QGIS.app/Contents/Resources/qgis/python
/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python
/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python/plugins
/Applications/QGIS.app/Contents/Resources/qgis/python/plugins
/Applications/QGIS.app/Contents/Frameworks/lib/python312.zip
/Applications/QGIS.app/Contents/Frameworks/lib/python3.12
/Applications/QGIS.app/Contents/Frameworks/lib/python3.12/lib-dynload
/Applications/QGIS.app/Contents/Frameworks/lib/python3.12/site-packages
/Users/rastoh/Library/Application Support/QGIS/QGIS3/profiles/Rasto Lutra/python
.
/Users/rastoh/Documents/1_Projects/SSO_plugin_regression/aaa_test_sync_120226

Conclusion
Created by GitHub Copilot and supervised by a human test analyst.

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Read plugin.py at current_project_sync and follow the path through projects_manager.py, project_status_dialog.py, validation.py, and utils.py at check_db_schema, has_schema_change, and get_schema. Trace how the missing GeoPackage reaches the schema check; done means Sync no longer leaves the user blocked and provides recovery or a clear actionable error without restarting QGIS.

Written by the indexing model from the issue text.

Assessment

Tech stack
python, sqlite
Domain
databases, desktop
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.