Toolbox: Fournir des cales pour les binaires bien connus, qui ne peuvent s'exécuter que sur l'hôte, à l'intérieur des conteneurs de la boîte à outils

Créé le 30 avr. 2019  ·  7Commentaires  ·  Source: containers/toolbox

Diverses commandes comme flatpak , podman , rpm-ostree etc. ne peuvent pas vraiment être utilisées dans un conteneur OCI. Certains d'entre eux, comme podman , peuvent avoir une utilisation limitée, mais, dans l'ensemble, les gens s'attendent à les exécuter directement sur l'hôte.

Dans le même temps, nous nous attendons à ce qu'un bon pourcentage d'utilisateurs de l'interface de ligne de commande passent la plupart de leur temps dans un conteneur de boîte à outils, et l'un des objectifs du projet Toolbox est de réduire la charge cognitive de l'utilisation de conteneurs mutables sur des fichiers verrouillés. des systèmes d'exploitation hôtes en panne et immuables comme Silverblue. Des commandes comme flatpak et rpm-ostree sont des outils importants pour l'interfaçage avec de tels systèmes d'exploitation.

Par conséquent, ce serait bien si nous pouvions fournir une expérience utilisateur meilleure que d'avoir à basculer entre un hôte et un shell de boîte à outils, ou d'avoir à préfixer chaque commande avec des choses comme flatpak-spawn --host .

L'option la plus simple consiste à installer des alias dans le shell exécuté à l'intérieur du conteneur. Cependant, cela ne nous donne pas des choses comme les manuels et la complétion du shell.

Une autre option consiste à pré-installer les flatpak , podman , rpm-ostree , etc. RPM dans les images de base fedora-toolbox mais supprimer tout le code, laissant derrière seulement les manuels et l'achèvement du shell. Ensuite, la commande toolbox peut placer les cales correspondantes via des montages de liaison pour transférer les appels à l'hôte lors du démarrage des conteneurs de la boîte à outils.

Cela garantira que les images fedora-toolbox ne grossissent pas avec les binaires Go inutiles, et les wrappers peuvent être mis à jour via le package toolbox sur l'hôte. L'un des avantages d'avoir des shims explicites sur les alias est que nous pouvons intercepter les cas extrêmes où les invocations de commandes ne peuvent pas être transmises à l'hôte. par exemple, ils peuvent impliquer un chemin qui n'est pas partagé entre l'hôte et le conteneur. Échouer avec un message d'erreur clair vaut mieux qu'un échec obscur ou des effets secondaires étranges.

Cependant, je ne sais pas ce qui se passera si l'un de ces packages est mis à jour à l'intérieur des conteneurs. Interféreraient-ils avec les cales montées sur la liaison ? Ce serait bien si nous pouvions supprimer les bits inutiles de ces packages pendant ou après la mise à jour du RPM.

1. Feature request 2. Container Realm 5. Help Wanted Project Pickle 🥒

Commentaire le plus utile

Je construis une boîte FROM registry.fedoraproject.org/f31/fedora-toolbox:31 outils dérivée host-runner dans /usr/local/bin/host-runner

$ cat /usr/local/bin/host-runner 
#!/bin/bash 
executable=$(basename $0)
set -x
exec flatpak-spawn --host $executable "$@"

Je crée ensuite un lien symbolique vers host-runner pour tout ce que je veux exécuter dans le contexte hôte :

$ ls -l /usr/local/bin/
total 4
lrwxrwxrwx. 1 root root 13 Jan 28 14:16 chromium-browser -> ./host-runner
-rwxr-xr-x. 1 root root 89 Jan 31 10:39 host-runner
lrwxrwxrwx. 1 root root 13 Jan 29 10:51 podman -> ./host-runner
lrwxrwxrwx. 1 root root 13 Jan 28 12:39 systemctl -> ./host-runner
lrwxrwxrwx. 1 root root 13 Jan 28 12:39 virsh -> ./host-runner
lrwxrwxrwx. 1 root root 13 Jan 28 12:39 virt-install -> ./host-runner

REMARQUE : la liste des commandes qu'un utilisateur souhaite transmettre par proxy à l'hôte est probablement différente pour chaque utilisateur, nous devrions donc probablement simplement créer un moyen générique de la configurer, puis laisser les utilisateurs le faire eux-mêmes.

Vous exécutez ensuite les choses à partir de la boîte à outils, mais elles sont transmises par proxy à l'hôte. Le seul élément supplémentaire est que la commande réelle qui est exécutée est imprimée sur stderr avant d'être exécutée. Par exemple:

$ virsh list --all
+ exec flatpak-spawn --host virsh list --all
 Id   Name              State
----------------------------------
 43   f31_vanilla-f31   running
 47   tester            running
 -    fcos              shut off

Nous pourrions fournir quelque chose comme ceci dans le conteneur de boîte à outils créé. Je peaufine encore un peu ça. Une chose qui ne fonctionne pas encore et à laquelle nous devrions réfléchir est ce qu'il faut faire si l'utilisateur souhaite exécuter la commande sur l'hôte en tant que sudo.

Tous les 7 commentaires

Je pense que ce sera considérablement plus simple si nous ajoutons /usr/libexec/toolbox/bin et modifions les scripts de démarrage du shell pour les injecter d'abord dans $PATH .

L'exécution de podman dans la boîte à outils peut être extrêmement utile. Je travaille avec de nombreux projets où les scripts de construction appellent simplement des images docker, et pouvoir exécuter ces scripts dans la boîte à outils peut être très utile. Cela pourrait créer des problèmes difficiles à détecter avec les montages de liaison en dehors du répertoire de base qui refléteraient l'hôte silverblue et non la boîte à outils.

