feat(serverless): network-volume warm cache (VolumeCache)#531
Conversation
…test state Wrap build_default_cache() parse+construct in try/except to prevent malformed RUNPOD_VOLUME_CACHE_MAX_GB from crashing worker startup; degrades to cache-disabled instead. Add sync() no-op to fake cache in test_run_worker_hydrates_registered_cache and wrap test body with reset_builtin_state_for_test() to prevent module-state leakage to subsequent tests (sync_after_job could fire and hit AttributeError).
|
Capy auto-review is paused for this organization because the usage-cycle auto-review limit has been reached. Increase the limit or turn it off in billing settings to resume automatic reviews. |
|
Promptless prepared a documentation update related to this change. Triggered by runpod-python PR #531 Documents the new Serverless network-volume warm cache: a new page covering the Review: Document Serverless network-volume warm cache (VolumeCache) |
…che-for-serverless-volumecache
There was a problem hiding this comment.
Pull request overview
This PR introduces a reusable serverless SDK primitive (VolumeCache) for warming local model/cache directories from a mounted network volume and syncing back deltas as per-worker tar “shards”, then wires it into the serverless worker lifecycle to persist model weights across worker recycling (SLS-367).
Changes:
- Added
runpod.serverless.utils.rp_volume_cache.VolumeCachewithhydrate(),sync(), andwarm()plus built-in helpers (build_default_cache,sync_after_job). - Auto-integrated the cache into the worker loop (
run_workerhydrates/registers) and job execution (run_jobdispatches a one-time async sync after a successful handler run). - Expanded public exports (
runpod.serverless.VolumeCache,runpod.serverless.utils.VolumeCache) and added a comprehensive unit test suite.
Reviewed changes
Copilot reviewed 8 out of 8 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
| tests/test_serverless/test_utils/test_rp_volume_cache.py | New unit test suite covering VolumeCache behavior, safety, retention, and worker/job wiring. |
| tests/test_serverless/test_utils_init.py | Updates runpod.serverless.utils.__all__ expectations to include VolumeCache. |
| tests/test_serverless/test_init.py | Updates runpod.serverless.__all__ expectations to include VolumeCache. |
| runpod/serverless/worker.py | Hydrates and registers the default cache before starting job scaling. |
| runpod/serverless/utils/rp_volume_cache.py | New implementation of VolumeCache plus built-in env-driven wiring helpers. |
| runpod/serverless/utils/init.py | Re-exports VolumeCache from runpod.serverless.utils. |
| runpod/serverless/modules/rp_job.py | Dispatches a one-time background cache sync after non-streaming jobs. |
| runpod/serverless/init.py | Re-exports VolumeCache from runpod.serverless. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
…e, namespace validation, lint
|
Addressed review feedback in ede2d5c: Copilot (behavioral):
CodeQL / code-quality:
Tests added for streaming sync, retention resilience, and namespace validation. Full suite green (566 tests, 94% coverage). Still open for a maintainer decision before merge: default-on vs opt-in for the serverless built-in when a volume is mounted (currently on, disabled via |
…che-for-serverless-volumecache
…che-for-serverless-volumecache
… open() in assert, unused global)
Summary
Adds
VolumeCache, a small explicit primitive that warms local directories (e.g. a model cache) across serverless workers using a mounted network volume. It turns a repeated multi-GB model download on every cold start into a one-time cost per endpoint. Stdlib-only, best-effort: any failure degrades to a cold worker and never raises into your handler.Interface — a closure
__enter__→hydrate(): reconcile volume → container (copy files missing/newer in the container).__exit__→sync(background=True): reconcile container → volume on a daemon thread so your code returns immediately; anatexitjoin (bounded by a timeout) completes it before the process ends.How it works
{volume}/.cache/{namespace}/…(namespacedefaults toRUNPOD_ENDPOINT_ID). No opaque archives, no accumulation.copy2to a unique temp +os.replace). Concurrent workers are last-writer-wins with no torn files.namespacemust be a single safe path component.Notes
>=3.10floor.withblock where it fits. There is no automatic worker-loop wiring or environment-variable toggle — an earlier draft had a built-in; it was removed in favor of the single explicit primitive. Auto-wiring can be layered on later if desired.Test plan
tests/test_serverless/test_utils/test_rp_volume_cache.py: availability gating, namespace validation, sync→hydrate round-trip, reconcile idempotence (unchanged files not recopied), newer-file protection, path exclusions, symlink skip, hydrate destination-containment (escape attempt blocked), context-manager enter/exit (+ exception propagation), background completion via the atexit join (bounded), temp-file exclusion, and best-effort swallow vs re-raise.tests/test_serverlesssuite green; repomake quality-checkpasses (557 tests, ~94% overall, ~98% on the new module).Docs
docs/serverless/volume_cache.mdand a short README section under Serverless.