Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
98 changes: 78 additions & 20 deletions dbsync_daemon.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,70 @@
import sys
import time
import argparse
import platform
import logging
import os
import pathlib
import typing

import dbsync
from version import __version__
from config import config, validate_config, ConfigError, update_config_path


def is_pyinstaller() -> bool:
if getattr(sys, 'frozen', False) and platform.system() == "Windows":
return True
return False


def pyinstaller_update_path() -> None:
path = pathlib.Path(__file__).parent / "lib"
os.environ["PATH"] += os.pathsep + path.as_posix()


def pyinstaller_path_fix() -> None:
if is_pyinstaller():
pyinstaller_update_path()


LOGGER: logging.Logger = None


def setup_logger(log_path, log_verbosity: str, with_time=True, with_level=True) -> logging.Logger:
global LOGGER
LOGGER = logging.getLogger(f"{log_path}")
if log_verbosity == "messages":
LOGGER.setLevel(logging.DEBUG)
elif log_verbosity == "errors":
LOGGER.setLevel(logging.WARNING)
else:
LOGGER.setLevel(logging.WARNING)
if not LOGGER.handlers:
log_handler = logging.FileHandler(log_path, mode="a")
format = "%(asctime)s -" if with_time else ""
format += "%(levelname)s - %(message)s" if with_level else "%(message)s"
log_handler.setFormatter(logging.Formatter(format))
LOGGER.addHandler(log_handler)


def handle_error(error: typing.Union[Exception, str]):
if LOGGER:
LOGGER.error(str(error))
print("Error: " + str(error), file=sys.stderr)
sys.exit(1)


def handle_message(msg: str):
if LOGGER:
LOGGER.debug(msg)
print(msg)


def main():

pyinstaller_path_fix()

parser = argparse.ArgumentParser(prog='dbsync_deamon.py',
description='Synchronization tool between Mergin Maps project and database.',
epilog='www.merginmaps.com')
Expand All @@ -24,29 +80,33 @@ def main():
parser.add_argument("--skip-init", action="store_true", help="Skip DB sync init step to make the tool start faster. It is not recommend to use it unless you are really sure you can skip the initial sanity checks.")
parser.add_argument("--single-run", action="store_true", help="Run just once performing single pull and push operation, instead of running in infinite loop.")
parser.add_argument("--force-init", action="store_true", help="Force removing working directory and schemas from DB to initialize from scratch.")
parser.add_argument("--log-file", default="", action="store", help="Store logging to file.")
parser.add_argument("--log-verbosity", choices=["errors", "messages"], default="errors", help="Log messages, not only errors.")

args = parser.parse_args()

print(f"== starting mergin-db-sync daemon == version {__version__} ==")
if args.log_file:
log_file = pathlib.Path(args.log_file)
setup_logger(log_file.as_posix(), args.log_verbosity)

handle_message(f"== starting mergin-db-sync daemon == version {__version__} ==")

try:
update_config_path(args.config_file)
except IOError as e:
print("Error: " + str(e), file=sys.stderr)
sys.exit(1)
handle_error(e)

sleep_time = config.as_int("daemon.sleep_time")
try:
validate_config(config)
except ConfigError as e:
print("Error: " + str(e), file=sys.stderr)
sys.exit(1)
handle_error(e)

if args.force_init and args.skip_init:
print("Cannot use `--force-init` with `--skip-init` Initialization is required. ", file=sys.stderr)
sys.exit(1)
handle_error("Cannot use `--force-init` with `--skip-init` Initialization is required. ")

handle_message("Logging in to Mergin...")

print("Logging in to Mergin...")
mc = dbsync.create_mergin_client()

if args.force_init:
Expand All @@ -58,37 +118,35 @@ def main():
try:
dbsync.dbsync_init(mc)
except dbsync.DbSyncError as e:
print("Error: " + str(e), file=sys.stderr)
sys.exit(1)
handle_error(e)

try:
print("Trying to pull")
handle_message("Trying to pull")
dbsync.dbsync_pull(mc)

print("Trying to push")
handle_message("Trying to push")
dbsync.dbsync_push(mc)

except dbsync.DbSyncError as e:
print("Error: " + str(e), file=sys.stderr)
sys.exit(1)
handle_error(e)

else:

if not args.skip_init:
try:
dbsync.dbsync_init(mc)
except dbsync.DbSyncError as e:
print("Error: " + str(e), file=sys.stderr)
sys.exit(1)
handle_error(e)

while True:

print(datetime.datetime.now())

try:
print("Trying to pull")
handle_message("Trying to pull")
dbsync.dbsync_pull(mc)

print("Trying to push")
handle_message("Trying to push")
dbsync.dbsync_push(mc)

# check mergin client token expiration
Expand All @@ -97,9 +155,9 @@ def main():
mc = dbsync.create_mergin_client()

except dbsync.DbSyncError as e:
print("Error: " + str(e), file=sys.stderr)
handle_error(e)

print("Going to sleep")
handle_message("Going to sleep")
time.sleep(sleep_time)


Expand Down
13 changes: 13 additions & 0 deletions scripts/build_exe.bat
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
pyinstaller ../dbsync_daemon.py ^
-c ^
--noconfirm ^
--add-binary="./windows_binaries/geodiff.exe;lib" ^
--add-binary="./windows_binaries/geodiff.dll;lib" ^
--add-binary="./windows_binaries/libcrypto-3-x64.dll;lib" ^
--add-binary="./windows_binaries/LIBPQ.dll;lib" ^
--add-binary="./windows_binaries/libssl-3-x64.dll;lib" ^
--add-binary="./windows_binaries/sqlite3.dll;lib" ^
--hidden-import dynaconf ^
--collect-all mergin ^
--clean ^
-F