L'ange Podman

Présentation de l'outil podman en remplaçant de docker

Depuis peu, j'ai choisi de passer de docker à podman, j'ai donc décidé d'écrire un petit article dessus.

Podman est au même titre que docker un outil pour créer et gérer des conteneurs, avec des images au format OCI.

Différences podman / docker

Avant de parler des différences, nous allons parler des points communs, podman et docker utilisent exactement la même CLI, c'est à dire que créer un alias docker pointant vers podman fonctionnera parfaitement :

  • docker run -ti alpine devient podman run -ti alpine
  • docker pull alpine devient podman pull alpine
  • etc ...

Pas de clustering

Par contre avec podman, pas de clustering, podman swarm n'existe pas.

Daemonless

Mais nous avons une différence de taille, podman est daemonless. Contrairement à docker, il n'a pas besoin d'exposer une API, nous avons donc une architecture beaucoup plus simple.
Sous docker, nous avons la commandline docker qui appelle l'API exposé par dockerd qui lui même appelle l'API exposé par containerd, qui lance containerd-shim qui lui lance runc qui lance enfin notre processus.
Sous podman, nous avons notre commandline podman qui lance conmon, qui lui lance runc pour lancer notre conteneur. Et c'est tout.

Nous avons donc beaucoup moins d'étape avec podman qu'avec docker, et donc nous réduisons la surface d'attaque.
De plus sous docker, containerd devient un SPOF, car il devient le maitre du lancement de tout les conteneurs, contrairement à podman qui lance un process conmon par conteneur.

Rootless

Même si docker le permets désormais (mais toujours avec son daemon) (cf documentation), podman est entièrement rootless Out-of-box. Cela veut dire que vous lancez vos conteneurs avec vos droits utilisateurs, pas de sudo, pas de groupe docker (qui vous donner beaucoup trop de permissions), vous lancez vos conteneurs, et ils tournerons avec vos permissions.
Dans votre conteneur, vous aurez tout de même l'utilisateur root, mais niveau host, il correspondra à votre utilisateur.
Petit exemple, mon utilisateur est xataz, il à l'UID 1000 sur ma machine Je lance donc mon conteneur comme ceci :

$ podman container run -d alpine ping 9.9.9.9
$ podman ps
CONTAINER ID  IMAGE                            COMMAND       CREATED        STATUS            PORTS  NAMES
6430b1dca84e  docker.io/library/alpine:latest  ping 9.9.9.9  6 seconds ago  Up 5 seconds ago         clever_euler

Si je fais un podman container top clever_euler, j'obtiens :

USER   PID   PPID   %CPU    ELAPSED           TTY   TIME   COMMAND
root   1     0      0.000   1m48.153058015s   ?     0s     ping 9.9.9.9

Dans le conteneur, on nous dit que c'est l'utilisateur root qui lance le ping, mais si on regarde sur l'hôte :

$ ps aux | grep 9.9.9.9
xataz     106366  106354  0 00:28 ?        00:00:00 ping 9.9.9.9

Nous avons donc l'utilisateur root du conteneur qui se retrouve mappé sur l'utilisateur qui lance le conteneur.

Cependant, le mode rootless à quelques limitations :

  • Pas de gestion de réseau, sur l'hôte seul root peut gérer ceci.
  • Un support partiel des cgroups, via les cgroups v2, mais tout n'est pas limitable.
  • Le mappage des ports limités au port supérieur à 1024.

Donc pour communiquer entre deux conteneurs, nous n'avons que 3 solutions :

  • Mappé les ports sur l'hôte et contacter directement l'IP de l'hôte (ex : podman container run -d -p 3306:3306 mariadb)
  • Utiliser le network host, pour que les ports soit directement mappé (ex : podman container run --network host mariadb), comme ceci chaque conteneur partage le localhost.
  • Utiliser les pods, nous verrons donc cette méthode ensuite.

D'ailleurs, tout les tests réalisé dans cette article l'on été en mode rootless, je n'ai fait aucun test en rootfull.

