podcell
A simple Podman-based development environment manager.
podcell is a personal utility I've primarily written for myself to quickly create, manage, and enter isolated development containers using Podman. It aims to provide a minimal and straightforward command-line interface for managing development environments.
This tool is intentionally simple and designed for personal workflows on the atomic Linux distribution I'm using.
Features
- Create new containers for development, with arbitrary repeatable bind mounts
- Edit an existing container's mounts and published ports
- Start and stop containers as a discrete lifecycle step
- Enter a running container from multiple terminals at once
- Send files and directories into a running container via
/inbox - List all available containers
- Remove containers when no longer needed
Usage
# Create the container (runs initialization, then exits to state Exited).
# Start it.
# Open a shell. Run from multiple terminals concurrently.
# Send a file or directory into the container (must be running).
# Stop it (terminates all open shells).
# Remove it (must be stopped first).
To change a container's bind mounts or published ports, you can edit it:
# Make sure the container is stopped first.
# Add a port and a mount.
# Drop a port and a mount (by host path).
podcell edit takes the same --mount / port syntax as podcell create, applies the changes
in order, and recreates the container so they take effect. Duplicate or missing ports/mounts
are rejected. The container must be stopped before editing.
The --mount flag takes HOST:CONTAINER[:MODE] where MODE is ro or rw (default ro).
The CONTAINER path must be absolute.
The HOST path may be relative: it is resolved against the current directory of the
podcell create invocation and recorded in the container configuration as an absolute path, so
podcell start works from any directory.
podcell send copies a file or directory into /inbox inside the container. The folder is created
on first use with mode 0777 and its contents belong to the container's primary user, so items can
be read, edited, moved and deleted from inside.
Mount path requirements
- The host path must be owned by the user running
podcell. Mounts owned by root or another user are rejected at create and start time. This is required for the rootless userns mapping to work correctly and to keep SELinux relabel side effects confined to user-owned data. - Avoid mounting paths whose SELinux labels matter to the host. Bind mounts are passed
to podman with the
:zflag, which recursively relabels the host path tree to a shared container label. This is fine for project directories, scratch space, etc.; it will break consumers of paths with load-bearing labels such as~/.ssh,~/.config/dconf,~/.local/share/keyrings, and similar. Don't pass those as--mount. - Relative host paths are frozen at create time. A relative
HOSTis canonicalized duringpodcell create, so moving the container does not retarget the mount: if you want a different source path, remove and recreate the container.
Build Instructions
Prerequisites
Install the musl C library development tools:
# Ubuntu/Debian
# Fedora
Building
-
Add the musl target to your Rust toolchain:
-
Build the project with static linking:
Verification
Verify the binary is statically linked:
The output should show "not a dynamic executable" or similar, confirming static linking.
Why Static Linking?
The podcell binary must be statically linked because it executes itself inside containers where dynamic dependencies may not be available. Static linking ensures the binary runs in any Linux environment without external dependencies.