目录

Nginx - 自定义镜像

笔记

虽然 DockerHub 已经有了 Nginx 或 OpenResty,但是不够「灵活」,我们无法安装第三方模块。本内容讲解如何利用 Dockerfile 构建属于自己的 Nginx 或 OpenResty 镜像。

2021-11-14 @Young Kbt

# 前言

之前我一直使用的是从 DockerHub 拉取下载的镜像,但是该镜像已经固定了模块,我在使用的过程时,尝试了 Nginx 自带的下载站点,但是界面比较简洁、普通,而且字体很「拥挤」,于是我踏上寻找优化下载站点页面的道路,然后我发现了第三方模块 ngx-fancyindex,该模块优化了下载站点的页面,看起来更加舒服,于是我打算使用它。

但是我发现了一个问题,我的 Nginx 是从 DockerHub 拉取的,说明供应商已经设计好所需的模块,但是并没有我想要的 ngx-fancyindex 模块,供应商只提供了基础的 Nginx 镜像。于是我就无法针对这个 Nginx 镜像添加第三方模块,特别是后期,如果我需要添加多个第三方模块,那面对拉取的 Nginx 镜像无能为力。

于是,我就打算自己构建一个 Nginx 镜像,在构建的过程,添加第三方模块。

我的下载站点地址:https://www.youngkbt.cn/download/ (opens new window)

下面的内容有很多代码,如果不喜欢复制这些代码,这里提供源码文件的下载地址:https://www.youngkbt.cn/download/OpenResty构建/ (opens new window)

需要全部的源码,下载 openresty-resource.tar.gz 压缩包。需要单个文件,就点击单个文件。

如果想要了解如何构建我的下载站点,点击跳转

# 构建过程

最后的结果不繁琐,仅仅一个 Dockerfile 文件就解决,但是过程耗费了我半天,这里先提供 Dockerfile 文件内容:

FROM centos:7.9

# openrestry 版本
ARG OPENRESTY_VERSION="1.19.9.1"

# 第三方模块版本,我安装 ngx-fancyindex 模块
#ARG FANCYINDEX_VERSION="0.5.2"

# 镜像信息
LABEL AUTHOR=YoungKbt

# 如果事先下载第三模块的压缩包,则放入 Dockerfile 所在的目录下,取消注释
#ADD ngx-fancyindex-${FANCYINDEX_VERSION}.tar.xz /tmp

# 安装 Nginx 环境库,下载第三方模块和 Nginx 或 Openresty,并解压编译安装
RUN yum install -y \
     gcc pcre pcre-devel zlib zlib-devel openssl openssl-devel --nogpgcheck \
     curl wget perl make vim tar \
    && cd /tmp \ 
    && wget https://openresty.org/download/openresty-${OPENRESTY_VERSION}.tar.gz \
    # 如果不喜欢先下载第三方模块然后 ADD,则这里填写第三方模块的下载地址,然后取消下面两行注释
    # && wget https://github.com/aperezdc/ngx-fancyindex/releases/download/v${FANCYINDEX_VERSION}/ngx-fancyindex-${FANCYINDEX_VERSION}.tar.xz \
    # && tar xvf ngx-fancyindex-${FANCYINDEX_VERSION}.tar.xz \
    && tar zxvf openresty-${OPENRESTY_VERSION}.tar.gz \
    && cd openresty-${OPENRESTY_VERSION} \
    && ./configure \
        --prefix=/usr/local/openresty \
        --with-cc-opt='-O2 -DNGX_LUA_ABORT_AT_PANIC -I/usr/local/openresty/zlib/include -I/usr/local/openresty/pcre/include -I/usr/local/openresty/openssl111/include' \
        --with-ld-opt='-Wl,-rpath,/usr/local/openresty/luajit/lib -L/usr/local/openresty/zlib/lib -L/usr/local/openresty/pcre/lib -L/usr/local/openresty/openssl111/lib -Wl,-rpath,/usr/local/openresty/zlib/lib:/usr/local/openresty/pcre/lib:/usr/local/openresty/openssl111/lib' \
        --with-pcre-jit \
        --with-stream \
        --with-stream_ssl_module \
        --with-stream_ssl_preread_module \
        --with-http_v2_module \
        --without-mail_pop3_module \
        --without-mail_imap_module \
        --without-mail_smtp_module \
        --with-http_stub_status_module \
        --with-http_realip_module \
        --with-http_addition_module \
        --with-http_auth_request_module \
        --with-http_secure_link_module \
        --with-http_random_index_module \
        --with-http_gzip_static_module \
        --with-http_sub_module \
        --with-http_dav_module \
        --with-http_flv_module \
        --with-http_mp4_module \
        --with-http_gunzip_module \
        --with-threads --with-stream \
        --with-http_ssl_module \
        # --add-module=../ngx-fancyindex-${FANCYINDEX_VERSION} \
    && make build \
    && make install \
    && cd /tmp \
    && rm -rf ngx-fancyindex-${FANCYINDEX_VERSION}.tar.xz \
    && rm -rf openresty-${OPENRESTY_VERSION}.tar.gz \
    && yum clean all \
    && mkdir -p /etc/nginx/conf.d \
    # 必须创建一个目录,如果这个目录不存在,则无法启动镜像
    && mkdir -p /var/run/openresty