Les Pods

Le concept de POD vient de kubernetes. C'est un groupe de un ou plusieurs conteneurs qui partagerons plusieurs ressources, notamment le réseau, avec un namespace partagé, mais aussi les cgroups par exemple.

Création et gestion d'un pod

Pour gérer un pod, c'est assez simple, nous avons la commande podman pod, avec les sous-commandes create, ps, start, stop, rm etc ...
Nous restons dans la même logique que docker, les commandes restent simples et explicites.

Nous allons pour tester rapidement un pod nommé test, avec un conteneur nginx, et un conteneur qui fait un curl sur le localhost. Ce pod exposera donc le port 8080.

Nous commençons donc par créer notre pod :

$ podman pod create --name test -p 8080:80
480348ec0517b5815053755386d0bc563f5f22e17d7db35c44662680ec05d796

Puis nous lançons notre premier conteneur dans notre pod test :

$ podman container run -d --pod test nginx

A ce stade nous avons donc notre pod test, et un conteneur nginx dedans, nous pouvons vérifier avec :

$ podman ps --pod
CONTAINER ID  IMAGE                           COMMAND               CREATED             STATUS                 PORTS                 NAMES            POD           POD NAME
df295bc43cfa  docker.io/library/nginx:latest  nginx -g daemon o...  About a minute ago  Up About a minute ago  0.0.0.0:8080->80/tcp  vibrant_bardeen  480348ec0517  test

Nous pouvons donc en local sur notre hôte acceder à locahost:8080, qui nous fournira la jolie page Welcome to nginx!.

Mais si d'un autre conteneur je veux accéder à cette page, comment faire ??
Il faudra taper sur le port 80, et non le port 8080 car celui n'est monté que sur l'hôte.
Donc si je fais un podman container run -ti --rm --pod test alpine wget 127.0.0.1 -O-, nous avons bien notre page Welcome to nginx! qui s'affiche.

Ce pod n'étant qu'un test, nous pouvons le supprimer, et supprimer tout les conteneurs associés :

$ podman pod rm -f test

Nextcloud + redis + postgres

Pour un exemple un peu plus concret, nous allons créer un pod nommé cloud, avec 3 conteneurs, nextcloud, redis et postgres.
Nous utiliserons les images officiels pour ces 3 conteneurs.

Création du pod

Nous avons donc besoin de notre pod, nous savons déjà que nous aurons besoin de rediriger le port 80 du conteneur vers l'exterieur, nous utiliserons ici le port 8080.

Donc pour créer notre pod, nous lançons :

$ podman pod create --name cloud -p 8080:80
14130d03a965cad53f1b3792533d1fef5494650c8f7ae32b9f242d025b22b33e

Création du conteneur mariadb

Ceci n'étant qu'un test, je vais faire une configuration plutôt simpliste, pas de mot de passe complexe, je lance donc mon conteneur mariadb :

$ podman container run -d \
    --pod cloud \
    --name nextclouddb \
    -e POSTGRES_USER="nextcloud" \
    -e POSTGRES_PASSWORD="nextcloud" \
    postgres
b4a4ef68b1b19226e8c3f259824ad289b56eff045ab077562b92aeca8a152f74

Création du conteneur redis

Pareil pour redis, nous utilisons l'image officiel :

$ podman container run -d \
    --pod cloud \
    --name nextcloudredis \
    redis
b7eacdeb95e57128b30d9d0d2f6a46571764349ead3dbc2f1b73769fc66b2266

Création du conteneur Nextcloud

Puis la création la plus compliqué, mais pas insurmontable non plus, puisque c'est pour du test :

$ podman container run -d \
    --pod cloud \
    --name nextcloud \
    -e POSTGRES_HOST="127.0.0.1" \
    -e POSTGRES_DB="nextcloud" \
    -e POSTGRES_USER="nextcloud" \
    -e POSTGRES_PASSWORD="nextcloud" \
    -e NEXTCLOUD_ADMIN_USER="xataz" \
    -e NEXTCLOUD_ADMIN_PASSWORD="xataz" \
    -e REDIS_HOST="127.0.0.1" \
    nextcloud

