From fdcd3e2debbf58887ffa55fc81ee91395900deb1 Mon Sep 17 00:00:00 2001 From: Peter Bieringer Date: Sun, 28 Dec 2025 09:13:07 +0100 Subject: [PATCH] fix tox issues --- radicale/__main__.py | 17 ++++++++++++++++- radicale/item/__init__.py | 19 ++++++++++++++++++- 2 files changed, 34 insertions(+), 2 deletions(-) diff --git a/radicale/__main__.py b/radicale/__main__.py index b3576a60..a2668b6f 100644 --- a/radicale/__main__.py +++ b/radicale/__main__.py @@ -33,7 +33,7 @@ import sys from types import FrameType from typing import List, Optional, cast -from radicale import VERSION, config, log, server, storage, types +from radicale import VERSION, config, item, log, server, storage, types from radicale.log import logger @@ -65,6 +65,8 @@ def run() -> None: parser.add_argument("--version", action="version", version=VERSION) parser.add_argument("--verify-storage", action="store_true", help="check the storage for errors and exit") + parser.add_argument("--verify-item", action="store", nargs=1, + help="check the provided item file for errors and exit") parser.add_argument("-C", "--config", help="use specific configuration files", nargs="*") parser.add_argument("-D", "--debug", action="store_const", const="debug", @@ -194,6 +196,19 @@ def run() -> None: sys.exit(1) return + if args_ns.verify_item: + encoding = configuration.get("encoding", "stock") + logger.info("Item verification start using 'stock' encoding: %s", encoding) + try: + if not item.verify(args_ns.verify_item[0], encoding): + logger.critical("Item verification failed") + sys.exit(1) + except Exception as e: + logger.critical("An exception occurred during item " + "verification: %s", e, exc_info=False) + sys.exit(1) + return + # Create a socket pair to notify the server of program shutdown shutdown_socket, shutdown_socket_out = socket.socketpair() diff --git a/radicale/item/__init__.py b/radicale/item/__init__.py index a05304ff..7b240512 100644 --- a/radicale/item/__init__.py +++ b/radicale/item/__init__.py @@ -37,7 +37,7 @@ from typing import (Any, Callable, List, MutableMapping, Optional, Sequence, import vobject from radicale import storage # noqa:F401 -from radicale import pathutils +from radicale import pathutils, utils from radicale.item import filter as radicale_filter from radicale.log import logger @@ -335,6 +335,23 @@ def find_time_range(vobject_item: vobject.base.Component, tag: str return math.floor(start.timestamp()), math.ceil(end.timestamp()) +def verify(file: str, encoding: str): + logger.info("Verifying item: %s", file) + with open(file, "rb") as f: + content_raw = f.read() + content = content_raw.decode(encoding) + logger.info("Verifying item: %s has sha256sum %r", file, utils.sha256_str(content)) + try: + vobject_items = read_components(content) # noqa: F841 + except Exception as e: + logger.error("Verifying item: %s problem: %s", file, e) + logger.info("Request content (hexdump/lines):\n%s", utils.hexdump_lines(content)) + return False + else: + logger.info("Verifying item: %s successful", file) + return True + + class Item: """Class for address book and calendar entries."""