为什么在容器IP和别名之间交换会导致AJAX请求的不同?
我有一个位于这里的小示例项目,说明了在使用nginx + node + 主机 docker stack 时看到的问题 。
我有2个容器:
- 简单地返回一个json对象的节点 (快速)应用程序。 它是根据这个网站启用CORs。 它有它的端口发布到主机通过
3000:80
- 一个nginx服务器也基于这个网站启用CORs。 它只从默认位置(
/usr/shared/nginx/html
)提供静态内容(index.html
和main.js
文件)。 其端口通过8080:80
。
当从主机单独运行容器时,我可以访问节点服务器并查看返回的JSON对象。 当我访问nginx服务器时,我看到我的index.html
和main.js
的javascript代码运行。
现在我有节点应用程序容器链接到nginx服务器容器。 从我的nginx容器的main.js
文件中,我试图通过http://nodeapp/api
访问服务器。 我看到一个CORs错误
XMLHttpRequest无法加载http:// nodeapp / api 。 请求的资源上没有“Access-Control-Allow-Origin”标题。 原因' http:// localhost:8080 '因此不被允许访问。
奇怪的是, 响应头指示它来自nginx,而不是我所期望的快速应用程序。 nginx容器也没有logging任何东西。
事情的工作
-
如果我将XMLHttpRequest的URL更改为节点容器的IP(比如说172.17.0.2),它将按预期工作, 并且响应标头指示它来自快速服务器。 在我的
/etc/hosts
文件中有一个条目:
172.17.0.2 nodeapp abc123ContainerId quickserve_nodeapp_run_1
-
当我从一个交互式的tty容器中
curl
节点容器时,它也能按预期工作。 -
如果我加载节点容器并使用
http-server
(主机上http-server
),则按预期工作, 并且响应标头指示它来自快速服务器。
以防万一它包含,那个旧的线程(2013年)在docker守护进程中提到了一个cor选项。
如今(2015年第四季度), docker守护进程包括:
--api-cors-header="" Set CORS headers in the remote API
要设置跨源请求到远程API,请在守护进程模式下运行Docker时为
--api-cors-header
。 设置*(星号)允许全部,默认或空白意味着禁用CORS
$ docker -d -H="192.168.1.9:2375" --api-cors-header="http://foo.bar"
这可能是一个设置在你的情况下使用。