Spaces:
Running
Running
| import time | |
| from pathlib import Path | |
| from apscheduler.schedulers.asyncio import AsyncIOScheduler | |
| _scheduler: AsyncIOScheduler | None = None | |
| def _cleanup_old_files(upload_dir: Path, output_dir: Path, max_age_seconds: int = 3600) -> None: | |
| """Delete MP3 files older than max_age_seconds. Runs in a thread pool.""" | |
| now = time.time() | |
| for f in upload_dir.glob("*.mp3"): | |
| try: | |
| if now - f.stat().st_mtime > max_age_seconds: | |
| f.unlink(missing_ok=True) | |
| except OSError: | |
| pass | |
| for f in output_dir.rglob("*.mp3"): | |
| try: | |
| if now - f.stat().st_mtime > max_age_seconds: | |
| f.unlink(missing_ok=True) | |
| except OSError: | |
| pass | |
| # Remove empty per-job output directories left after file cleanup. | |
| for d in sorted(output_dir.rglob("*"), reverse=True): | |
| if not d.is_dir(): | |
| continue | |
| try: | |
| next(d.iterdir()) | |
| except StopIteration: | |
| d.rmdir() | |
| except OSError: | |
| pass | |
| def start_cleanup_scheduler(upload_dir: Path, output_dir: Path) -> None: | |
| global _scheduler | |
| _scheduler = AsyncIOScheduler() | |
| _scheduler.add_job( | |
| _cleanup_old_files, | |
| "interval", | |
| minutes=15, | |
| args=[upload_dir, output_dir], | |
| executor="default", | |
| ) | |
| _scheduler.start() | |
| def stop_cleanup_scheduler() -> None: | |
| global _scheduler | |
| if _scheduler is not None: | |
| _scheduler.shutdown(wait=False) | |
| _scheduler = None | |