Normalement, vous devriez pouvoir accéder à votre nextcloud avec l'IP de l'hôte sur le port 8080.

Analyse des conteneurs et du pod

Que pouvons nous voir de ces conteneurs ??
Déjà nous pouvons voir qu'il partage le même pod :

$ podman ps --pod
CONTAINER ID  IMAGE                               COMMAND               CREATED       STATUS           PORTS                 NAMES           POD           POD NAME
4658539082d1  docker.io/library/nextcloud:latest  apache2-foregroun...  16 hours ago  Up 16 hours ago  0.0.0.0:8080->80/tcp  nextcloud       e234d8f0f183  cloud
0844854e09aa  docker.io/library/redis:latest      redis-server          16 hours ago  Up 16 hours ago  0.0.0.0:8080->80/tcp  nextcloudredis  e234d8f0f183  cloud
3b265454c8c0  docker.io/library/postgres:latest   postgres              16 hours ago  Up 16 hours ago  0.0.0.0:8080->80/tcp  nextclouddb     e234d8f0f183  cloud

Nous pouvons également voir que les conteneurs partages des namespaces :

$ podman ps --ns
CONTAINER ID  NAMES           PID     CGROUPNS    IPC         MNT         NET         PIDNS       USERNS      UTS
4658539082d1  nextcloud       134799  4026531835  4026533078  4026533084  4026532736  4026533085  4026532734  4026533077
0844854e09aa  nextcloudredis  134529  4026531835  4026533078  4026533082  4026532736  4026533083  4026532734  4026533077
3b265454c8c0  nextclouddb     134427  4026531835  4026533078  4026533080  4026532736  4026533081  4026532734  4026533077

Ici nous constatons que les namespaces CGROUP, IPC, NET, USER et UTS sont les mêmes.

Nous constatons également que nous avons 4 conteneurs dans notre pod :

$ podman pod ps
POD ID         NAME    STATUS    CREATED        # OF CONTAINERS   INFRA ID
e234d8f0f183   cloud   Running   16 hours ago   4                 e82ce3139620

Pourquoi 4 conteneurs ? Nous n'en avons créés que 3 !!!

Tout simplement que dans un pod, nous avons un conteneur qui ne sert qu'à maintenir les namespaces partagés ouvert, car un namespace est forcément utilisé, sinon il est supprimé.
Nous pourrions utiliser une autre image, par exemple une image qui permet la gestion du pod, ou même un reverse proxy par exemple, je n'ai pas d'image en tête, mais cela reste une possibilité.

Bonus

L'intégration avec systemd

Podman intègre une fonction sympathique qui permets de générer des fichiers de configuration systemd, afin de l'utiliser en tant que service.

podman generate systemd --help
Generate a systemd unit file for a Podman container

Description:
  Command generates a systemd unit file for a Podman container
  

Usage:
  podman generate systemd [flags] CONTAINER | POD

Examples:
  podman generate systemd ctrID


Flags:
  -f, --files                   generate files instead of printing to stdout
  -n, --name                    use the container/pod name instead of ID
      --new                     create a new container instead of starting an existing one
      --restart-policy string   applicable systemd restart-policy (default "on-failure")
  -t, --timeout int             stop timeout override (default -1)

L'utilisation est plutôt simple.

La génération simple n'est pas des plus recommandé, car il ne permet que de lancer et stopper le conteneur déjà créé, il ne le créera pas :

$ podman generate systemd nextcloud
# container-4658539082d1f28bbd6c3d5fa59b525affa8cc1b7aa4247110cc5a87e049e3b4.service
# autogenerated by Podman 1.8.2
# Tue Apr 14 20:27:46 CEST 2020

[Unit]
Description=Podman container-4658539082d1f28bbd6c3d5fa59b525affa8cc1b7aa4247110cc5a87e049e3b4.service
Documentation=man:podman-generate-systemd(1)
Wants=network.target
After=network-online.target

