Geoff Irons
07/09/2025, 9:50 PMMarvin
07/09/2025, 9:50 PMMarvin
07/09/2025, 9:50 PMpython
from prefect import flow
from prefect.deployments import deploy
@flow
def my_flow():
pass
# Deploy the same flow with different names/tags for test and prod
deploy(
my_flow,
name="test/my-flow", # Using a prefix pattern
tags=["test"],
work_pool="test-pool"
)
deploy(
my_flow,
name="prod/my-flow",
tags=["prod"],
work_pool="prod-pool"
)
2. Batch Deployment of Multiple Flows
python
from prefect import flow
from prefect.deployments import deploy
@flow
def flow1(): pass
@flow
def flow2(): pass
@flow
def flow3(): pass
# Deploy all test flows at once
flows = [flow1, flow2, flow3]
for f in flows:
deploy(
f,
name=f"test/{f.__name__}",
tags=["test"],
work_pool="test-pool"
)
3. Using Different Work Pools
- Create separate work pools for test and production
- Assign deployments to their respective work pools
- This provides isolation and different infrastructure configurations
Best Practices for Test/Prod Split:
1. Consistent Naming Convention
- Use prefixes like "test/" and "prod/" in deployment names
- This keeps your deployments organized and easily filterable
2. Tags for Environment
- Always tag deployments with their environment ("test" or "prod")
- Makes it easy to filter and manage deployments
3. Separate Work Pools
- Use different work pools for test and production
- Allows for different infrastructure and scaling requirements
4. Environment-Specific Variables
- Use different parameters and job variables for test and prod environments
- Can be set at the deployment level
While you can't have a single deployment running multiple different flows (each deployment is tied to a specific flow), you can:
- Use consistent naming patterns
- Deploy multiple flows at once with shared configuration
- Use tags and work pools to organize and manage your deployments effectively
The key is to use a combination of these approaches to create a clean, maintainable separation between your test and production environments. This gives you the organization you're looking for while maintaining the flexibility to manage each flow independently when needed.
You can find more detailed examples and patterns in the deployment documentation.Geoff Irons
07/09/2025, 10:02 PMMarvin
07/09/2025, 10:02 PMMarvin
07/09/2025, 10:03 PMprefect.yaml
file that defines your deployment configurations. Here's how to structure it:
yaml
# prefect.yaml
deployments:
- name: test/my-flow
entrypoint: flows/my_flow.py:my_flow
work_pool:
name: test-pool
tags: [test]
schedule: null
- name: prod/my-flow
entrypoint: flows/my_flow.py:my_flow
work_pool:
name: prod-pool
tags: [prod]
schedule: null
# Additional flows
- name: test/another-flow
entrypoint: flows/another_flow.py:another_flow
work_pool:
name: test-pool
tags: [test]
schedule: null
- name: prod/another-flow
entrypoint: flows/another_flow.py:another_flow
work_pool:
name: prod-pool
tags: [prod]
schedule: null
Then deploy using the CLI:
bash
# Deploy all flows
prefect deploy
# Or deploy specific flows
prefect deploy --name 'test/*' # Deploy all test flows
prefect deploy --name 'prod/*' # Deploy all prod flows
# Deploy a specific flow
prefect deploy --name 'test/my-flow'
You can also use different YAML files for different environments:
yaml
# test.yaml
deployments:
- name: my-flow
entrypoint: flows/my_flow.py:my_flow
work_pool:
name: test-pool
tags: [test]
schedule: null
- name: another-flow
entrypoint: flows/another_flow.py:another_flow
work_pool:
name: test-pool
tags: [test]
schedule: null
yaml
# prod.yaml
deployments:
- name: my-flow
entrypoint: flows/my_flow.py:my_flow
work_pool:
name: prod-pool
tags: [prod]
schedule: null
- name: another-flow
entrypoint: flows/another_flow.py:another_flow
work_pool:
name: prod-pool
tags: [prod]
schedule: null
Then deploy using:
bash
prefect deploy --file test.yaml # Deploy test environment
prefect deploy --file prod.yaml # Deploy prod environment
Best Practices for CLI Deployments:
1. Consistent File Structure
project/
├── flows/
│ ├── my_flow.py
│ └── another_flow.py
├── prefect.yaml # or separate test.yaml and prod.yaml
└── requirements.txt
2. Use Environment-Specific Work Pools
- Create separate work pools for test and production
- Reference them in your YAML configurations
3. Naming Conventions
- Use consistent prefixes in deployment names (test/, prod/)
- Keep entrypoint paths relative to your project root
4. Tags and Organization
- Use tags consistently to identify environments
- Group related deployments together in your YAML files
5. Version Control
- Keep your YAML configurations in version control
- Consider using environment variables for sensitive values
The CLI approach with YAML configuration provides a declarative way to manage your deployments and makes it easy to version control your deployment configurations. You can find more details about the YAML configuration options in the Prefect documentation.Geoff Irons
07/09/2025, 10:22 PMMarvin
07/09/2025, 10:22 PMMarvin
07/09/2025, 10:23 PMyaml
# prefect.yaml
definitions:
# Define common configurations
work_pools:
test: &test_pool
name: test-pool
work_queue_name: default
job_variables:
env: test
memory: 1GB
prod: &prod_pool
name: prod-pool
work_queue_name: default
job_variables:
env: prod
memory: 2GB
# Common configurations that can be shared
configs:
test_base: &test_base
work_pool: *test_pool
tags: [test]
schedule: null
description: "Test deployment"
prod_base: &prod_base
work_pool: *prod_pool
tags: [prod]
schedule: null
description: "Production deployment"
deployments:
# Test deployments
- name: test/flow-1
entrypoint: flows/flow1.py:flow1
<<: *test_base # Inherit test base config
description: "Flow 1 Test" # Override specific fields
- name: test/flow-2
entrypoint: flows/flow2.py:flow2
<<: *test_base
description: "Flow 2 Test"
# Production deployments
- name: prod/flow-1
entrypoint: flows/flow1.py:flow1
<<: *prod_base
description: "Flow 1 Production"
- name: prod/flow-2
entrypoint: flows/flow2.py:flow2
<<: *prod_base
description: "Flow 2 Production"
You can also create more specific configurations by combining and extending base configurations:
yaml
definitions:
# ... previous definitions ...
configs:
# Base configurations
common: &common_base
schedule: null
parameters: {}
test_base: &test_base
<<: *common_base # Inherit common configuration
work_pool: *test_pool
tags: [test]
# Specific configurations for different types of flows
etl_test: &etl_test
<<: *test_base # Inherit test base
tags: [test, etl] # Add additional tags
parameters:
batch_size: 100
ml_test: &ml_test
<<: *test_base
tags: [test, ml]
parameters:
model_version: "test"
deployments:
- name: test/etl-flow-1
entrypoint: flows/etl1.py:etl_flow
<<: *etl_test # Use ETL-specific configuration
- name: test/ml-flow-1
entrypoint: flows/ml1.py:train_model
<<: *ml_test # Use ML-specific configuration
Some useful patterns for sharing configurations:
1. Environment-Specific Settings
yaml
definitions:
env_vars:
test: &test_env
DATABASE_URL: "<postgresql://test-db:5432>"
API_KEY: "test-key"
prod: &prod_env
DATABASE_URL: "<postgresql://prod-db:5432>"
API_KEY: "prod-key"
configs:
test_base: &test_base
work_pool: *test_pool
job_variables:
<<: *test_env # Include all test environment variables
2. Resource Configurations
yaml
definitions:
resources:
small: &small_resources
memory: "1GB"
cpu: "0.5"
large: &large_resources
memory: "4GB"
cpu: "2"
configs:
test_base: &test_base
work_pool:
name: test-pool
job_variables:
<<: *small_resources # Include resource configuration
3. Schedule Patterns
yaml
definitions:
schedules:
hourly: &hourly
interval: 3600
daily: &daily
cron: "0 0 * * *"
deployments:
- name: test/hourly-flow
<<: *test_base
schedule: *hourly
- name: test/daily-flow
<<: *test_base
schedule: *daily
Key benefits of this approach:
- Reduces duplication in your configuration
- Makes it easier to maintain consistent settings across deployments
- Allows for easy updates to shared configurations
- Keeps your prefect.yaml
file organized and readable
- Makes it clear which configurations are being used whereMarvin
07/09/2025, 10:23 PM