找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 300|回复: 8

[编程] docker nginx 一把梭

[复制链接]
发表于 2022-2-10 17:15:21 | 显示全部楼层 |阅读模式
游戏昵称 小虫子|U币余额 97997


# OpenResty

`ngx_lua` 是 `nginx` 的一个模块,提供了使用 `lua` 语言操作 `nginx` 的 API。

`OpenResty` 是对 `nginx`、`ngx_lua` 等模块、`nginx` 所需的 `OpenSSL`、`PCRE`、以及 `OpenResty` 的 `lua` 库、相关脚本和工具的打包。

## Docker 版说明

Docker 版本的 Openresty,使用预编译后手工精简的方法制作。Docker 镜像仅添加预编译包和添加相关依赖,以减小镜像体积。

## 编译

安装编译时依赖:
```bash
apk add build-base coreutils curl gd-dev geoip-dev libxslt-dev linux-headers make perl-dev readline-dev patch gd geoip libgcc libxslt ccache
```

### 编译 zlib

```bash
wget https://www.zlib.net/zlib-1.2.11.tar.xz
tar xf zlib-1.2.11.tar.xz
cd zlib-1.2.11
export CC="ccache gcc -fdiagnostics-color=always -g3"
export CFLAGS=
export CXXFLAGS=
export CPPFLAGS=
export LDFLAGS=
./configure --prefix=/opt/openresty/zlib
make -j$(nproc) CFLAGS='-O3 -D_LARGEFILE64_SOURCE=1 -DHAVE_HIDDEN -g3' \
    SFLAGS='-O3 -fPIC -D_LARGEFILE64_SOURCE=1 -DHAVE_HIDDEN -g3' \
    CC='ccache gcc -fdiagnostics-color=always'
make install
```

### 编译 PCRE

```bash
wget https://ftp.pcre.org/pub/pcre/pcre-8.44.tar.bz2
tar xf pcre-8.44.tar.bz2
cd pcre-8.44/
export CC="ccache gcc -fdiagnostics-color=always -g3"
export CFLAGS=
export CXXFLAGS=
export CPPFLAGS=
export LDFLAGS=
./configure \
    --prefix=/opt/openresty/pcre \
    --libdir=/opt/openresty/pcre/lib \
    --disable-cpp \
    --enable-jit \
    --enable-utf \
    --enable-unicode-properties
make -j$(nproc)
make install
cd
```

### 编译 OpenSSL

需要额外安装 OpenResty 唯一指定 OpenSSL,且需要打 OpenResty 的 patch。

```bash
wget https://www.openssl.org/source/openssl-1.1.1l.tar.gz
wget https://raw.githubusercontent.com/openresty/openresty/master/patches/openssl-1.1.1f-sess_set_get_cb_yield.patch
tar xf openssl-1.1.1l.tar.gz
cd openssl-1.1.1l/
patch -p1 < ../openssl-1.1.1f-sess_set_get_cb_yield.patch
export CC="ccache gcc -fdiagnostics-color=always -g3"
export CFLAGS=
export CXXFLAGS=
export CPPFLAGS=
export LDFLAGS=
./config \
    shared zlib -g3 \
    enable-camellia enable-seed enable-rfc3779 \
    enable-cms enable-md2 enable-rc5 \
    enable-weak-ssl-ciphers \
    enable-ssl3 enable-ssl3-method \
    --prefix="/opt/openresty/openssl111" \
    --libdir=lib \
    -I/opt/openresty/zlib/include \
    -L/opt/openresty/zlib/lib \
    -Wl,"-rpath,/opt/openresty/zlib/lib:/opt/openresty/openssl111/lib"
make CC='ccache gcc -fdiagnostics-color=always -g3' -j$(nproc)
make install_sw
cd
```
这里使用了上一步安装的 gnu patch 来打补丁。因为 Alpine Linux 自带的 `patch` 是 `busybox` 实现的,存在兼容性问题,无法正确打补丁。


