"""Author RAG Chatbot SaaS — GeoIP Database Update Task. Runs weekly. Downloads the latest MaxMind GeoLite2 City database. Requires MAXMIND_LICENSE_KEY env var (free MaxMind account). """ import os import structlog from app.tasks.celery_app import celery_app logger = structlog.get_logger(__name__) @celery_app.task(name="app.tasks.geo_update_task.update_geoip_database") def update_geoip_database(): """Download and update the MaxMind GeoLite2 City database.""" import httpx import tarfile import shutil from app.config import get_settings cfg = get_settings() license_key = os.environ.get("MAXMIND_LICENSE_KEY", "") if not license_key: logger.warning("MAXMIND_LICENSE_KEY not set — skipping GeoIP update") return url = ( f"https://download.maxmind.com/app/geoip_download" f"?edition_id=GeoLite2-City&license_key={license_key}&suffix=tar.gz" ) try: with httpx.Client(timeout=60) as client: response = client.get(url) response.raise_for_status() # Write to temp file tmp_path = "/tmp/geolite2.tar.gz" with open(tmp_path, "wb") as f: f.write(response.content) # Extract .mmdb file with tarfile.open(tmp_path, "r:gz") as tar: for member in tar.getmembers(): if member.name.endswith(".mmdb"): member.name = os.path.basename(member.name) tar.extract(member, path=os.path.dirname(cfg.GEO_DB_PATH)) break os.remove(tmp_path) logger.info("GeoIP database updated successfully") except Exception as e: logger.error("GeoIP update failed", error=str(e))