Nginx在php-fpm上作为带有后端的反向代理工作,始终返回状态码200

时间:2019-11-07 20:05:40

标签: php nginx php-7 alpine nginx-reverse-proxy

每当php服务器返回带有正文的响应时,即使应用程序未返回状态码200,nginx也会以状态代码200和正确的正文从应用程序进行响应。如果未设置应用程序并响应正文,则nginx返回相同的内容应用程序返回的状态代码。

我正在使用此Dockerfile。

FROM php:7.2-fpm-alpine3.9

RUN apk update && apk add nginx

WORKDIR /var/www

RUN mkdir -p /run/nginx

# nginx conf
RUN echo '\
server {                                                                \
    listen 80 default_server;                                           \
    listen [::]:80 default_server;                                      \
                                                                        \
    location / {                                                        \
      # Remove trailing slashes before checking for matching locations  \
      rewrite ^(.+)\/$ $1 permanent;                                    \
                                                                        \
      dav_methods PUT DELETE MKCOL COPY MOVE;                           \
      dav_access all:r;                                                 \
      index index.php index.html index.htm;                             \
      try_files $uri $uri/ /index.php?$args;                            \
    }                                                                   \
                                                                        \
    location ~ index\.php$ {                                            \
      include /etc/nginx/fastcgi_params;                                \
      fastcgi_split_path_info ^(.+\.php)(/.+)$;                         \
      fastcgi_pass 127.0.0.1:9000;                                      \
      fastcgi_index index.php;                                          \
      fastcgi_param SCRIPT_FILENAME /var/www/html$fastcgi_script_name;  \
    }                                                                   \
}                                                                       \
' > /etc/nginx/conf.d/default.conf;

# php file
RUN echo '\
<?php                             \
echo "Hello World";               \
http_response_code(400);          \
?>                                \
'> /var/www/html/index.php

ENTRYPOINT [ "ash" ]

要进行测试,请进入运行的Docker容器

  1. 启动nginx
  2. 开始php-fpm进程
  3. 使用curl创建请求
  4. 检查nginx输出日志
$ nginx && \
  php-fpm --daemonize && \
  curl -XGET 127.0.0.1/abcd && \
  cat /var/log/nginx/access.log

注意:如果从index.php中删除 echo“ Hello World”; ,nginx将返回正确的状态码。

编辑:

但这可以按预期工作。

FROM debian:10-slim

ARG VERSION=7.2

# replace shell with bash so we can source files
SHELL ["/bin/bash", "-c"]

ENV DEBIAN_FRONTEND=noninteractive NODE_VERSION=12

ADD https://packages.sury.org/php/apt.gpg /opt/apt-php.gpg

RUN set -ex; \
    apt-get update -y; \
    apt-get install git gnupg -y; \
    apt-key add - < /opt/apt-php.gpg; \
    apt-get install -y apt-transport-https lsb-release ca-certificates; \
    echo "deb https://packages.sury.org/php/ $(lsb_release -sc) main" > /etc/apt/sources.list.d/php.list; \
    apt-get update -y; \
    apt-get upgrade -y; \
    apt-get install -y \
    php${VERSION} \
    php${VERSION}-fpm \
    nginx \
    curl;

# nginx conf
RUN echo '\
server {                                                                \
    listen 80 default_server;                                           \
    listen [::]:80 default_server;                                      \
                                                                        \
    location / {                                                        \
      # Remove trailing slashes before checking for matching locations  \
      rewrite ^(.+)\/$ $1 permanent;                                    \
                                                                        \
      dav_methods PUT DELETE MKCOL COPY MOVE;                           \
      dav_access all:r;                                                 \
      index index.php index.html index.htm;                             \
      try_files $uri $uri/ /index.php?$args;                            \
    }                                                                   \
                                                                        \
    location ~ index\.php$ {                                            \
      include /etc/nginx/fastcgi_params;                                \
      fastcgi_split_path_info ^(.+\.php)(/.+)$;                         \
      fastcgi_pass 127.0.0.1:9000;                                      \
      fastcgi_index index.php;                                          \
      fastcgi_param SCRIPT_FILENAME /var/www/html$fastcgi_script_name;  \
    }                                                                   \
}                                                                       \
' > /etc/nginx/sites-available/default;

# php file
RUN echo '\
<?php                             \
echo "Hello World";               \
http_response_code(400);          \
?>                                \
'> /var/www/html/index.php

RUN sed -i "s/listen\ =\ \/run\/php\/php7.2-fpm.sock/listen\ =\ 127.0.0.1:9000/"  /etc/php/7.2/fpm/pool.d/www.conf

RUN mkdir -p /run/php

RUN ln -s /usr/sbin/php-fpm7.2 /usr/sbin/php-fpm

ENTRYPOINT [ "bash" ]

1 个答案:

答案 0 :(得分:0)

这是一种预期的行为,您可以在此处看到-https://www.php.net/manual/en/function.header.php

特别是

  

请记住,在发送任何实际输出之前,必须通过常规HTML标记,文件中的空白行或从PHP调用header()。这是一个非常常见的错误   读取包含或要求功能或其他文件访问权限的代码   函数,并且在header()之前输出空格或空行   叫。使用单个PHP / HTML文件时,存在相同的问题。

可以通过在php ini设置中将 output_buffering 设置为“开”或使用php -S localhost:5000 -d output_buffering=4098之类的选项运行cli来避免这种情况。