Introduction to Podman on Windows Server 2022

Podman is an OCI-compatible container engine developed by Red Hat that runs containers without requiring a central daemon process. Unlike Docker, which relies on a long-running dockerd daemon process running as root, Podman uses a fork-exec model where each container runs as a direct child process of the invoking user. On Linux, this enables true rootless containers. On Windows Server 2022, Podman runs Linux containers by managing a lightweight virtual machine (Podman Machine) running Fedora CoreOS, which hosts the actual container workloads.

Podman’s CLI is intentionally designed to be a drop-in replacement for Docker: every docker command has a direct podman equivalent. You can alias docker=podman in many environments and existing scripts will work without modification. This makes Podman an attractive choice for organizations that want daemonless container management, better systemd integration on Linux, or environments where the Docker daemon model is seen as a security concern.

This article covers the complete setup of Podman on Windows Server 2022, from installation through Podman Machine configuration, container management, Podman Compose, and integration with WSL2.

Installing Podman Desktop on Windows Server 2022

Podman on Windows is distributed as Podman Desktop — an installer package that includes both the Podman CLI and an optional GUI application. Download the installer from the official GitHub releases page for the containers/podman project. As of 2024-2025, stable releases are available as .exe installers for Windows x64.

Download and install Podman Desktop from PowerShell:

# Check for the latest version on GitHub releases
# Download Podman Desktop installer (example with version 1.10.0)
Invoke-WebRequest -Uri "https://github.com/containers/podman-desktop/releases/download/v1.10.0/podman-desktop-1.10.0-setup.exe" -OutFile podman-desktop-setup.exe -UseBasicParsing
Start-Process -FilePath .podman-desktop-setup.exe -ArgumentList "/S" -Wait

Alternatively, use winget if it is available on the server:

winget install RedHat.Podman
winget install RedHat.Podman-Desktop

The Podman installer places podman.exe in C:Program FilesRedHatPodman and adds it to the system PATH. Verify the installation:

podman --version
podman info

Podman Machine: Initializing and Starting the Linux VM

On Windows, Podman runs Linux containers by managing a Podman Machine — a Fedora CoreOS virtual machine that serves as the container host. The Podman CLI on Windows communicates with the Podman service running inside this VM via a named pipe and SSH tunnel. Podman Machine uses either the Windows Hypervisor Platform (WHPX) or WSL2 as the virtualization backend.

Initialize a Podman Machine with default settings:

podman machine init

This downloads a Fedora CoreOS disk image and creates a VM configuration. You can customize resources at initialization time:

podman machine init --cpus 4 --memory 4096 --disk-size 60 myserver

Parameters: --cpus sets vCPU count, --memory is in MiB, --disk-size is in GiB, and the final positional argument is the machine name (defaults to podman-machine-default).

Start the machine:

podman machine start

Check the status:

podman machine list

Expected output:

NAME                     VM TYPE     CREATED      LAST UP            CPUS        MEMORY      DISK SIZE
podman-machine-default*  wsl         2 hours ago  Currently running  4           4GiB        60GiB

SSH into the machine for direct access to the Fedora CoreOS host if needed:

podman machine ssh

Stop and remove the machine when not needed:

podman machine stop
podman machine rm

Podman vs Docker CLI Compatibility

Podman’s CLI was designed to mirror Docker’s command structure exactly. The following table shows common command equivalents — they are syntactically identical:

docker pullpodman pull
docker runpodman run
docker pspodman ps
docker imagespodman images
docker buildpodman build
docker execpodman exec
docker logspodman logs
docker stoppodman stop
docker rmpodman rm
docker rmipodman rmi

To make Podman a transparent Docker replacement in existing scripts, create a PowerShell alias:

Set-Alias -Name docker -Value podman -Scope Global
# Add to PowerShell profile for persistence:
Add-Content $PROFILE "`nSet-Alias -Name docker -Value podman -Scope Global"

One important behavioral difference: Podman does not have a background daemon. Each podman invocation is a fresh process that queries the container state from the Podman Machine. This means startup latency is slightly higher for the first command, but there is no persistent privileged process that could be targeted by container escape attacks.

Basic Container Operations with Podman

Pull an image from Docker Hub or any OCI-compatible registry:

podman pull nginx:alpine
podman pull mcr.microsoft.com/azure-cli:latest
podman pull registry.access.redhat.com/ubi9/ubi-minimal

List available images:

podman images

Run a container in detached mode with port mapping and environment variables:

podman run -d 
  --name webserver 
  -p 8080:80 
  -e NGINX_HOST=myserver.local 
  -v C:/data/html:/usr/share/nginx/html:z 
  nginx:alpine

List running containers:

podman ps
podman ps -a   # include stopped containers

Execute a command inside a running container:

podman exec -it webserver sh
podman exec webserver nginx -t   # test nginx config

View container logs:

podman logs webserver
podman logs -f webserver   # follow/tail logs

Stop and remove a container:

podman stop webserver
podman rm webserver

Inspect container metadata (networking, mounts, environment):

podman inspect webserver

Building Container Images with Podman

Podman builds OCI images using the same Dockerfile syntax as Docker. The build process runs entirely within the Podman Machine VM:

# Dockerfile example
FROM nginx:alpine
COPY ./html /usr/share/nginx/html
COPY ./nginx.conf /etc/nginx/nginx.conf
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
podman build -t myapp:1.0 -f Dockerfile .
podman build -t myapp:latest --no-cache .

Tag and push to a registry:

podman tag myapp:1.0 myregistry.azurecr.io/myapp:1.0
podman login myregistry.azurecr.io
podman push myregistry.azurecr.io/myapp:1.0

Podman Compose for Multi-Container Applications

Podman Compose is a community tool that implements Docker Compose v2 spec support for Podman. It reads docker-compose.yml (or compose.yaml) files and translates them into Podman commands, allowing you to manage multi-container applications the same way you would with Docker Compose.

Install podman-compose (requires Python):

pip install podman-compose

Or install via winget/pip inside WSL2 for better compatibility. Example compose.yaml:

version: "3.8"
services:
  web:
    image: nginx:alpine
    ports:
      - "8080:80"
    volumes:
      - ./html:/usr/share/nginx/html
    depends_on:
      - api
  api:
    image: node:20-alpine
    working_dir: /app
    volumes:
      - ./api:/app
    command: node server.js
    environment:
      - NODE_ENV=production
      - DB_HOST=db
  db:
    image: postgres:16-alpine
    environment:
      - POSTGRES_DB=myapp
      - POSTGRES_USER=appuser
      - POSTGRES_PASSWORD=securepassword
    volumes:
      - pgdata:/var/lib/postgresql/data
volumes:
  pgdata:
podman-compose up -d
podman-compose ps
podman-compose logs web
podman-compose down

Alternatively, Podman 4.0+ includes native Compose support via podman compose (without the hyphen), which delegates to either podman-compose or Docker Compose v2 if they are installed.

Podman Desktop GUI

Podman Desktop is a cross-platform GUI application for managing containers, images, volumes, and Podman Machines. It is similar in concept to Docker Desktop but is open source and works with Podman (and can also work with Docker if Docker is installed). On Windows Server 2022, Podman Desktop runs as a system tray application and provides a visual interface for:

– Starting, stopping, and deleting containers
– Pulling images and browsing the local image cache
– Viewing container logs in real time
– Managing Podman Machines (start, stop, delete, resource settings)
– Kubernetes integration (can connect to a local kind or minikube cluster)
– Extensions marketplace for additional functionality

On a headless Windows Server 2022, the GUI is less useful, but the Podman Desktop installer conveniently sets up the CLI environment including the correct PATH entries and Podman Machine configuration defaults.

Integrating Podman with WSL2

By default on Windows, Podman uses WSL2 as its virtualization backend for the Podman Machine. This means WSL2 must be enabled (see the WSL2 article) before Podman Machine will function. When using the WSL2 backend, the Podman Machine is implemented as a WSL2 distribution named podman-machine-default:

wsl --list --verbose

You will see podman-machine-default in the list alongside any other WSL2 distributions. You can SSH into it directly or via podman machine ssh. Installing the Podman CLI inside an existing Ubuntu WSL2 distribution lets you run Podman natively in Linux (rootless) while also sharing the same Podman Machine backend:

# Inside WSL2 Ubuntu
sudo apt-get update
sudo apt-get install -y podman
podman run --rm hello-world

Running Podman natively inside WSL2 is actually the recommended path for production workloads on Windows Server 2022. The Linux Podman binary has full rootless container support, systemd integration via podman generate systemd, and better performance than going through the Windows Podman proxy.

Managing Containers Without a Daemon

One of Podman’s design advantages for Windows Server workloads is the absence of a persistent daemon. On Docker, if the dockerd process crashes or is killed, all containers may be affected. With Podman, containers are managed as cgroup entries within the VM — the Podman CLI process exits after completing its command, and containers continue running independently.

This is particularly relevant for container lifecycle management in production environments. Check container health without a daemon:

podman healthcheck run mycontainer
podman stats --no-stream
podman top mycontainer

For Windows Server 2022 workloads where operational simplicity and security hardening are priorities, Podman provides a compelling Docker-compatible alternative with a more conservative privilege model.