Capistrano-inspired deployment automation for Django and FastAPI apps.
Project description
Pystrano
Capistrano-inspired deployment automation for Django and FastAPI apps.
Pystrano helps you define repeatable SSH-based Python web deployment workflows with simple YAML playbooks.
- Website: https://pystrano.com
- Documentation: https://pystrano.com/docs
- PyPI: https://pypi.org/project/pystrano/
- Issues: https://github.com/lexpank/pystrano/issues
Project Status
Pystrano currently supports Django and FastAPI deployment workflows.
Other Python applications may be possible through custom commands, but they are not the primary supported workflow yet.
Why Pystrano?
Use Pystrano if:
- you deploy Django or FastAPI apps to one or more servers over SSH
- you want repeatable deployment workflows
- you prefer simple YAML playbooks
- you want release-oriented deploys and rollback-friendly structure
- you are deploying to VPS-style servers with tools like Gunicorn and systemd
Pystrano may be adaptable to other Python applications through custom commands, but Django and FastAPI are the supported and documented workflows today.
Consider other tools if:
- you need full infrastructure provisioning
- you need container orchestration
- you need complex multi-cloud workflows
- you already have a mature CI/CD platform handling deployments
- you need a fully managed deployment platform
Installation
Pystrano requires Python 3.12 or newer.
pip install pystrano
Quickstart
Pystrano reads a deployment config from this default path:
deploy/<app_name>/<environment_name>/deployment.yml
For an app named api and an environment named production, create:
deploy/api/production/deployment.yml
Build that file interactively:
pystrano init production api
The init flow also writes a starter gunicorn.service or uvicorn.service
file referenced by the generated config.
Then inspect the remote commands without executing them:
pystrano setup production api --dry-run
pystrano deploy production api --dry-run
Run the setup flow when the server is ready to be provisioned:
pystrano setup production api
Run the deployment flow:
pystrano deploy production api
Use a different config root or file name when needed:
pystrano init production api --deploy-config-dir ./ops/deploy --config-file-name pystrano.yml
pystrano deploy production api --deploy-config-dir ./ops/deploy --config-file-name pystrano.yml
Add --verbose to show more Fabric, Invoke, and Paramiko output.
Configuration
A deployment config contains a common section and a servers list.
Values in common apply to every server. Values on an individual server override
the common values for that server.
Use pystrano init <environment> <app> to create this file interactively. The
command writes to deploy/<app>/<environment>/deployment.yml by default,
generates the referenced systemd service file, and prompts before overwriting an
existing file. pystrano configure <environment> <app> is accepted as an alias.
config_version: 2
common:
source_code_url: "git@github.com:example/example-django-app.git"
framework: "django"
project_root: "apps/example-django-app"
project_user: "deploy"
venv_dir: ".venv"
package_manager: "pip"
dependency_file: "requirements.txt"
keep_releases: 5
system_packages: |
libpq-dev
python3-dev
env_file: "./deploy/api/production/.env"
ssh_known_hosts: "github.com"
service_file: "./deploy/api/production/gunicorn.service"
secrets: "./deploy/api/production/secret.json"
branch: "main"
clone_depth: 1
servers:
- host: "app1.example.com"
port: 22
run_migrations: true
collect_static_files: true
- host: "app2.example.com"
run_migrations: false
collect_static_files: true
Common fields used by the current implementation:
config_version: Pystrano config format version. Version 2 configs should declare2; missing or older values produce a runtime compatibility warning.source_code_url: Git repository URL cloned on each deploy.framework: Deployment workflow. Supported values aredjangoandfastapi. Defaults todjango.project_root: Project directory under/home/<project_user>/.project_user: Remote user that owns and deploys the app.venv_dir: Virtualenv directory under/home/<project_user>/.package_manager: Dependency installer. Supported values arepipanduv. Defaults topip.dependency_file: Dependency file used during install. Defaults torequirements.txtforpipanduv.lockforuv.dependency_install_command: Optional exact dependency install command. When set, Pystrano runs it instead of the built-inpiporuvcommand.keep_releases: Number of release directories to keep. Use0or less to keep all.system_packages: Extra packages installed duringsetup.env_file: Local dotenv file copied to the remote shared directory during deploy.ssh_known_hosts: Semicolon-separated hosts added withssh-keyscanduringsetup.service_file: Optional local systemd service file copied duringsetup.secrets: Optional semicolon-separated local files copied duringsetupand linked into releases.branch: Git branch cloned during deploy.clone_depth: Shallow clone depth. Use0or less for a full clone.revision: Optional tag, SHA, or ref checked out after cloning. When set, Pystrano performs a full clone.migration_command: FastAPI migration command. Defaults to<venv_dir>/bin/alembic upgrade head.static_files_command: FastAPI static files command. Required whenframework: fastapiandcollect_static_files: true.
Server fields:
host: SSH host.port: SSH port. Defaults to22.run_migrations: Whether to run the framework migration step during deploy.collect_static_files: Whether to run the framework static files step during deploy.
Deployment Workflow
pystrano setup <environment> <app> connects as root and prepares the remote
host. The setup flow creates the project user, copies authorized SSH keys,
creates the shared/releases/current directory structure, installs base packages,
creates the virtualenv, updates known hosts, optionally installs a systemd
service file, and optionally uploads secret files to the shared directory.
pystrano deploy <environment> <app> connects as project_user and creates a
timestamped release under:
/home/<project_user>/<project_root>/releases/<timestamp>
The deploy flow clones the configured repository, copies the dotenv file into
the shared directory, links shared assets, installs Python dependencies, links
configured secrets, optionally runs framework-specific static collection and
migrations, updates the current symlink, optionally restarts the configured
systemd service, and removes old releases according to keep_releases.
For package_manager: pip, dependencies are installed with:
<venv_dir>/bin/pip install -r <dependency_file>
For package_manager: uv with dependency_file: uv.lock, Pystrano ensures
uv exists in the virtualenv, then runs:
UV_PROJECT_ENVIRONMENT=<venv_dir> <venv_dir>/bin/uv sync --frozen --no-dev
If package_manager: uv is configured with another dependency file, Pystrano
runs:
<venv_dir>/bin/uv pip install --python <python_path> -r <dependency_file>
Set dependency_install_command when your project needs a custom flow such as
additional uv flags or dependency groups.
For Django, the framework steps are:
<python_path> manage.py collectstatic --noinput
<python_path> manage.py migrate
For FastAPI, migrations default to:
<venv_dir>/bin/alembic upgrade head
Set migration_command to override the FastAPI migration command. Set
static_files_command when a FastAPI deployment needs a custom static asset
build step.
Pystrano does not currently expose a rollback CLI command. Deployments are
release-oriented, so a maintainer can inspect previous release directories on
the server and manually repoint the current symlink if needed. Keep
keep_releases high enough for the rollback window you want.
Example: Django on a VPS
See examples/django-gunicorn-systemd for a starting point that combines Django, Gunicorn, systemd, SSH deployment, shared files, and release cleanup.
Example: FastAPI on a VPS
See examples/fastapi-uvicorn-systemd for a starting point that combines FastAPI, Uvicorn, systemd, SSH deployment, Alembic migrations, shared files, and release cleanup.
Maintainer Checklist
Recommended GitHub repository metadata:
- Repository description:
Capistrano-inspired deployment automation for Django and FastAPI apps. - Website:
https://pystrano.com - Topics:
python,django,fastapi,deployment,deploy,cli,yaml,capistrano,devops,ssh,systemd,gunicorn,uvicorn,vps
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file pystrano-2.0.0.tar.gz.
File metadata
- Download URL: pystrano-2.0.0.tar.gz
- Upload date:
- Size: 25.1 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
4ac0207a8a514636973859460371dba185231f27e606e959e91a7ec54922389e
|
|
| MD5 |
6b65768b196bad1cb778ae477aff603a
|
|
| BLAKE2b-256 |
3939f1573a67c23bac38c25ff86c87ec62d819e01cca9c419da68ec8aa62ce81
|
File details
Details for the file pystrano-2.0.0-py3-none-any.whl.
File metadata
- Download URL: pystrano-2.0.0-py3-none-any.whl
- Upload date:
- Size: 25.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e8f24733f864f618296d8bc8f61d338978947192ad0d1dbf00648084fe182872
|
|
| MD5 |
0077f83c0fb0ff901395bfe4cff1860a
|
|
| BLAKE2b-256 |
fff81afb8cb1d9601d0dcfd56cdc96e16ca5369a208883e6bac4586ddb22c02a
|