Je vais ajouter docker-compose à la liste des choses utiles pour les flux de développement. Il a une très faible barrière à l'entrée pour tout ce qui a besoin d'un magasin de données ou deux, donc un bon nombre de choses de type application Web l'utilisent - open source et non.

Je construis une boîte FROM registry.fedoraproject.org/f31/fedora-toolbox:31 outils dérivée host-runner dans /usr/local/bin/host-runner

$ cat /usr/local/bin/host-runner 
#!/bin/bash 
executable=$(basename $0)
set -x
exec flatpak-spawn --host $executable "$@"

Je crée ensuite un lien symbolique vers host-runner pour tout ce que je veux exécuter dans le contexte hôte :

$ ls -l /usr/local/bin/
total 4
lrwxrwxrwx. 1 root root 13 Jan 28 14:16 chromium-browser -> ./host-runner
-rwxr-xr-x. 1 root root 89 Jan 31 10:39 host-runner
lrwxrwxrwx. 1 root root 13 Jan 29 10:51 podman -> ./host-runner
lrwxrwxrwx. 1 root root 13 Jan 28 12:39 systemctl -> ./host-runner
lrwxrwxrwx. 1 root root 13 Jan 28 12:39 virsh -> ./host-runner
lrwxrwxrwx. 1 root root 13 Jan 28 12:39 virt-install -> ./host-runner

REMARQUE : la liste des commandes qu'un utilisateur souhaite transmettre par proxy à l'hôte est probablement différente pour chaque utilisateur, nous devrions donc probablement simplement créer un moyen générique de la configurer, puis laisser les utilisateurs le faire eux-mêmes.

Vous exécutez ensuite les choses à partir de la boîte à outils, mais elles sont transmises par proxy à l'hôte. Le seul élément supplémentaire est que la commande réelle qui est exécutée est imprimée sur stderr avant d'être exécutée. Par exemple:

$ virsh list --all
+ exec flatpak-spawn --host virsh list --all
 Id   Name              State
----------------------------------
 43   f31_vanilla-f31   running
 47   tester            running
 -    fcos              shut off

Nous pourrions fournir quelque chose comme ceci dans le conteneur de boîte à outils créé. Je peaufine encore un peu ça. Une chose qui ne fonctionne pas encore et à laquelle nous devrions réfléchir est ce qu'il faut faire si l'utilisateur souhaite exécuter la commande sur l'hôte en tant que sudo.

J'ai essayé de dupliquer cela, mais j'ai juste placé host-runner dans ~/.local/bin plutôt que de créer une nouvelle image .. et à cause d'être paresseux comme ça, j'ai eu

[user<strong i="8">@toolbox</strong> ~] podman ps
+ exec flatpak-spawn --host podman ps
+ exec flatpak-spawn --host podman ps
/var/home/user/.local/bin/podman: line 4: exec: flatpak-spawn: not found

Bien sûr, puisque ~/.local/bin est dans le PATH sur l'hôte et le conteneur, host-runner a exécuté le lien symbolique podman dans ~/.local/bin .. qui a exécuté host-runner sur l'hôte, mais flatpak-spawn était n'y est pas installé. Je n'ose pas penser à ce que la récursivité imbriquée se serait produite si c'était :wink:

Quoi qu'il en soit, je l'ai résolu en changeant

executable=$(basename $0) à executable=/usr/bin/$(basename $0) qui fonctionne assez bien pour le moment.

EDIT : Cela pose quelques autres problèmes. Par exemple, toolbox sur l'hôte ne fonctionnera plus car il essaie d'appeler ~/.local/bin/podman . Ma solution pour l'instant est d'avoir un chemin de bac séparé que je n'ajoute qu'à PATH dans mon conteneur de boîte à outils.

Utiliser flatpak-spawn --host est une astuce sympa ! Voici une version pure sh* de ceci qui fonctionne dans ~/.local/bin et évite la boucle infinie si vous exécutez accidentellement la commande directement :

#!/bin/sh
set -o errexit
set -o nounset

executable="$(basename "$0")"

if [ "$(basename "$(realpath "$0")")" = "${executable}" ]; then
  echo "can't run ${executable} via ${executable}" >&2
  exit 1
fi

# This seems like the best way to detect if we're inside a toolbox container.
if [ -n "${TOOLBOX_PATH:-}" ]; then
  set -x
  exec flatpak-spawn --host "${executable}" "$@"
fi

# Otherwise do a little dance to find the executable that would have run if not
# for $0 being on the path, and run that instead.
executable="$(
  # Remove this script's directory from PATH; this assumes that you'll never want
  # to run a sibling via this script.
  dir="$(dirname "$0")"
  PATH="$(echo "${PATH}" | sed "s+:${dir}:++")"
  PATH="$(echo "${PATH}" | sed "s+${dir}:++")"
  PATH="$(echo "${PATH}" | sed "s+:${dir}++")"
  command -v "${executable}"
)"

exec "${executable}" "$@"

(Cela n'a pas été testé dans des cas d'exécution imbriqués étranges, bien que je pense que cela devrait fonctionner.)

*suppose que realpath est disponible

Une autre option pourrait être de faire en sorte que podman dans le conteneur utilise toujours --remote . Le socket du serveur d'API semble être visible dans un conteneur de boîte à outils.

Cette page vous a été utile?
0 / 5 - 0 notes