你如何在代理后面的dockerfile中运行apt-get?

我运行一个虚拟机(Ubuntu 13.10)与docker(版本0.8.1,生成a1598d1)。 我正在试图build立一个docker文件的形象。 首先,我想更新软件包(使用下面的代码 – 代理被混淆),但apt-get超时错误: 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 

我也在主机系统中运行以下内容:

 sudo HTTP_PROXY=http://<PROXY_DETAILS>/ docker -d & 

主机能够正常运行apt-get

如何更改dockerfile以允许它从容器内到达ubuntu服务器?

更新

我在CentOS中运行代码(将FROM ubuntu:13.10更改为FROM centos ),它工作正常。 这似乎是Ubuntu的一个问题。

更新

ENV中的环境variables的大小写错误。 正确的是http_proxy 。 你的例子应该是:

 FROM ubuntu:13.10 ENV http_proxy <HTTP_PROXY> ENV https_proxy <HTTPS_PROXY> RUN apt-get update && apt-get upgrade 

要么

 FROM centos ENV http_proxy <HTTP_PROXY> ENV https_proxy <HTTPS_PROXY> RUN yum update 

在ENV中指定的所有variables都预置于每个RUN命令。 每个RUN命令都在自己的容器/环境中执行,所以它不会从之前的RUN命令inheritancevariables!

注意:没有必要使用代理来调用docker守护进程以使其工作,但是如果您想要拉取图片等,则需要为docker deamon设置代理。 您可以在Ubuntu的/etc/default/docker中设置守护进程的代理(不影响容器设置)。


此外,如果您在主机上运行代理 (例如localhost,127.0.0.1),则会发生这种情况。 主机上的本地主机与容器中的本地主机不同。 在这种情况下,您需要使用另一个IP(如172.17.42.1)将代理绑定到或绑定到0.0.0.0,则可以使用172.17.42.1而不是127.0.0.1来在Docker docker build期间从容器进行连接。

你也可以在这里找一个例子: 如何使用caching快速重builddockerfile?

在Dockerfile中的设置下面为我工作。 我在CoreOSVagrantboot2dockertesting过。 假设代理端口是3128

在Centos中:

 ENV http_proxy=ip:3128 ENV https_proxy=ip:3128 

在Ubuntu中:

 ENV http_proxy 'http://ip:3128' ENV https_proxy 'http://ip:3128' 

格式要小心,有的有http,有的没有,有的只有一个。 如果IP地址是192.168.0.193,那么设置将是:

在Centos中:

 ENV http_proxy=192.168.0.193:3128 ENV https_proxy=192.168.0.193:3128 

在Ubuntu中:

 ENV http_proxy 'http://192.168.0.193:3128' ENV https_proxy 'http://192.168.0.193:3128' 

如果你需要在coreos中设置代理,例如拉图像

 cat /etc/systemd/system/docker.service.d/http-proxy.conf [Service] Environment="HTTP_PROXY=http://192.168.0.193:3128" 

如果要使用Dockerfile构build,可以使用--build-arg选项。

https://github.com/docker/docker/issues/14634上的链接,请参阅“使用; – 使用多个HTTP_PROXY生成–build-build”一节:

 [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 . 

注意:在您自己的系统上,确保已经设置了HTTP_PROXY和NO_PROXY环境variables。

在你的Dockerfile中的任何apt-get命令之前,你应该把这一行

 COPY apt.conf /etc/apt/apt.conf 

不要忘记在Dockerfile所在的文件夹中创buildapt.confapt.conf文件的内容应该是这样的:

 Acquire::socks::proxy "socks://YOUR-PROXY-IP:PORT/"; Acquire::http::proxy "http://YOUR-PROXY-IP:PORT/"; Acquire::https::proxy "http://YOUR-PROXY-IP:PORT/"; 

如果你使用用户名和密码来连接你的代理,那么apt.conf应该是这样的:

 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/"; 

例如 :

 Acquire::https::proxy "http://foo:bar@127.0.0.1:8080/"; 

foo是用户名, bar是密码。

在小写的环境variables中使用–build-arg:

 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 . 

我有同样的问题,并find了另一个小的解决方法:我有一个预备脚本是从docker构build环境添加。 在脚本中我设置环境variables依赖于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 

这仍然有点粗糙,但为我工作

正如其他答案所示,– --build-arg可能是解决scheme。 在我的情况下,除了--build-arg选项之外,还必须添加--network=host

 docker build -t <TARGET> --build-arg http_proxy=http://<IP:PORT> --build-arg https_proxy=http://<IP:PORT> --network=host . 

如果你的代理设置正确,仍然无法访问互联网,那可能是DNSparsing。 检查主机Ubuntu VM上的/etc/resolve.conf 。 如果它包含nameserver 127.0.1.1 ,那是错误的。

在主机Ubuntu VM上运行这些命令来修复它:

 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 

现在/etc/resolv.conf应该有一个名称服务器的有效值,它将被docker容器复制。

我们正在做 …

 ENV http_proxy http://9.9.9.9:9999 ENV https_proxy http://9.9.9.9:9999 

并在docker文件结束…

 ENV http_proxy "" ENV https_proxy "" 

这个,现在(直到docker介绍构build环境variables),允许代理env vars只用于构build而不暴露他们

解决scheme的替代scheme不是在代理的本地构build您的图像,而是让docker使用docker“自动构build”为您构build图像。 由于docker不是build立你的代理背后的图像,问题就解决了。 一个自动构build的例子可在…

https://github.com/danday74/docker-nginx-lua(GITHUB回购);

https://registry.hub.docker.com/u/danday74/nginx-lua(DOCKER repo使用自动构build来观察github repo,并在github主分支上执行docker构build)

如果你想为wget设置代理,你应该把这些行放在Dockerfile中

 ENV http_proxy YOUR-PROXY-IP:PORT/ ENV https_proxy YOUR-PROXY-IP:PORT/ ENV all_proxy YOUR-PROXY-IP:PORT/ 

正如Tim Potter指出的那样,在dockerfile中设置代理是非常糟糕的。 在构build映像时,需要为公司networking添加代理,但是您可能正在部署在云或DMZ中,无需代理或代理服务器不同。

此外,你不能与你的公司以外的其他人分享你的形象。