web-dev-qa-db-fra.com

Comment déterminer si un processus s'exécute dans lxc / Docker?

Existe-t-il un moyen de déterminer si un processus (script) s'exécute dans un conteneur lxc (~ runtime Docker)? Je sais que certains programmes sont capables de détecter s’ils s’exécutent dans une machine virtuelle. Existe-t-il quelque chose de similaire pour lxc/docker?

142
Mate Varga

Le moyen le plus fiable est de vérifier /proc/1/cgroup. Il vous indiquera les groupes de contrôle du processus init, et quand vous serez pas dans un conteneur, ce sera / pour toutes les hiérarchies. Lorsque vous êtes à l'intérieur un conteneur, vous verrez le nom du point d'ancrage. Avec les conteneurs LXC/Docker, ce sera quelque chose comme /lxc/<containerid> ou /docker/<containerid> respectivement.

144
jpetazzo

Docker crée un .dockerenv fichier à la racine de l'arborescence de répertoires à l'intérieur du conteneur. Vous pouvez exécuter ce script pour vérifier

#!/bin/bash
if [ -f /.dockerenv ]; then
    echo "I'm inside matrix ;(";
else
    echo "I'm living in real world!";
fi


MORE: Ubuntu a en réalité un script bash: /bin/running-in-container et il peut effectivement renvoyer le type de conteneur dans lequel il a été appelé. Peut-être utile. Je ne sais pas sur les autres principales distributions cependant.

139
at0S

Sur un nouveau système Ubuntu 16.04, un nouveau système et lxc 2.0

Sudo grep -qa container=lxc /proc/1/environ
17
larss

Une manière concise de vérifier le menu fixe dans un script bash est la suivante:

#!/bin/bash
if grep docker /proc/1/cgroup -qa; then
   echo I'm running on docker.
fi
13
oNaiPs

Handy Python pour vérifier si vous utilisez Docker:

def in_docker():
    """ Returns: True if running in a Docker container, else False """
    with open('/proc/1/cgroup', 'rt') as ifh:
        return 'docker' in ifh.read()
12
JJC

Nous utilisons le sched du proc (/ proc/$ PID/sched) pour extraire le PID du processus. Le PID du processus à l'intérieur du conteneur sera différent, puis il sera le même sur l'hôte (système non conteneur).

Par exemple, la sortie de/proc/1/sched sur un conteneur retournera:

root@33044d65037c:~# cat /proc/1/sched | head -n 1
bash (5276, #threads: 1)

En tant qu'hôte non conteneur:

$ cat /proc/1/sched  | head -n 1
init (1, #threads: 1)

Cela aide à différencier si vous êtes dans un conteneur ou non.

9
Founder

Le moyen le plus simple serait de vérifier l'environnement. Si vous avez le container=lxc variable, vous êtes dans un conteneur.

Sinon, si vous êtes root, vous pouvez essayer d'effectuer l'opération mknod ou mount. Si elle échoue, vous vous trouvez probablement dans un conteneur dont les fonctionnalités ont été abandonnées.

6
creack

Vérifiez toutes les solutions ci-dessus en Python:

import os
import subprocess

def in_container():
    # type: () -> bool
    """ Determines if we're running in an lxc/docker container. """
    out = subprocess.check_output('cat /proc/1/sched', Shell=True)
    out = out.decode('utf-8').lower()
    checks = [
        'docker' in out,
        '/lxc/' in out,
        out.split()[0] not in ('systemd', 'init',),
        os.path.exists('/.dockerenv'),
        os.path.exists('/.dockerinit'),
        os.getenv('container', None) is not None
    ]
    return any(checks)
5
blakev

Ma réponse ne s'applique qu'aux processus de Node.js , mais peut être utile pour certains visiteurs qui tombent sur cette question à la recherche d'une réponse spécifique à Node.js.

J'ai eu le même problème et en s'appuyant sur /proc/self/cgroup J'ai créé un package npm uniquement dans le but de détecter si un processus Node.js s'exécute ou non dans un conteneur Docker.

Le module npm conteneurisé vous aidera dans Node.js. Il n’a pas encore été testé sur Io.js mais pourrait tout aussi bien fonctionner là-bas.

3
Martin Tajur

Docker évolue de jour en jour, nous ne pouvons donc pas dire avec certitude s'ils vont conserver .dockerenv .dockerinit Dans le futur.

Dans la plupart des versions de Linux, init est le premier processus à démarrer. Mais dans le cas des conteneurs, ce n'est pas vrai.

#!/bin/bash
if ps -p1|grep -q init;then  
  echo "non-docker" 
else 
  echo "docker" 
fi
2
Govind Kailas

S'appuyant sur la réponse acceptée qui teste /proc/*/cgroup ..

awk -F: '$3 ~ /^\/$/ {c=1} END{ exit c }' /proc/self/cgroup

Donc, pour une utilisation dans un script, un test pourrait être construit de cette façon.

is_running_in_container() {
  awk -F: '$3 ~ /^\/$/{ c=1 } END { exit c }' /proc/self/cgroup
}

if is_running_in_container; then
  echo "Aye!! I'm in a container"
else 
  echo "Nay!! I'm not in a container"
fi
1
shalomb

J'ai traduit la réponse de JJC en Ruby

def in_docker
  File.open('/proc/1/cgroup', 'rt') do |f|
    contents = f.read
    return contents =~ /docker/i || contents =~ /kubepod/i
  end
rescue StandardError => e
  p 'Local development'
  p e
  false
end
0
Souradeep Nanda

This SO Questions-réponses: "Détermine si le système d'exploitation fonctionne dans un environnement virtuel" ; bien que différent de la question du PO, il répond effectivement aux cas courants de trouver dans quel conteneur vous vous trouvez (le cas échéant).

En particulier, installez et lisez le code de ce script bash qui semble plutôt bien fonctionner:

virt-what :

Sudo apt install virt-what
0
kaiwan