2017-08-13 212 views
3

我有一个角度应用程序运行在一个docker ubuntu镜像中,安装了nginx。我想将此映像部署到Kubernetes,并使用nginx代理将所有对/ api的调用重定向到Kubernetes中的后端服务。nginx proxy_pass导致404未找到页面

我的静态Web资源趴在/ var/www/html等我添加下面的配置到/etc/nginx/conf.d:

upstream backend-service { 
    server backend-service:8080; 
} 

server { 
    listen 80; 

    location/{ 
    try_files $uri $uri/ /index.html; 
    } 

    location ^~ /api { 
    proxy_pass http://backend-service; 
    } 
} 

上访问前端服务/或/#/仪表板返回我的Angular页面的预期组件,但对/ api/v1/data的调用仅显示默认的nginx 404 Not Found页面

我需要修改哪些后端调用重定向到后端?

我使用nginx的1.10.3在Ubuntu 16.04和我的前端Dockerfile看起来是这样的:

FROM ubuntu:16.04 

# Install curl, nodejs and nginx 
RUN apt-get update && \ 
    apt-get install -y curl && \ 
    curl -sL https://deb.nodesource.com/setup_8.x | bash - && \ 
    apt-get install -y nodejs nginx && \ 
    rm -rf /var/lib/apt/lists/* 

# Create directory 
RUN mkdir -p /usr/src/app 
WORKDIR /usr/src/app 

# Copy and build rest of the app 
COPY . /usr/src/app 
RUN npm install 
RUN node_modules/@angular/cli/bin/ng build --prod 
RUN cp -a dist/. /var/www/html 

# Configure and start nginx 
COPY frontend.conf /etc/nginx/conf.d 

EXPOSE 80 

CMD ["nginx", "-g", "daemon off;"] 

编辑:关于后端服务信息

后端服务听得到并在/ api/v1/data上发布请求,并可通过名为后端服务的服务在Kubernetes中进行访问。

EDIT2:Nginx的access.log的

https://gist.github.com/Steffen911/a56e3175bf12e511048d01359a475724

172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET/HTTP/1.1" 200 380 "-" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /styles.d41d8cd98f00b204e980.bundle.css HTTP/1.1" 200 0 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /inline.c9a1a6b995c65c13f605.bundle.js HTTP/1.1" 200 1447 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /polyfills.117078cae3e3d00fc376.bundle.js HTTP/1.1" 200 97253 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /main.3e9a37b4dd0f3bf2465f.bundle.js HTTP/1.1" 200 64481 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /vendor.146173c1a99cc2172a5f.bundle.js HTTP/1.1" 200 661261 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /api/v1/data/ HTTP/1.1" 404 209 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /assets/home.jpg HTTP/1.1" 200 2608 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /assets/busy.gif HTTP/1.1" 200 48552 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /assets/background_light.png HTTP/1.1" 200 170599 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /assets/google.svg HTTP/1.1" 200 2232 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /assets/email.svg HTTP/1.1" 200 1596 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:40 +0000] "GET /favicon.ico HTTP/1.1" 200 198 "http://192.168.99.100:30497/" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 
172.17.0.1 - - [13/Aug/2017:13:11:44 +0000] "GET /api/v1/data/ HTTP/1.1" 404 209 "-" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36" 

error.log文件是空的。

EDIT3:nginx的新版本和其他SO线程

我也试过nginx的1.12.1,它显示了相同的行为。这个问题的答案也没有帮助:nginx proxy_pass 404 error, don't understand why

Edit4:我上传再现GitHub上

https://github.com/Steffen911/nginx-sample

+0

你没有发布任何有关后端服务?它期望什么网址?使用/ api /还是不使用? –

+0

@TarunLalwani我更新了问题。它预计会打电话给/ api/v1/data –

+0

发布您的nginx日志也 –

回答

2

从你的nginx的故障排除,看来你有nginx的配置文件没有有效的效果 - 你报告接受404 Not Found误差比索引页之外的一切,所有的指令,从try_fileslocation /,到更具体的location ^~ /api中的proxy_passreturn 200 test,没有效果。

因此,问题似乎在Dockerfile - 看起来大多数其他NGINX + Docker教程删除默认配置(例如,与RUN rm /etc/nginx/conf.d/default.conf),而您的文件丢失任何此类删除。

事实上,Debian/Ubuntu似乎有一个名为/etc/nginx/sites-available/etc/nginx/sites-enabled可疑程序,对不规范的目录,其默认情况下,必须包含一个放肆listen 80 default_server一个default文件,有效地采取优先的任何其他listen同样的港口在没有更具体的server_name


因此,有多个独立的解决方案:


  • 不要使用从根本上破包,比如由于Debian/Ubuntu提供的服务。我曾经花了很多时间拉我的头发,试图找出为什么我的配置不起作用,只是要注意,即使从emacstest.conf~的备份文件通过Debian的默认include /etc/nginx/sites-enabled/*;包括在Debian中。 启用网站是邪恶的。

    注意NGINX provides official binary packages for most distributions,这不会有这样的问题,因为它不会尝试在其/etc/nginx/conf.d/default.conf定义default_server,而不是做一个listen 80;server_name localhost;,在大多数走出自己的方式自动本身情况。

    例如,将FROM ubuntu:16.04替换为您的Dockerfile中的FROM nginx即可使用NGINX官方图片。


  • 如果仍然使用nginx的来自于Debian/Ubuntu,确保RUN rm /etc/nginx/sites-enabled/defaultDockerfile删除default_serverlisten

  • 使用server_name指令与listen指令与default_server参数来定义基于主机的服务器,可能在一起了。

    注意,在配置重复server_name规范结果警告(与[warn]严重性),但重复default_server配置错误([emerg]严重程度),这可能有助于解决该问题早。

2

呼叫我的问题,一个最小的例子/ API/V1 /数据只显示默认的nginx 404 Not Found页面

proxy_pass指令不太可能产生默认的nginx 404 Not Found错误页面本身。

  • 404可能由上游产生,在这种情况下,不存在进一步的说明,nginx的将简单地从上游传播消息。如果你在404上有一个nginx签名,那么这意味着上游也在运行nginx,可能会让你大吃一惊,揭示配置的罪魁祸首。

  • 如果404实际上是由nginx生成的,那么它可能是location不匹配的情况。尝试将return 200 thisisatest;代替proxy_pass来解决问题。

    然而,在特定情况下,location ^~ /api {是一个几乎不可能的指令不匹配/api/v1/data/请求URI - 我能想到的唯一的事情是,如果你可能有一个try_filesserver配置任何其他location指令之外,这可能会使所有的位置指令无效。您确定您的try_files完全包含在location /的上下文中吗?

+0

我知道我的上游正在运行不基于nginx的nodejs docker容器。我也尝试了你的第二个建议,并用返回200代替了proxy_pass;但我仍然得到一个404不是“/”的东西。我只添加了我在此粘贴的配置文件。默认的nginx配置是否覆盖了可能会破坏我预期行为的事情? –

+0

我还添加了一个例子,将我的问题完全复制到 –

+0

@SteffenSchmitz,哇,这真的很奇怪,您可以像这样重现它;因为即使使用了'return 200',你仍然会得到404,但我唯一的建议是,你仍旧有一个旧的配置文件,它优先于你的新配置文件;就我个人而言,我遇到了一个问题,我尝试在'/ etc/nginx/sites-enabled'中修改文件,备份文件(例如test.conf〜)优先于'test.conf' ,因此事情会非常奇怪。 – cnst