[Service]
Environment=PODMAN_SYSTEMD_UNIT=%n
Restart=on-failure
ExecStart=/usr/bin/podman start 4658539082d1f28bbd6c3d5fa59b525affa8cc1b7aa4247110cc5a87e049e3b4
ExecStop=/usr/bin/podman stop -t 10 4658539082d1f28bbd6c3d5fa59b525affa8cc1b7aa4247110cc5a87e049e3b4
PIDFile=/run/user/1000/containers/vfs-containers/4658539082d1f28bbd6c3d5fa59b525affa8cc1b7aa4247110cc5a87e049e3b4/userdata/conmon.pid
KillMode=none
Type=forking

[Install]
WantedBy=multi-user.target default.target

Nous pouvons donc via l'option --new créer un service qui le créera proprement :

$ podman generate systemd --new nextcloud
# container-4658539082d1f28bbd6c3d5fa59b525affa8cc1b7aa4247110cc5a87e049e3b4.service
# autogenerated by Podman 1.8.2
# Tue Apr 14 20:28:02 CEST 2020

[Unit]
Description=Podman container-4658539082d1f28bbd6c3d5fa59b525affa8cc1b7aa4247110cc5a87e049e3b4.service
Documentation=man:podman-generate-systemd(1)
Wants=network.target
After=network-online.target

[Service]
Environment=PODMAN_SYSTEMD_UNIT=%n
Restart=on-failure
ExecStartPre=/usr/bin/rm -f %t/%n-pid %t/%n-cid
ExecStart=/usr/bin/podman run --conmon-pidfile %t/%n-pid --cidfile %t/%n-cid --cgroups=no-conmon -d --pod cloud --name nextcloud -e POSTGRES_HOST=127.0.0.1 -e POSTGRES_DB=nextcloud -e POSTGRES_USER=nextcloud -e POSTGRES_PASSWORD=nextcloud -e NEXTCLOUD_ADMIN_USER=xataz -e NEXTCLOUD_ADMIN_PASSWORD=xataz -e REDIS_HOST=127.0.0.1 nextcloud
ExecStop=/usr/bin/podman stop --ignore --cidfile %t/%n-cid -t 10
ExecStopPost=/usr/bin/podman rm --ignore -f --cidfile %t/%n-cid
PIDFile=%t/%n-pid
KillMode=none
Type=forking

[Install]
WantedBy=multi-user.target default.target

L'option --name est vraiment pas mal également, rends les services générés beaucoup plus clair :

$ podman generate systemd --new --name nextcloud
# container-nextcloud.service
# autogenerated by Podman 1.8.2
# Tue Apr 14 20:28:45 CEST 2020

[Unit]
Description=Podman container-nextcloud.service
Documentation=man:podman-generate-systemd(1)
Wants=network.target
After=network-online.target

[Service]
Environment=PODMAN_SYSTEMD_UNIT=%n
Restart=on-failure
ExecStartPre=/usr/bin/rm -f %t/%n-pid %t/%n-cid
ExecStart=/usr/bin/podman run --conmon-pidfile %t/%n-pid --cidfile %t/%n-cid --cgroups=no-conmon -d --pod cloud --name nextcloud -e POSTGRES_HOST=127.0.0.1 -e POSTGRES_DB=nextcloud -e POSTGRES_USER=nextcloud -e POSTGRES_PASSWORD=nextcloud -e NEXTCLOUD_ADMIN_USER=xataz -e NEXTCLOUD_ADMIN_PASSWORD=xataz -e REDIS_HOST=127.0.0.1 nextcloud
ExecStop=/usr/bin/podman stop --ignore --cidfile %t/%n-cid -t 10
ExecStopPost=/usr/bin/podman rm --ignore -f --cidfile %t/%n-cid
PIDFile=%t/%n-pid
KillMode=none
Type=forking

[Install]
WantedBy=multi-user.target default.target

