Brady Mitchell
08/15/2025, 6:19 PMMarvin
08/15/2025, 6:19 PMMarvin
08/15/2025, 6:21 PMPREFECT_LOCAL_STORAGE_PATH
at startup, so it falls back to {PREFECT_HOME}/storage
(default {home}/.prefect/storage
).
In Prefect 3.x:
- The local result store defaults to {PREFECT_HOME}/storage
.
- PREFECT_LOCAL_STORAGE_PATH
overrides that, but only if the environment variable is present in the process before Prefect loads settings.
Common reasons it still uses the default:
- The env var isn’t set in the worker/job environment (e.g., set in your shell, but your Docker/Kubernetes worker runs with a different env).
- It’s set after Prefect is imported (settings are resolved at startup).
- You’re setting it in one place (e.g., agent/worker) but not in the actual runtime (e.g., Kubernetes job spawned by the worker).
- The path isn’t writable or doesn’t exist, and something in your setup falls back to default.
What to do:
- Make sure the variable is set where the run actually executes.
- Docker worker: set it on the worker container env (and any job container, if different).
- Kubernetes worker: add it to the worker Pod env and to the job env via your work pool/deployment.
- Set it before the process starts.
- Alternatively, set PREFECT_HOME=/home/prefect/cache
and let Prefect use /home/prefect/cache/storage
as the default. Create the directory and ensure it’s writable.
Quick check inside your flow (early, before importing much else) to confirm what the run sees:
import os
print("PREFECT_LOCAL_STORAGE_PATH =", os.getenv("PREFECT_LOCAL_STORAGE_PATH"))
print("PREFECT_HOME =", os.getenv("PREFECT_HOME"))
If you’re on Prefect 2.x, note that storage blocks or deployment-specific settings can override globals. In 3.x, PREFECT_LOCAL_STORAGE_PATH
and/or PREFECT_HOME
should be sufficient if correctly set in the runtime.
Docs for reference:
- Settings and profiles (how Prefect resolves settings): Settings & Profiles
If you share:
- Your Prefect version
- How you’re running (worker type, Docker/K8s/etc.)
- Where you set the env var(s)
…I can point at the exact place to set it so Prefect stops being “helpful” and writing to ~/.prefect/storage
.Brady Mitchell
08/15/2025, 6:36 PMMarvin
08/15/2025, 6:36 PMMarvin
08/15/2025, 6:38 PMPREFECT_HOME
as {PREFECT_HOME}/storage
. The PREFECT_LOCAL_STORAGE_PATH
variable you’re setting is not a documented/recognized setting in 3.x, so Prefect keeps using the default {home}/.prefect/storage
.
Given you’re on Kubernetes workers:
- Set PREFECT_HOME=/home/prefect/cache
in the job pod’s environment (not just the worker pod).
- Ensure /home/prefect/cache/storage
exists and is writable by the container user.
- If you’re using a ConfigMap, make sure it’s referenced by the job template used by the work pool so the job pod actually sees it.
Quick ways to verify in the running flow pod:
import os
print("PREFECT_HOME =", os.getenv("PREFECT_HOME"))
print("PREFECT_LOCAL_STORAGE_PATH =", os.getenv("PREFECT_LOCAL_STORAGE_PATH"))
If PREFECT_HOME
is unset in the job pod, Prefect will fall back to /home/prefect/.prefect/storage
.
Example snippet for your Kubernetes work pool job template to ensure the env var is present and the path exists/mounted:
pod:
env:
- name: PREFECT_HOME
value: /home/prefect/cache
volumeMounts:
- name: cache
mountPath: /home/prefect/cache
volumes:
- name: cache
emptyDir: {} # or use a PVC if you want persistence
Or, if you prefer to inject via ConfigMap:
pod:
envFrom:
- configMapRef:
name: your-configmap-with-prefect-home
Reference: Settings & Profiles
If you can share your work pool’s job template (or how you attach the ConfigMap to the job pods), I can point at the exact spot to fix.Brady Mitchell
08/15/2025, 6:43 PMlocal_storage_path
Marvin
08/15/2025, 6:43 PMMarvin
08/15/2025, 6:44 PMPREFECT_LOCAL_STORAGE_PATH
is a valid setting in 3.x and maps to local_storage_path
. If Prefect is still writing to /home/prefect/.prefect/storage
, it usually means the job pod isn’t actually seeing your env var at runtime, or something else is forcing the default.
Quickest way to confirm inside the flow pod:
import os
from prefect.settings import get_current_settings
print("env PREFECT_LOCAL_STORAGE_PATH =", os.getenv("PREFECT_LOCAL_STORAGE_PATH"))
s = get_current_settings()
print("effective local_storage_path =", s.local_storage_path)
print("PREFECT_HOME (effective) =", s.home)
Checklist for Kubernetes workers:
- Put the env var on the job pod, not just the worker. The worker’s env does not automatically propagate to submitted jobs. Add it to the work pool’s job template or the deployment’s pod spec.
- Ensure the target path exists and is writable. Mount an emptyDir
or PVC at /home/prefect/cache/storage
(or whatever you’re setting).
- If you want belt-and-suspenders, also set PREFECT_HOME=/home/prefect/cache
so the default {PREFECT_HOME}/storage
aligns with your desired path.
Example job template bits:
pod:
env:
- name: PREFECT_LOCAL_STORAGE_PATH
value: /home/prefect/cache/storage
# optional but helpful:
- name: PREFECT_HOME
value: /home/prefect/cache
volumeMounts:
- name: cache
mountPath: /home/prefect/cache
volumes:
- name: cache
emptyDir: {}
If the snippet above shows effective local_storage_path
is your custom path but you still see writes to ~/.prefect/storage
, please share the traceback or which component is writing there (results, source checkout, etc.). That would point to a specific code path that’s ignoring the setting — in which case we’ll file it.
Docs for the setting you cited: https://docs.prefect.io/v3/api-ref/settings-ref#local-storage-pathBrady Mitchell
08/15/2025, 6:50 PMlogger = get_run_logger()
<http://logger.info|logger.info>(f"PREFECT_LOCAL_STORAGE_PATH: {PREFECT_LOCAL_STORAGE_PATH}")
<http://logger.info|logger.info>(f"current_settings: {pprint(get_current_settings())}")
Inside a flow results in this:
PREFECT_LOCAL_STORAGE_PATH: /home/prefect/cache/storage
current_settings: None
Marvin
08/15/2025, 6:50 PMMarvin
08/15/2025, 6:51 PMcurrent_settings: None
is just pprint
being “helpful.” pprint.pprint()
prints and returns None. Use pprint.pformat()
or inspect specific fields.
Try this inside the flow:
from prefect.settings import get_current_settings
from pprint import pformat
import os, prefect
logger = get_run_logger()
s = get_current_settings()
<http://logger.info|logger.info>(f"prefect: {prefect.__version__}")
<http://logger.info|logger.info>(f"env PREFECT_LOCAL_STORAGE_PATH = {os.getenv('PREFECT_LOCAL_STORAGE_PATH')}")
<http://logger.info|logger.info>(f"effective local_storage_path = {s.local_storage_path}")
<http://logger.info|logger.info>(f"effective PREFECT_HOME = {s.home}")
<http://logger.info|logger.info>(f"PREFECT_PROFILE = {os.getenv('PREFECT_PROFILE')}")
<http://logger.info|logger.info>(f"all settings = {pformat(s.model_dump())}")
If effective local_storage_path
shows /home/prefect/cache/storage
but you still see errors about /home/prefect/.prefect/storage
, that path is likely coming from something that uses PREFECT_HOME
directly (not local_storage_path
) — e.g., other internal caches. In that case, set both so everything aligns:
- PREFECT_LOCAL_STORAGE_PATH=/home/prefect/cache/storage
- PREFECT_HOME=/home/prefect/cache
Kubernetes specifics:
- Put these env vars on the job pod spec (work pool job template or deployment), not just the worker pod.
- Mount the path and ensure it’s writable by the container user:
pod:
env:
- name: PREFECT_HOME
value: /home/prefect/cache
- name: PREFECT_LOCAL_STORAGE_PATH
value: /home/prefect/cache/storage
volumeMounts:
- name: cache
mountPath: /home/prefect/cache
volumes:
- name: cache
emptyDir: {} # or a PVC if you want persistence
If effective local_storage_path
is correct but you still get a traceback referencing ~/.prefect/storage
, paste that traceback. We can identify which component is ignoring the setting and squash it accordingly.
Docs you cited for the setting: local_storage_path