"""
io_utils.py — Safe I/O wrappers for the Starsend pipeline.

Handles partial writes, transient file system errors, and Dropbox
sync race conditions that can produce truncated JSON files.
"""

import json
import time
from pathlib import Path


def safe_read_json(filepath, retries=3):
    """Read and parse a JSON file with retry on decode/read errors.

    Handles:
    - Truncated files from Dropbox sync race conditions
    - Transient FileNotFoundError from cloud sync
    - json.JSONDecodeError from partial writes

    Args:
        filepath: Path to JSON file (str or Path).
        retries: Number of attempts before re-raising.

    Returns:
        Parsed JSON data (dict or list).

    Raises:
        Last exception if all retries exhausted.
    """
    filepath = Path(filepath)
    for i in range(retries):
        try:
            with open(filepath, "r", encoding="utf-8") as f:
                return json.load(f)
        except (json.JSONDecodeError, FileNotFoundError) as e:
            if i == retries - 1:
                raise e
            time.sleep(0.5)