Nous pouvons bien évidemment générer directement le fichier :

$ podman generate systemd --new --name --files nextcloud
/home/xataz/Documents/Projects/podman/container-nextcloud.service

Pour l'utiliser il suffit donc de le mettre dans ~/.config/systemd/user/, si le répertoire n'existe pas, il faudra le créer.
Puis le lancer avec systemctl --user start container-nextcloud.

Nous pouvons également en générer plusieurs pour un pod complet, malheureusement je trouve dommage qu'il n'est pas possible d'utiliser l'option --new avec un pod (Peut être dans une prochaine version):

$ podman generate systemd --new --name --files cloud
Error: error generating systemd unit files: cannot generate generic files for a pod
$ podman generate systemd --name --files cloud
/home/xataz/Documents/Projects/podman/pod-cloud.service
/home/xataz/Documents/Projects/podman/container-nextcloudredis.service
/home/xataz/Documents/Projects/podman/container-nextclouddb.service
/home/xataz/Documents/Projects/podman/container-nextcloud.service

Génération de fichier kubernetes

Podman permets également de générer des fichiers de configuration pour kubernetes, la commande est similaire à celle de systemd :

$ podman generate kube --help
Generate Kubernetes pod YAML from a container or pod

Description:
  Command generates Kubernetes Pod YAML (v1 specification) from a podman container or pod.

  Whether the input is for a container or pod, Podman will always generate the specification as a Pod. The input may be in the form of a pod or container name or ID.

Usage:
  podman generate kube [flags] CONTAINER | POD

Examples:
  podman generate kube ctrID
  podman generate kube podID
  podman generate kube --service podID

Flags:
  -f, --filename string   Filename to output to
  -s, --service           Generate YAML for kubernetes service object

Nous pouvons générer un fichier que pour notre conteneur (podman create --name test alpine) :

$ podman generate kube alpine
# Generation of Kubernetes YAML is still under development!
#
# Save the output of this file and use kubectl create -f to import
# it into Kubernetes.
#
# Created with podman-1.8.2
apiVersion: v1
kind: Pod
metadata:
  creationTimestamp: "2020-04-14T18:47:56Z"
  labels:
    app: alpine
  name: alpine
spec:
  containers:
  - command:
    - /bin/sh
    env:
    - name: PATH
      value: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
    - name: TERM
      value: xterm
    - name: container
      value: podman
    - name: HOSTNAME
    image: docker.io/library/alpine:latest
    name: alpine
    resources: {}
    securityContext:
      allowPrivilegeEscalation: true
      capabilities: {}
      privileged: false
      readOnlyRootFilesystem: false
      seLinuxOptions: {}
    workingDir: /
status: {}

Ou alors pour notre pod directement :

$ podman generate kube cloud
# Generation of Kubernetes YAML is still under development!
#
# Save the output of this file and use kubectl create -f to import
# it into Kubernetes.
#
# Created with podman-1.8.2
apiVersion: v1
kind: Pod
metadata:
  creationTimestamp: "2020-04-14T18:48:26Z"
  labels:
    app: cloud
  name: cloud