# 将 nginx 命令添加至全局变量,这里演示常用的三个
ENV PATH=$PATH:/usr/local/openresty/luajit/bin:/usr/local/openresty/nginx/sbin:/usr/local/openresty/bin
ENV LUA_PATH="/usr/local/openresty/site/lualib/?.ljbc;/usr/local/openresty/site/lualib/?/init.ljbc;/usr/local/openresty/lualib/?.ljbc;/usr/local/openresty/lualib/?/init.ljbc;/usr/local/openresty/site/lualib/?.lua;/usr/local/openresty/site/lualib/?/init.lua;/usr/local/openresty/lualib/?.lua;/usr/local/openresty/lualib/?/init.lua;./?.lua;/usr/local/openresty/luajit/share/luajit-2.1.0-beta3/?.lua;/usr/local/share/lua/5.1/?.lua;/usr/local/share/lua/5.1/?/init.lua;/usr/local/openresty/luajit/share/lua/5.1/?.lua;/usr/local/openresty/luajit/share/lua/5.1/?/init.lua"
ENV LUA_CPATH="/usr/local/openresty/site/lualib/?.so;/usr/local/openresty/lualib/?.so;./?.so;/usr/local/lib/lua/5.1/?.so;/usr/local/openresty/luajit/lib/lua/5.1/?.so;/usr/local/lib/lua/5.1/loadall.so;/usr/local/openresty/luajit/lib/lua/5.1/?.so"

# 将 nginx 配置文件,覆盖 Nginx 自带的配置文件
COPY nginx.conf /usr/local/openresty/nginx/conf/nginx.conf

# 将 default.conf 配置文件,添加到指定目录下
COPY nginx.vh.default.conf /etc/nginx/conf.d/default.conf

# 启动容器时,执行该命令,如果不执行,则容器启动后会自动停止运行
CMD ["/usr/local/openresty/nginx/sbin/nginx", "-g", "daemon off;"]

# Use SIGQUIT instead of default SIGTERM to cleanly drain requests
# See https://github.com/openresty/docker-openresty/blob/master/README.md#tips--pitfalls
STOPSIGNAL SIGQUIT
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79

