Comment exécuter 'apt-get' dans un fichier dockerfile derrière un proxy?
j'exécute une machine virtuelle (Ubuntu 13.10) avec docker (version 0.8.1, construire a1598d1). J'essaie de construire une image avec un fichier dockerfile. Tout d'abord, je veux mettre à jour les paquets (en utilisant le code ci - dessous-le proxy est masqué) mais apt-get
est multiplié par l'erreur: Could not resolve 'archive.ubuntu.com'
.
FROM ubuntu:13.10
ENV HTTP_PROXY <HTTP_PROXY>
ENV HTTPS_PROXY <HTTPS_PROXY>
RUN export http_proxy=$HTTP_PROXY
RUN export https_proxy=$HTTPS_PROXY
RUN apt-get update && apt-get upgrade
j'ai aussi exécuté ce qui suit dans le système hôte:
sudo HTTP_PROXY=http://<PROXY_DETAILS>/ docker -d &
l'hôte peut exécuter apt-get
sans problème.
Comment puis-je changer le dockerfile pour permettre d'atteindre la ubuntu serveurs de l'intérieur du conteneur?
mise à Jour
j'ai lancé le code dans CentOS (en changeant le FROM ubuntu:13.10
en FROM centos
) et ça a bien marché. Il semble être un problème avec Ubuntu.
12 réponses
mise à JOUR :
vous avez une mauvaise capitalisation des variables d'environnement dans ENV. La bonne est http_proxy
. Votre exemple devrait être:
FROM ubuntu:13.10
ENV http_proxy <HTTP_PROXY>
ENV https_proxy <HTTPS_PROXY>
RUN apt-get update && apt-get upgrade
ou
FROM centos
ENV http_proxy <HTTP_PROXY>
ENV https_proxy <HTTPS_PROXY>
RUN yum update
toutes les variables spécifiées dans ENV sont prépendées à chaque commande RUN. Chaque commande RUN est exécutée dans son propre conteneur / environnement, de sorte qu'elle n'hérite pas des variables des commandes RUN précédentes!
Note: il n'est pas nécessaire d'appeler le démon docker avec un proxy pour que cela fonctionne, bien que si vous voulez tirer des images etc. vous devez définir le mandataire pour docker deamon aussi. Vous pouvez définir proxy pour daemon dans /etc/default/docker
dans Ubuntu (cela n'affecte pas la configuration des conteneurs).
cela peut aussi se produire dans le cas où vous exécutez votre mandataire sur l'hôte (i.e. localhost, 127.0.0.1). Localhost sur l'hôte diffèrent de localhost en conteneur. Dans de tels cas, vous devez utiliser une autre IP (comme 172.17.42.1) pour lier votre mandataire à ou si vous liez à 0.0.0.0, vous pouvez utiliser 172.17.42.1 au lieu de 127.0.0.1 pour la connexion à partir du conteneur pendant docker build
.
vous pouvez aussi chercher un exemple ici: comment reconstruire dockerfile rapidement en utilisant cache?
mis à jour le 02/10/2018
avec la nouvelle fonctionnalité dans l'option docker --config
, vous n'avez plus besoin de définir Proxy dans Dockerfile.
--config string Location of client config files (default "~/.docker/config.json")
ou variable d'environnement DOCKER_CONFIG
`DOCKER_CONFIG` The location of your client configuration files.
$ export DOCKER_CONFIG=~/.docker/config.json
https://docs.docker.com/engine/reference/commandline/cli / https://docs.docker.com/network/proxy /
je recommande de définir proxy avec httpProxy, httpsProxy and ftpProxy
.
{
"proxies":
{
"default":
{
"httpProxy": "http://127.0.0.1:3001",
"httpsProxy": "http://127.0.0.1:3001",
"ftpProxy": "http://127.0.0.1:3001",
"noProxy": "*.test.example.com,.example2.com"
}
}
}
ajuster L'adresse IP et le port de proxy si nécessaire et sauvegarder sur ~/.docker/config.json
après que vous avez mis correctement avec elle, vous pouvez exécuter docker build et docker run comme normal.
$ docker build -t demo .
$ docker run -ti --rm demo env|grep -ri proxy
(standard input):http_proxy=http://127.0.0.1:3001
(standard input):HTTPS_PROXY=http://127.0.0.1:3001
(standard input):https_proxy=http://127.0.0.1:3001
(standard input):NO_PROXY=*.test.example.com,.example2.com
(standard input):no_proxy=*.test.example.com,.example2.com
(standard input):FTP_PROXY=http://127.0.0.1:3001
(standard input):ftp_proxy=http://127.0.0.1:3001
(standard input):HTTP_PROXY=http://127.0.0.1:3001
ancienne réponse
ci-dessous le réglage dans Dockerfile fonctionne pour moi. J'ai testé dans CoreOS
, Vagrant
et boot2docker
. Supposons que le port de procuration est 3128
En Centos:
ENV http_proxy=ip:3128
ENV https_proxy=ip:3128
Dans Ubuntu:
ENV http_proxy 'http://ip:3128'
ENV https_proxy 'http://ip:3128'
attention au format, certains y ont du http, d'autres pas, certains avec un seul quota. si l'adresse IP est 192.168.0.193, alors le paramètre sera:
Dans Centos:
ENV http_proxy=192.168.0.193:3128
ENV https_proxy=192.168.0.193:3128
Dans Ubuntu:
ENV http_proxy 'http://192.168.0.193:3128'
ENV https_proxy 'http://192.168.0.193:3128'
si vous avez besoin de définir proxy dans coreos, par exemple pour tirer l'image
cat /etc/systemd/system/docker.service.d/http-proxy.conf
[Service]
Environment="HTTP_PROXY=http://192.168.0.193:3128"
vous pouvez utiliser l'option --build-arg
lorsque vous voulez construire en utilisant un fichier Dockerfile.
à Partir d'un lien sur https://github.com/docker/docker/issues/14634 , voir la section "Construire avec --build-arg avec plusieurs HTTP_PROXY":
[root@pppdc9prda2y java]# docker build
--build-arg https_proxy=$HTTP_PROXY --build-arg http_proxy=$HTTP_PROXY
--build-arg HTTP_PROXY=$HTTP_PROXY --build-arg HTTPS_PROXY=$HTTP_PROXY
--build-arg NO_PROXY=$NO_PROXY --build-arg no_proxy=$NO_PROXY -t java .
NOTE: Sur votre propre système, assurez-vous d'avoir défini les variables D'environnement HTTP_PROXY et NO_PROXY.
avant toute commande apt-get dans votre Dockerfile vous devez mettre cette ligne
COPY apt.conf /etc/apt/apt.conf
N'oubliez pas de créer apt.conf dans le même dossier que vous avez le Dockerfile , le contenu du apt.conf fichier devrait être comme ceci:
Acquire::socks::proxy "socks://YOUR-PROXY-IP:PORT/";
Acquire::http::proxy "http://YOUR-PROXY-IP:PORT/";
Acquire::https::proxy "http://YOUR-PROXY-IP:PORT/";
si vous utilisez nom d'utilisateur et mot de passe pour vous connecter à votre proxy, alors l'apt.conf devrait être comme ci-dessous:
Acquire::socks::proxy "socks://USERNAME:PASSWORD@YOUR-PROXY-IP:PORT/";
Acquire::http::proxy "http://USERNAME:PASSWORD@YOUR-PROXY-IP:PORT/";
Acquire::https::proxy "http://USERNAME:PASSWORD@YOUR-PROXY-IP:PORT/";
par exemple:
Acquire::https::proxy "http://foo:bar@127.0.0.1:8080/";
où foo est le nom d'utilisateur et barre est le mot de passe.
Utilisation --build-arg en minuscules variable d'environnement:
docker build --build-arg http_proxy=http://proxy:port/ --build-arg https_proxy=http://proxy:port/ --build-arg ftp_proxy=http://proxy:port --build-arg no_proxy=localhost,127.0.0.1,company.com -q=false .
j'ai eu le même problème et trouvé une autre solution de contournement: j'ai un script de provision qui est ajouté de l'environnement de construction docker. Dans le script, j'ai défini la variable d'environnement dépendante d'une vérification de ping:
Dockerfile:
ADD script.sh /tmp/script.sh
RUN /tmp/script.sh
script.sh:
if ping -c 1 ix.de ; then
echo "direct internet doing nothing"
else
echo "proxy environment detected setting proxy"
export http_proxy=<proxy address>
fi
c'est encore un peu grossier mais a travaillé pour moi
si vous avez les mandataires correctement configurés et que vous ne pouvez toujours pas accéder à internet, cela pourrait être la résolution DNS. Cochez la case /etc/resolve.conf
sur l'hôte de machine virtuelle Ubuntu. S'il contient nameserver 127.0.1.1
, c'est faux.
exécutez ces commandes sur L'hôte Ubuntu VM pour le corriger:
sudo vi /etc/NetworkManager/NetworkManager.conf
# Comment out the line `dns=dnsmasq` with a `#`
# restart the network manager service
sudo systemctl restart network-manager
cat /etc/resolv.conf
maintenant /etc/resolv.conf
devrait avoir une valeur valide pour le serveur de noms, qui sera copié par les conteneurs docker.
comme le suggèrent d'autres réponses, --build-arg
pourrait être la solution.
Dans mon cas, j'ai dû ajouter --network=host
en plus des options --build-arg
.
docker build -t <TARGET> --build-arg http_proxy=http://<IP:PORT> --build-arg https_proxy=http://<IP:PORT> --network=host .
nous faisons ...
ENV http_proxy http://9.9.9.9:9999
ENV https_proxy http://9.9.9.9:9999
et à la fin de dockerfile ...
ENV http_proxy ""
ENV https_proxy ""
ceci, pour l'instant (jusqu'à ce que docker introduise build env vars), permet d'utiliser les env vars proxy uniquement pour la construction sans les exposer
l'alternative à la solution n'est pas de construire vos images localement derrière un proxy mais de laisser docker construire vos images pour vous en utilisant docker"automated builds". Comme docker ne construit pas le images derrière votre proxy le problème est résolu. Un exemple de construction automatisée est disponible à l'adresse suivante:...
https://github.com/danday74/docker-nginx-lua (GitHub repo)
https://registry.hub.docker.com/u/danday74/nginx-lua (Docker repo qui regarde le GitHub repo en utilisant une construction automatisée et en faisant une construction docker sur une poussée à la branche principale de github)
et si vous voulez définir proxy pour wget vous devez mettre ces lignes dans votre Dockerfile
ENV http_proxy YOUR-PROXY-IP:PORT/
ENV https_proxy YOUR-PROXY-IP:PORT/
ENV all_proxy YOUR-PROXY-IP:PORT/
comme L'a fait remarquer Tim Potter, la mise en place de proxy dans dockerfile est horrible. Lors de la construction de l'image, vous ajoutez un proxy pour votre réseau d'entreprise, mais vous pouvez vous déployer dans le cloud ou une DMZ où il n'y a pas besoin de proxy ou le serveur proxy est différent.
en outre, vous ne pouvez pas partager votre image avec d'autres en dehors de votre entreprise n/W.
une légère alternative à la réponse fournie par @Reza Farshi (qui fonctionne mieux dans mon cas) est d'écrire les paramètres de proxy sur /etc/apt/apt.conf
en utilisant echo
via le fichier Dockerfile par exemple:
FROM ubuntu:16.04
RUN echo "Acquire::http::proxy \"$HTTP_PROXY\";\nAcquire::https::proxy \"$HTTPS_PROXY\";" > /etc/apt/apt.conf
# Test that we can now retrieve packages via 'apt-get'
RUN apt-get update
l'avantage de cette approche est que les adresses proxy peuvent être passées dynamiquement au moment de la compilation de l'image, plutôt que d'avoir à copier le fichier de paramètres depuis l'hôte.
p.ex.
docker build --build-arg HTTP_PROXY=http://<host>:<port> --build-arg HTTPS_PROXY=http://<host>:<port> .
que par docker construire docs.