spec:
  containers:
  - command:
    - redis-server
    env:
    - name: PATH
      value: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
    - name: TERM
      value: xterm
    - name: container
      value: podman
    - name: GOSU_VERSION
      value: "1.11"
    - name: REDIS_VERSION
      value: 5.0.8
    - name: REDIS_DOWNLOAD_URL
      value: http://download.redis.io/releases/redis-5.0.8.tar.gz
    - name: REDIS_DOWNLOAD_SHA
      value: f3c7eac42f433326a8d981b50dba0169fdfaf46abb23fcda2f933a7552ee4ed7
    - name: HOSTNAME
      value: cloud
    image: docker.io/library/redis:latest
    name: nextcloudredis
    ports:
    - containerPort: 80
      hostPort: 8080
      protocol: TCP
    resources: {}
    securityContext:
      allowPrivilegeEscalation: true
      capabilities: {}
      privileged: false
      readOnlyRootFilesystem: false
      seLinuxOptions: {}
    workingDir: /data
  - command:
    - postgres
    env:
    - name: PATH
      value: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/lib/postgresql/12/bin
    - name: TERM
      value: xterm
    - name: LANG
      value: en_US.utf8
    - name: PG_MAJOR
      value: "12"
    - name: GOSU_VERSION
      value: "1.11"
    - name: PGDATA
      value: /var/lib/postgresql/data
    - name: POSTGRES_PASSWORD
      value: nextcloud
    - name: PG_VERSION
      value: 12.2-2.pgdg100+1
    - name: POSTGRES_USER
      value: nextcloud
    - name: container
      value: podman
    - name: HOSTNAME
      value: cloud
    image: docker.io/library/postgres:latest
    name: nextclouddb
    resources: {}
    securityContext:
      allowPrivilegeEscalation: true
      capabilities: {}
      privileged: false
      readOnlyRootFilesystem: false
      seLinuxOptions: {}
    workingDir: /
  - command:
    - apache2-foreground
    env:
    - name: PATH
      value: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
    - name: TERM
      value: xterm
    - name: APACHE_CONFDIR
      value: /etc/apache2
    - name: PHP_EXTRA_CONFIGURE_ARGS
      value: --with-apxs2 --disable-cgi
    - name: NEXTCLOUD_VERSION
      value: 18.0.3
    - name: PHP_CFLAGS
      value: -fstack-protector-strong -fpic -fpie -O2 -D_LARGEFILE_SOURCE -D_FILE_OFFSET_BITS=64
    - name: REDIS_HOST
      value: 127.0.0.1
    - name: PHP_LDFLAGS
      value: -Wl,-O1 -Wl,--hash-style=both -pie
    - name: PHP_INI_DIR
      value: /usr/local/etc/php
    - name: PHP_EXTRA_BUILD_DEPS
      value: apache2-dev
    - name: POSTGRES_HOST
      value: 127.0.0.1
    - name: NEXTCLOUD_ADMIN_USER
      value: xataz
    - name: GPG_KEYS
      value: CBAF69F173A0FEA4B537F470D66C9593118BCCB6 F38252826ACD957EF380D39F2F7956BC5DA04B5D
    - name: PHP_VERSION
      value: 7.3.16
    - name: POSTGRES_DB
      value: nextcloud
    - name: NEXTCLOUD_ADMIN_PASSWORD
      value: xataz
    - name: PHP_ASC_URL
      value: https://www.php.net/get/php-7.3.16.tar.xz.asc/from/this/mirror
    - name: PHP_MD5
    - name: POSTGRES_USER
      value: nextcloud
    - name: APACHE_ENVVARS
      value: /etc/apache2/envvars
    - name: PHP_SHA256
      value: 91aaee3dbdc71b69b4f3292f9d99211172a2fa926c3f3bbdb0e85dab03dd2bcb
    - name: container
      value: podman
    - name: PHP_CPPFLAGS
      value: -fstack-protector-strong -fpic -fpie -O2 -D_LARGEFILE_SOURCE -D_FILE_OFFSET_BITS=64
    - name: PHPIZE_DEPS
      value: "autoconf \t\tdpkg-dev \t\tfile \t\tg++ \t\tgcc \t\tlibc-dev \t\tmake
        \t\tpkg-config \t\tre2c"
    - name: POSTGRES_PASSWORD
      value: nextcloud
    - name: PHP_URL
      value: https://www.php.net/get/php-7.3.16.tar.xz/from/this/mirror
    - name: HOSTNAME
      value: cloud
    image: docker.io/library/nextcloud:latest
    name: nextcloud
    resources: {}
    securityContext:
      allowPrivilegeEscalation: true
      capabilities: {}
      privileged: false
      readOnlyRootFilesystem: false
      seLinuxOptions: {}
    workingDir: /var/www/html
status: {}

Avec un fichier c'est mieux :

$ podman generate kube --filename cloud.yaml cloud