代码虽然多,但是并不复杂,容我慢慢解释:

  • 首先注意你的基础镜像,我是基于 Centos:7.9 系统,你可以是 Ubuntu 或者其他的系统,FROM 指令会先去本地找镜像,没有找到则去 DockerHub 下载到本地,再使用

  • 我这里使用的是 OpenRestry,这个平台集成了 Nginx 和 Lua 语言,总体而言就是拥有更多功能的 Nginx。

  • 4、7 行请填写 OpenRestry 或者 Nginx 的版本,以及第三方模块的版本号,我使用一个变量存储版本号,你也可以直接在下载的时候,写版本号

  • 10 行的镜像信息 LABEL 可以不写,一般是镜像的关键词、作者信息等

  • 13 行的 ADD 可以不写,因为我的第三方模块地址在 GitHub,而通过 wget 下载经常连接超时、下载失败,所以我就先下载到 Windows,然后传输到服务器里。注意,如果采用这种方式,请将第三方模块放到 Dockerfile 所在的目录里

  • 17 - 18 行 是下载安装 Nginx 所需的运行环境,以及一些常用的命令,可以根据需求自行添加命令

  • 20 行下载 OpenResty,可以更换为 Nginx 的下载地址,后面 ${} 就是存储版本号的变量

  • 21 行表示在 /tmp 目录下执行安装操作,构建完成后,可以去该目录下查看源码

  • 22 - 23 行下载第三方模块并解压,如果采用第 13 行的 ADD 方式,就注释掉或者删除掉

  • 26 - 54 行是编译并安装。第三方模块请添加在第 51 行代码后,第 52 行代码就是我添加的第三方模块,该路径与 OpenResty 同级,所以 ../ 就是返回上一级目录,找到第三模块的根目录名。

    52 行之前都是常用的自带模块,建议不要删除,日后可能用到。

  • 55 - 57 行是删除下载的压缩包,但是并没有删除解压之后的目录,你可以根据需求决定要不要删除

  • 58 行是清除之前 yum 安装的环境以及命令的缓存,注意:只是清除安装过程的缓存,不会卸载安装的库和命令。因为 yum 下载后成功后,将一份存在缓存,为了不占用空间,所以清除掉

  • 59 行是为了适应官方的镜像配置处理。一般而言,我们不能直接操作 Nginx 的「核心」配置文件 nginx.conf,而是操作「子」配置文件 xxx.conf。因为「核心」配置文件通过 include 指令将「子」配置文件进行引入,所以我们只需在 nginx.conf 加入 include /etc/nginx/conf.d;,即可把 conf.d 目录下的所有「子」配置文件引入其中。这样做是为了安全考虑,直接操作核心配置文件,容易引起安全问题。

    下面我会提供 nginx.conf 的模板,该模板已经使用了 include /etc/nginx/conf.d;,不需要自己写。

  • 61 行是因为我在启动镜像的时候,报错:/var/run/openresty 不存在,所以构建时候需要创建,如果你的报错不是这个目录,而修改即可

  • 64 - 66 行添加 nginx 命令到全局变量,如果是 OpenRestry 不需要修改,如果是 Nginx,你需要删除第一个和第三个路径,只留下第二个

  • 69 行将宿主机的 nginx.conf 覆盖原来的 nginx.conf,因为原来的 nginx.conf 没有 include /etc/nginx/conf.d;,下面会有宿主机的 nginx.conf 模板

  • 72 行给 /etc/nginx/conf.d 目录下添加一个 .conf 配置文件,以后我们只需要在这个配置文件添加 server 模块,下方有模板提供

  • 75 行是必须的,它是启动容器后不希望容器停止的命令

  • 79 行是优化命令,可以不加

说了那么多,大家可能没有耐心看完,我想说,如果你想了解 OpenResty 或 Nginx 镜像的构建过程,请了解它。我这里也说明下简单的上手:

  • 第 1 行可以修改

  • 第 4、7 行可以修改版本,版本目前是最新的

  • 第 10 行可以修改

  • 第 22、23 行修改自己的第三方模块地址,如果下载失败,则看上方的第 5 个解释(黑点)

  • 第 52 行以及后面的是第三模块路径(容器内的路径,并不是宿主机的路径)

  • 第 65、66 行如果是 Nginx,请删除掉,并且 64 行删除掉第一个和第三个路径

  • 第 75 行如果是 Nginx,请填写 nginx 可执行文件的路径

# 配置文件模板

下面提供 nginx.conf 的模板:

# nginx.conf  --  docker-openresty
#
# This file is installed to:
#   `/usr/local/openresty/nginx/conf/nginx.conf`
# and is the file loaded by nginx at startup,
# unless the user specifies otherwise.
#
# It tracks the upstream OpenResty's `nginx.conf`, but removes the `server`
# section and adds this directive:
#     `include /etc/nginx/conf.d/*.conf;`
#
# The `docker-openresty` file `nginx.vh.default.conf` is copied to
# `/etc/nginx/conf.d/default.conf`.  It contains the `server section
# of the upstream `nginx.conf`.
#
# See https://github.com/openresty/docker-openresty/blob/master/README.md#nginx-config-files
#

user  nobody;
#worker_processes 1;

# Enables the use of JIT for regular expressions to speed-up their processing.
pcre_jit on;



#error_log  logs/error.log;
#error_log  logs/error.log  notice;
#error_log  logs/error.log  info;

#pid        logs/nginx.pid;


