Podman Quadlet Gotchas

I have been switching from Docker to Podman and now I am taking the next step of using Quadlet such that containers start via systemd.

I used podlet as a starting point by executing podlet compose -pod to generate Quadlet files from my compose.yml. From there I reviewed the output, reviewed the systemd units from quadlet -dryrun, adjusted, tested, and repeat until content.

Below are some of the things I ran into while migrating from Compose to Quadlet.

Naming

Pod Names

Since I was using podlet to generate Quadlet files for the pod, the first thing podlet complained about was that the compose.yml did not have the name property.

podlet compose --pod

Error: 
   0: error converting compose file
   1: `name` is required when using `--pod`

The compose.yml adjustment was pretty straightforward.

Container Names

The next thing that came up was that the generated container names would sometimes be very long, taking on the form of systemd-$name. This was because I did not specify container_name for my services.

Therefore the adjustment to my compose.yml was that I needed to specify container_name for the service. This may be less of an issue if you are specifying container_name already.

Paths to directories and files

In Compose we can specify relative paths to directories and files. With Quadlet files, we need to specify the full path as though we are starting the containers via podman run.

I have had to update the resulting container units for things like EvironmentFile and Volume when doing bind mounts.

Networking

Specifying the Network

When using Compose, default networking is handled. With Quadlet, I found that I had to be a little more explicit if I wanted podlet to generate the network unit file and add the appropriate lines to the container unit files.

In compose.yml, I specified a network in the networks block and added the same block to each of the services.

Below is a snippet from my compose.yml for Paperless-ngx

name: paperless-ngx
services:
  broker:
    image: docker.io/library/redis:8
    restart: unless-stopped
    networks:
      - default
    volumes:
      - redisdata:/data

networks:
  default:

Hostnames

When Quadlet generates the systemd units and ContainerName is not specified in the container unit file, the name of that container will be systemd-$name. Where $name is the name of the unit file. As a result, the hostname for that container will be systemd-$name.

For example paperless-ngx-broker.container gives us a container named systemd-paperless-ngx-broker.

With that in mind, we need to update the connection strings for services like databases, caches, etc. accordingly.

Although the documentation mentions a HostName option, setting that results in the following error when we go to start the container

Error: invalid config provided: cannot set hostname when joining the pod UTS namespace: invalid configuration

Summary

Going from Compose to Quadlet has been nice once things work.

I will still keep my compose.yml files because being able to regenerate Quadlet files is still useful for changes such as environment variables and labels.