Cependant, comme nous pouvons le voir, la génération n'est pas totalement complète et correcte, car nous avons mappé les ports sur le pod, et non sur le conteneur redis, nous avons bien l'option --service, mais celui ci monte les ports sur des ports aléatoires :

$ podman generate kube --service cloud
# Generation of Kubernetes YAML is still under development!
#
# Save the output of this file and use kubectl create -f to import
# it into Kubernetes.
#
# Created with podman-1.8.2
[...]
---
apiVersion: v1
kind: Service
metadata:
  creationTimestamp: "2020-04-14T18:54:47Z"
  labels:
    app: cloud
  name: cloud
spec:
  ports:
  - name: "80"
    nodePort: 30004
    port: 80
    protocol: TCP
    targetPort: 0
  selector:
    app: cloud
  type: NodePort
status:
  loadBalancer: {}

J'espère sincèrement que tout ceci sera amélioré dans de futures versions.

podman-compose

Comme précedemment dit, il existe un podman-compose. Je ne vais pas expliquer ici l'installation de l'outil, ou même son fonctionnement, car il est 100% compatible avec docker-compose.

Podman-compose n'est différent que dans la gestion des conteneurs, il part du principe que chaque fichier yaml est un pod, et donc va créer un pod et y mettre les conteneurs dedans. Pour un soucis de transparence avec docker, il va cependant ajouter les noms des conteneurs dans le fichier /etc/hosts afin de pouvoir simuler un réseau docker (en rootless évidemment).

Cependant j'ai remarqué un petit défaut, par exemple j'avais l'habitude avec docker-compose de simplement lancer un docker-compose up -d pour mettre à jour les modifications apporté, il gérait donc automatiquement les conteneurs à mettre à jour ou non. Avec podman-compose, cela ne fonctionne malheureusement pas, il faut d'abord supprimer le pod, puis le relancer.

TroubleShooting

J'ai pu observer quelques bugs :

  • Problème de purge des répertoires, j'avais beau avoir supprimer mes images et conteneurs, ainsi que volumes, mon répertoire home était toujours pleins, et pleins de layers liés à podman. Je n'ai pas observé ce problème sous Manjaro ou CentOS 8.
  • Des problèmes aléatoires sur le mappage de port, enfin plutôt des fonctionnements aléatoires. J'ai créer un pod en mappant des ports, au premier lancement les ports se sont correctement mappés, mais il m'a fallu environ 50 lancements pour qu'ils remappent correctement. Pareil, que sur debian et apparemment ubuntu, je n'ai pas vu le soucis sur Manjaro et CentOS.
  • Un soucis également avec le localhost dans un pod, qui ne pointe pas sur 127.0.0.1, donc j'ai pris l'habitude d'utiliser 127.0.0.1.

Problème avec le rootless

Il faudra peut être que vous autorisiez les utilisateurs à créer des namespacesv pour ceci il suffit de modifier le fichier en root /proc/sys/kernel/unprivileged_userns_clone en y écrivant un 1 dedans :

echo 1 > /proc/sys/kernel/unprivileged_userns_clone

Ceci ne sera modifier que jusqu'au reboot de la machine.

Pour le modifier définitivement, soit vous modifiez le fichier /etc/sysctl.conf en y ajoutant kernel.unprivileged_userns_clone = 1, toujours en root

Conclusion

Podman est vraiment un très bon outil, je l'ai testé que en mode rootless, ceci manque cruellement de maturité pour un usage en production.
Pour le l'usage personnel, c'est vraiment top, je l'utilise sur mon PC portable depuis quelques temps, j'ai remplacé mes docker par podman, même si je pense de plus en plus à passer sur du k3s pour clusterer le tout.
Podman a vraiment un énorme potentiel, déjà il rend le rootless facilement accessible, puis en plus il est daemonless, ce qui en fait l'outils parfait pour le développement.

Je l'ai déjà dis, j'ai tout testé en mode rootless, peux être que certains beug rencontrer ne le sont pas en rootfull.