events {
    worker_connections  1024;
}


http {
    include       mime.types;
    default_type  application/octet-stream;

    # Enables or disables the use of underscores in client request header fields.
    # When the use of underscores is disabled, request header fields whose names contain underscores are marked as invalid and become subject to the ignore_invalid_headers directive.
    # underscores_in_headers off;

    #log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
    #                  '$status $body_bytes_sent "$http_referer" '
    #                  '"$http_user_agent" "$http_x_forwarded_for"';

    #access_log  logs/access.log  main;

        # Log in JSON Format
        # log_format nginxlog_json escape=json '{ "timestamp": "$time_iso8601", '
        # '"remote_addr": "$remote_addr", '
        #  '"body_bytes_sent": $body_bytes_sent, '
        #  '"request_time": $request_time, '
        #  '"response_status": $status, '
        #  '"request": "$request", '
        #  '"request_method": "$request_method", '
        #  '"host": "$host",'
        #  '"upstream_addr": "$upstream_addr",'
        #  '"http_x_forwarded_for": "$http_x_forwarded_for",'
        #  '"http_referrer": "$http_referer", '
        #  '"http_user_agent": "$http_user_agent", '
        #  '"http_version": "$server_protocol", '
        #  '"nginx_access": true }';
        # access_log /dev/stdout nginxlog_json;

    # See Move default writable paths to a dedicated directory (#119)
    # https://github.com/openresty/docker-openresty/issues/119
    client_body_temp_path /var/run/openresty/nginx-client-body;
    proxy_temp_path       /var/run/openresty/nginx-proxy;
    fastcgi_temp_path     /var/run/openresty/nginx-fastcgi;
    uwsgi_temp_path       /var/run/openresty/nginx-uwsgi;
    scgi_temp_path        /var/run/openresty/nginx-scgi;

    sendfile        on;
    #tcp_nopush     on;

    #keepalive_timeout  0;
    keepalive_timeout  65;

    #gzip  on;

    include /etc/nginx/conf.d/*.conf;

    # Don't reveal OpenResty version to clients.
    # server_tokens off;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90

nginx.vh.default.conf 模板内容:

# nginx.vh.default.conf  --  docker-openresty
#
# This file is installed to:
#   `/etc/nginx/conf.d/default.conf`
#
# It tracks the `server` section of the upstream OpenResty's `nginx.conf`.
#
# This config (and any other configs in `etc/nginx/conf.d/`) is loaded by
# default by the `include` directive in `/usr/local/openresty/nginx/conf/nginx.conf`.
#
# See https://github.com/openresty/docker-openresty/blob/master/README.md#nginx-config-files
#


server {
    listen       80;
    server_name  localhost;

    #charset koi8-r;
    #access_log  /var/log/nginx/host.access.log  main;

    location / {
        root   /usr/local/openresty/nginx/html;
        index  index.html index.htm;
    }

    #error_page  404              /404.html;

    # redirect server error pages to the static page /50x.html
    #
    error_page   500 502 503 504  /50x.html;
    location = /50x.html {
        root   /usr/local/openresty/nginx/html;
    }

    # proxy the PHP scripts to Apache listening on 127.0.0.1:80
    #
    #location ~ \.php$ {
    #    proxy_pass   http://127.0.0.1;
    #}

    # pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
    #
    #location ~ \.php$ {
    #    root           /usr/local/openresty/nginx/html;
    #    fastcgi_pass   127.0.0.1:9000;
    #    fastcgi_index  index.php;
    #    fastcgi_param  SCRIPT_FILENAME  /scripts$fastcgi_script_name;
    #    include        fastcgi_params;
    #}

    # deny access to .htaccess files, if Apache's document root
    # concurs with nginx's one
    #
    #location ~ /\.ht {
    #    deny  all;
    #}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58

这里给出我的 Dockfile 所在的目录下所有内容:

image-20211214191438954

可以看出,我并非 ADD nginx.conf,而是 ADD mynginx.conf,这是我修改后的 nginx.conf,比如开启压缩、优化访问速度等指令,压缩包是我的第三方模块,因为 wget 下载的地址是 GitHub,太慢了。

更新时间: 2024/01/17, 05:48:13
最近更新
01
JVM调优
12-10
02
jenkins
12-10
03
Arthas
12-10
更多文章>