### 编译 OpenResty

这一步是编译 `OpenResty` 自带的 `Nginx` 和 `luajit`,以及 Openrsty 的 lua 库、命令行工具。

```bash
wget https://openresty.org/download/openresty-1.19.9.1.tar.gz
tar xf openresty-1.19.9.1.tar.gz
cd openresty-1.19.9.1/
export CC="ccache gcc -fdiagnostics-color=always -g3"
export CFLAGS=
export CXXFLAGS=
export CPPFLAGS=
export LDFLAGS=
./configure -j$(nproc) \
    --prefix='/opt/openresty' \
    --with-cc='ccache gcc -fdiagnostics-color=always -g3' \
    --with-cc-opt="-DNGX_LUA_ABORT_AT_PANIC -I/opt/openresty/zlib/include -I/opt/openresty/pcre/include -I/opt/openresty/openssl111/include" \
    --with-ld-opt="-L/opt/openresty/zlib/lib -L/opt/openresty/pcre/lib -L/opt/openresty/openssl111/lib -Wl,-rpath,/opt/openresty/zlib/lib:/opt/openresty/pcre/lib:/opt/openresty/openssl111/lib" \
    --with-luajit-xcflags='-DLUAJIT_NUMMODE=2 -DLUAJIT_ENABLE_LUA52COMPAT' \
    --with-pcre-jit \
    --without-http_rds_json_module \
    --without-http_rds_csv_module \
    --without-lua_rds_parser \
    --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-compat \
    --http-client-body-temp-path=/dev/shm/nginx_request_temp \
    --http-proxy-temp-path=/dev/shm/nginx_proxy_temp \
    --http-fastcgi-temp-path=/dev/shm/nginx_fastcgi_temp \
    --http-uwsgi-temp-path=/dev/shm/nginx_uwsgi_temp \
    --http-scgi-temp-path=/dev/shm/nginx_scgi_temp
make -j$(nproc)
make install
cd
```

编译完成的 `OpenResty`,以及其自带的 `openssl`,`luajit`,`zlib` 与 `pcre` 均在 `/opt/openresty` 目录下。

将 `/opt/openresty` 目录打包备用,即可部署预编译的二进制文件。

## 瘦身

刚完成编译的 `OpenResty`,包含 `openssl`,`luajit`,`zlib` 与 `pcre`,有 250+MiB 的体积。

如果环境对体积比较敏感,可删除生产环境不需要的文件,精简二进制 `elf` 来缩减体积。

通过 `ldd` 观察 `nginx` 二进制的动态库,发现仅需要以下文件
```bash
        libluajit-5.1.so.2 => /opt/openresty/luajit/lib/libluajit-5.1.so.2 (0x7f52023cb000)
        libpcre.so.1 => /opt/openresty/pcre/lib/libpcre.so.1 (0x7f520233d000)
        libssl.so.1.1 => /opt/openresty/openssl111/lib/libssl.so.1.1 (0x7f52022a3000)
        libcrypto.so.1.1 => /opt/openresty/openssl111/lib/libcrypto.so.1.1 (0x7f5201fad000)
        libz.so.1 => /opt/openresty/zlib/lib/libz.so.1 (0x7f5201f90000)
```
因此,针对 `openssl`,`luajit`,`zlib` 与 `pcre` 四个组件,可精简 `openresty` 用不到的文件

`luajit` 可删除 `bin` 可执行文件、`include` 头文件、`share` 文档和脚本。`lib` 目录下可删除 `*.a` 静态库、各种目录,仅保留 `*.so` 动态库和其软连接文件即可。

`openssl` 可删除 `bin` 可执行文件、`include` 头文件。`lib` 目录下可删除 `*.a` 静态库和 `pkgconfig` 目录。

