Tejas Shah
08/15/2025, 7:39 AMMarvin
08/15/2025, 7:39 AMMarvin
08/15/2025, 7:42 AMPREFECT_API_URL
for the run you care about. In Prefect 3.x, that’s the knob that decides which server (API) your flow talks to.
Practical ways to do it, depending on how you’re running things:
- One-off in Python (recommended in notebooks)
from prefect import flow
from prefect.settings import PREFECT_API_URL, temporary_settings
@flow
def my_flow():
...
with temporary_settings({PREFECT_API_URL: "<https://prefect.example.com/api>"}):
my_flow()
Note: this must wrap the code that constructs/uses the Prefect client. In notebooks, this avoids having to restart the kernel.
- Set an environment variable for the process
import os
os.environ["PREFECT_API_URL"] = "<https://prefect.example.com/api>"
from prefect import flow
@flow
def my_flow(): ...
my_flow()
Set it before Prefect creates a client (ideally before importing/using Prefect). Otherwise use the temporary_settings
context manager.
- Programmatically via a client (if you’re making API calls yourself)
import anyio
from prefect.client.orchestration.client import PrefectClient
async def main():
async with PrefectClient(api="<https://prefect.example.com/api>") as client:
# do orchestration things here
...
anyio.run(main)
- Profiles (for switching targets without changing code)
Create/use a profile that sets PREFECT_API_URL
to the desired server, then activate that profile before running. See Settings & profiles and Manage settings.
Important notes for deployments/workers
- The server your flow run uses is ultimately determined by the environment the worker runs in. Changing PREFECT_API_URL
inside flow code won’t move an already-submitted deployment run to a different server.
- Set PREFECT_API_URL
in the worker’s environment (or via your deployment’s environment/base variables) so the worker talks to the right API.
- For self-hosted behind Nginx, use the externally reachable URL and include the /api
suffix (e.g., `https://prefect.example.com/api`). If authentication is enabled, ensure the appropriate credentials (e.g., API key) are also set in that environment.
Docs for reference:
- Settings and profiles: Concepts: Settings & profiles
- Managing settings: How-to: Manage settings
- Server CLI/self-hosted: Self-hosted server CLI
If you share how you’re launching the flow (direct call in a notebook vs. deployment run on a worker), I can tailor the exact snippet. I know, thrilling.Tejas Shah
08/15/2025, 7:43 AMMarvin
08/15/2025, 7:43 AMMarvin
08/15/2025, 7:44 AMfrom prefect import flow
from prefect.settings import PREFECT_API_URL, temporary_settings
@flow
def my_flow(tag):
print(f"running on {tag}")
with temporary_settings({PREFECT_API_URL: "<https://server-a.example.com/api>"}):
my_flow("server A")
with temporary_settings({PREFECT_API_URL: "<https://server-b.example.com/api>"}):
my_flow("server B")
- Concurrently to two servers from the same process is possible but fiddly; use separate kernels/processes to avoid config cross-talk. One kernel per server keeps your sanity.
Option B: Deployments/workers
- Run two workers on the same machine, each pointed at a different server:
# Terminal 1
export PREFECT_API_URL="<https://server-a.example.com/api>"
export PREFECT_API_KEY="...key for server A..."
prefect worker start -p pool-a
# Terminal 2
export PREFECT_API_URL="<https://server-b.example.com/api>"
export PREFECT_API_KEY="...key for server B..."
prefect worker start -p pool-b
Each worker will poll its own server/work pool. Submit deployments to the corresponding pool, and they’ll run on the right server.
Notes
- Always include the /api
suffix in the URL.
- Use the correct API key per server.
- Profiles are another way to switch targets without changing code; just activate the desired profile per process/terminal.
- Behind Nginx, ensure each server is reachable at a distinct external URL.
Docs if you want the gory details:
- Settings & profiles: Concepts: Settings & profiles
- Managing settings: How-to: Manage settings
- Self-hosted server CLI: Self-hosted server CLI