appenv pins Python packages to exact versions and exposes their binaries
via symlinks — one file, no installation step. Drop it into a repository,
commit it, and every checkout (local or remote) gets the same tools at the
same versions by running ./http, ./pytest, ./batou, or whatever you need.
appenv never modifies your system — all state lives in .appenv/ inside
the project directory. Remove that folder and nothing is left behind.
Built on uv for environment management.
Someone gave you a project that already uses appenv? Just run the command:
git clone <project> && cd <project>
./http # First run sets up everything automaticallyRunning the command will get an appenv-managed uv if it's not globally available on your system.
No uv.lock (should be committed) or dependencies changed?
./appenv update-lockfile(Only needed again after manually editing pyproject.toml)
Use ./appenv uv add/remove to manage your dependencies or just use uv as you are used to it.
Already an appenv user and still using requirements.txt instead of pyproject.toml?
uvx appenv migrateRequires Python 3.9+ (managed environments need 3.10+). uv 0.5.0+ is auto-installed if not found.
Get appenv via uvx or download the single-file script.
appenv init will ask you some questions and set up the project (interactive
by default — pass --binary and --dep for non-interactive use). The example
assumes that you want to run a binary called http from the httpie package.
uvx is part of uv — the easiest way to start:
# appenv init is interactive
# Answer:
# httpie as dependency
# http as binary
uvx appenv init
./httpNo uv installed? Download appenv directly:
curl -sL https://raw.githubusercontent.com/flyingcircusio/appenv/master/src/appenv.py -o appenv
chmod +x appenv
# appenv init is interactive
# Answer:
# httpie as dependency
# http as binary
./appenv init
./httpWhat just happened?
- appenv installed itself inplace by adding the
./appenvscript. initcreatedpyproject.tomland a symlinkhttp → appenv../httpset up the venv with pinned versions fromuv.lock, then ran thehttpbinary (from the httpie package)
The repository now contains:
myproject/
├── appenv # The appenv script
├── http -> appenv # Runs the `http` binary from installed deps
├── pyproject.toml # Project config and dependency list
└── uv.lock # Exact versions of all dependenciesAll of these files should be VCS-tracked to ensure a consistent environment across all machines.
For scripts and CI pipelines — no TTY needed:
appenv init --binary http --dep httpie --name myprojectFor dev tooling, uv run and other uv commands work transparently.
appenv automatically creates a .venv symlink to make this work:
# includes dev dependencies automatically
uv run pytest -xvsFull documentation at Readthedocs:
- User Guide -- how to get started with appenv
- Commands Reference -- all commands with options
- Workflows -- common usage patterns
- Locking Behavior -- how uv.lock works
- Developer Guide -- development setup and architecture