From d66c5d21e9e0fdd709fc7e4d0d2c5969e95c3296 Mon Sep 17 00:00:00 2001 From: nullrouten0 Date: Tue, 27 Oct 2026 17:15:33 -0700 Subject: [PATCH] Log request values and MQTT topics with %r so they cannot add log lines (#181) * Log request values and MQTT topics with %r so they cannot add log lines /api/packets logged an unparseable since, portnum or node id filter with an f-string, so the decoded query value went into the log as is. ?since=1%0A wrote a second, forged log line, and escape sequences (ESC, BEL) reached whoever reads the log in a terminal. The ingest error added in startdb.py logged the MQTT topic with %s. Use %r for these values, as the gateway_id warning in mqtt_store.py already does, so CR, LF, ESC and other control characters appear escaped. Co-Authored-By: Claude Opus 5.5 * Remove a blank line that fails the ruff format check `ruff format --check .` (the Ruff workflow, ruff 0.13.3) fails on develop because of this line, so every pull request's lint job is red regardless of its content. Co-Authored-By: Claude Opus 5.5 --------- Co-authored-by: Nathan <201262769+nullrouten0@users.noreply.github.com> Co-authored-by: Claude Opus 5.5 --- meshview/web_api/api.py | 10 +++++----- startdb.py | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/meshview/web_api/api.py b/meshview/web_api/api.py index fbf8e2b..5d5376e 100644 --- a/meshview/web_api/api.py +++ b/meshview/web_api/api.py @@ -293,7 +293,7 @@ async def api_packets(request): try: since = int(since_str) except ValueError: - logger.warning(f"Invalid 'since' value (expected microseconds): {since_str}") + logger.warning("Invalid 'since' value (expected microseconds): %r", since_str) # --- Parse portnum --- portnum = None @@ -301,7 +301,7 @@ async def api_packets(request): try: portnum = int(portnum_str) except ValueError: - logger.warning(f"Invalid portnum: {portnum_str}") + logger.warning("Invalid portnum: %r", portnum_str) # --- Parse node filters --- from_node_id = None @@ -312,19 +312,19 @@ async def api_packets(request): try: from_node_id = int(from_node_id_str, 0) except ValueError: - logger.warning(f"Invalid from_node_id: {from_node_id_str}") + logger.warning("Invalid from_node_id: %r", from_node_id_str) if to_node_id_str: try: to_node_id = int(to_node_id_str, 0) except ValueError: - logger.warning(f"Invalid to_node_id: {to_node_id_str}") + logger.warning("Invalid to_node_id: %r", to_node_id_str) if node_id_str: try: node_id = int(node_id_str, 0) except ValueError: - logger.warning(f"Invalid node_id: {node_id_str}") + logger.warning("Invalid node_id: %r", node_id_str) # --- Fetch packets using explicit filters --- contains_for_query = contains diff --git a/startdb.py b/startdb.py index 5b55d98..b1326e8 100644 --- a/startdb.py +++ b/startdb.py @@ -347,7 +347,7 @@ async def load_database_from_mqtt( await mqtt_store.process_envelope(topic, env) except Exception: # One bad or unexpected message must not stop ingestion for everyone. - logger.exception("Failed to store a message from topic %s; skipping it", topic) + logger.exception("Failed to store a message from topic %r; skipping it", topic) # -------------------------