import os import json import shutil import zipfile from datetime import datetime from typing import List, Dict class SyncManager: """ Manages the creation of export packages and synchronization of files. """ def __init__(self): self.manifest_name = "bridge_manifest.json" def create_export_package( self, source_root: str, changes: Dict[str, List[str]], output_zip: str, commit_message: str ) -> None: """ Creates a ZIP file containing modified/added files and a manifest. """ with zipfile.ZipFile(output_zip, "w", zipfile.ZIP_DEFLATED) as zip_file: manifest_data = { "timestamp": datetime.now().isoformat(), "commit_message": commit_message, "changes": changes } manifest_content = json.dumps(manifest_data, indent=4) zip_file.writestr(self.manifest_name, manifest_content) for category in ["added", "modified"]: for relative_path in changes.get(category, []): full_path = os.path.join(source_root, relative_path) if os.path.exists(full_path): zip_file.write(full_path, relative_path) def apply_package(self, package_path: str, destination_root: str) -> str: """ Extracts the package and applies changes to the destination folder. """ with zipfile.ZipFile(package_path, "r") as zip_file: with zip_file.open(self.manifest_name) as f: manifest = json.load(f) changes = manifest.get("changes", {}) for relative_path in changes.get("deleted", []): target_path = os.path.join(destination_root, relative_path) if os.path.exists(target_path): os.remove(target_path) for file_info in zip_file.infolist(): if file_info.filename == self.manifest_name: continue zip_file.extract(file_info, destination_root) return manifest.get("commit_message", "") def copy_file(self, source_path: str, destination_path: str) -> None: """ Copies a single file from source to destination, creating directories. """ os.makedirs(os.path.dirname(destination_path), exist_ok=True) shutil.copy2(source_path, destination_path)