`pcre` 可删除 `bin` 可执行文件、`include` 头文件、`share` 文档。`lib` 目录下可删除 `*.a` 静态库、`*.la` 动态库配置和 `pkgconfig` 目录。

`zlib` 可删除 `include` 头文件、`share` 文档和脚本。`lib` 目录下可删除 `*.a` 静态库和 `pkgconfig` 目录。

`pod` 目录是文档,可以删。

删除了生产环境不需要的文件之后,可对 `elf` 文件 `strip`,删除编译时的调试符号来瘦身。

```bash
for file in $(find openresty -type f -perm 755 -exec file {} \;|grep ELF|grep not\ stripped|awk -F: '{
print $1}');do strip -s $file ;done
```

最终,整个 `openresty` 目录的体积可以缩小到 8MiB 左右。打包 `openresty` 目录,即可部署到其他机器上。

```bash
/opt # du -sh *
7.8M        openresty
109M        openresty-1.19.9.1-alpine-binary-full.tar.gz
3.1M        openresty-1.19.9.1-alpine-binary.tar.gz
```

## 二进制部署

安装运行时依赖:
```bash
apk add libgcc
```

将预编译的二进制包解压到 `/opt/` 目录即可使用。

## 镜像构建

准备好 `openresty-1.19.9.1-alpine-binary.tar.gz` 并将以下内容保存为 `Dockerfile`

```docker
FROM alpine:3.15.0

ADD openresty-1.19.9.1-alpine-binary.tar.gz /opt

RUN sed -i 's@dl-cdn.alpinelinux.org@mirrors.aliyun.com@g' /etc/apk/repositories \
    && apk add --no-cache \
        libgcc \
        tzdata \
    && ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime \
    && ln -sf /dev/stdout /opt/openresty/nginx/logs/access.log \
    && ln -sf /dev/stderr /opt/openresty/nginx/logs/error.log

ENV PATH=$PATH:/opt/openresty/openssl/bin:/opt/openresty/nginx/sbin:/opt/openresty/bin TZ=Asia/Shanghai

CMD ["/opt/openresty/nginx/sbin/nginx", "-g", "daemon off;"]
```

最后构建
```bash
docker built -t openresty:1.19.9.1 .
```

评分

参与人数 1U点 +100 收起 理由
无知颜 + 100 很给力!

查看全部评分

回复

使用道具 举报

发表于 2022-2-10 17:48:45 | 显示全部楼层
游戏昵称 Gunslinger|U币余额 19833
围观
回复

使用道具 举报

头像被屏蔽
发表于 2022-2-10 18:09:44 | 显示全部楼层
游戏昵称 琉紫璃音|U币余额 165815
李再赣森莫
回复 支持 反对

使用道具 举报

发表于 2022-2-10 21:16:37 | 显示全部楼层
游戏昵称 YZI|U币余额 8803
太牛了,这是啥东西
回复 支持 反对

使用道具 举报

发表于 2022-2-10 22:50:02 | 显示全部楼层
游戏昵称 无知颜|U币余额 17371
在ub你甚至可以学习docker
回复 支持 反对

使用道具 举报

发表于 2022-2-11 02:58:49 | 显示全部楼层
游戏昵称 oboro|U币余额 59792
看不懂
回复

使用道具 举报

发表于 2022-2-11 13:33:30 | 显示全部楼层
游戏昵称 提鸭马特|U币余额 21263
回复

使用道具 举报

发表于 2022-2-11 18:26:16 来自手机 | 显示全部楼层
游戏昵称 鱼卵掉下去|U币余额 644
我还以为我在csdn
回复 支持 反对

使用道具 举报

发表于 2022-2-18 22:10:06 | 显示全部楼层
游戏昵称 永远喜欢山田凉小姐|U币余额 3847
很好,看个文像是在坐牢
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|UB游戏社区 ( 闽ICP备2021016118号-1 )

GMT+8, 2024-11-23 15:58

Powered by Discuz! X3.5

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表