前言 链接到标题

本文主要介绍内容如下:

  • 如何使用 hub.docker.com
  • 如何基于 Docker 官方提供的 centos 镜像构建系统基础镜像。
  • 如何构建 Nodejs Base (Node.js + NPM + PM2) 镜像。
  • 使用 Nodejs Base 镜像,构建并启动 Koa 容器服务。
  • 使用 Systemd,实现容器中的 Koa 服务开机启动。

一,使用 Docker Hub 链接到标题

1.1. 注册 Docker 账号 链接到标题

使用任意邮箱注册 Docker 账号。点击开始注册 blog/20201115103341_9383b768527cb815bddfffc969a88c03.png

1.2. 关联 Github 账号 链接到标题

Docker 账号可以关联 Github 账号,进而借助 Github Webhooks 能力,实现镜像自动构建。点击开始关联 blog/20201115103711_fc6de812ecb82abea5da1ca05355809b.png

1.3. 新建镜像仓库 链接到标题

blog/20201115104639_d4c0c485a9585f174007674618543541.png

1.4. 配置自动构建 链接到标题

Docker Hub 镜像仓库关联 Github 仓库后,可配置监听分支或 Tag 的改变实现 Docker 镜像自动构建。 blog/20201115104830_e06d333481c3c721491d698a6aa4a39b.png

blog/20201115104908_2401f07d9475c623b1bd4643767f7a82.png

1.5. 构建状态 链接到标题

blog/20201115105259_54cd439e601522ef3cf50cbb6e069b79.png

二,构建系统基础镜像 链接到标题

2.1. Dockerfile 链接到标题

Docker 官方提供的 centos:7centos:latest 基础容器中都包含 Systemd,但默认情况下它不处于活动状态。为了使用 systemd,将需要包含类似于以下示例 Dockerfile 的配置。该 Dockerfile 删除了若干可能导致问题的文件。

FROM centos:7
ENV container docker
# 删除了若干可能导致问题的文件
RUN (cd /lib/systemd/system/sysinit.target.wants/; for i in *; do [ $i == \
systemd-tmpfiles-setup.service ] || rm -f $i; done); \
rm -f /lib/systemd/system/multi-user.target.wants/*;\
rm -f /etc/systemd/system/*.wants/*;\
rm -f /lib/systemd/system/local-fs.target.wants/*; \
rm -f /lib/systemd/system/sockets.target.wants/*udev*; \
rm -f /lib/systemd/system/sockets.target.wants/*initctl*; \
rm -f /lib/systemd/system/basic.target.wants/*;\
rm -f /lib/systemd/system/anaconda.target.wants/*;
VOLUME [ "/sys/fs/cgroup" ]
# Centos7 版本启动使用 systemd
CMD [ "/usr/sbin/init" ]

该系统基础镜像已托管到 Github点击查看

2.2. 构建镜像 链接到标题

使用一,使用 Docker Hub描述的方法,构建镜像。点击查看系统基础镜像仓库

blog/20201115112426_dfa202b0ec73851fb6c0e888a963b15b.png

2.3. 拉取镜像 链接到标题

$ docker push yorkyucn/docker-centos-base-image:latest

三,构建Nodejs Base 链接到标题

使用 Node.js 二进制安装包与 yorkyucn/docker-centos-base-image 构建 Nodejs Base 镜像。

3.1. 下载 Node.js 链接到标题

下载 Node.js 二进制安装包,点击进入下载页面,选择需要的版本。 blog/20201115125612_820906595be8996611a072240877f80d.png

点击下载 node-v12.19.0-linux-x64.tar.xz

3.2. 新建 Github 项目 链接到标题

项目包含 node-v12.19.0-linux-x64.tar.xz 安装包与 Dockerfile 文件,项目结构如下所示:

blog/20201115132531_817d3047fc3eb79d4881753e7575bf6c.png

点击查看 yorkiyu/docker-nodejs-base-image

3.3. Dockerfile 链接到标题

yorkyucn/docker-nodejs-base-image 镜像的 Dockerfile 如下

FROM yorkyucn/docker-centos-base-image:latest 

LABEL maintainer="yorkyu.cn"

# 配置 Node.js 版本信息 
ENV NODE_VERSION="v12.19.0" \
    NODE_DISTRO="linux-x64"

# 解压 Node.js
ADD "./lib/node-${NODE_VERSION}-${NODE_DISTRO}.tar.xz" /usr/local/services/
# 配置 Node.js 运行环境变量,使命令行可运行 node/npm 命令
ENV PATH="/usr/local/services/node-${NODE_VERSION}-${NODE_DISTRO}/bin:${PATH}"

# 安装 pm2
RUN npm install pm2 -g

3.4. 构建镜像 链接到标题

使用一,使用 Docker Hub描述的方法,构建镜像。点击查看系统基础镜像仓库

blog/20201115133119_fc9fc5d2c06d98c5f98aab39db314875.png

3.5. 拉取镜像 链接到标题

$ docker pull yorkyucn/docker-nodejs-base-image:latest

3.6. 验证镜像 链接到标题

# 启动容器
$ docker run -d yorkyucn/docker-nodejs-base-image:latest
# 进入容器 
$ docker exec -it cd10ab4f9c51 /bin/bash

blog/20201115133537_bc5dbcd1108151b925824a10e2de61c3.png

四,构建 Koa 应用 链接到标题

基于 yorkyucn/docker-nodejs-base-image 镜像,构建 koa 应用的镜像 demo

4.1. 新建 Github 项目 链接到标题

新建 koa 应用项目。其目录结构如下图: blog/20201121122854_e09c356023420b3bb6968d2d947a4419.png

  • app.js 入口文件
  • ecosystem.config.js pm2 配置文件
  • koa.service systemd 服务配置文件
  • Dockerfile 镜像构建配置

点击查看 docker-nodejs-base-koa-demo 项目源码

4.2. Dockerfile 链接到标题

由于 docker-centos-base-image 系统基础镜像已经使用了 1 号进程,所以应用镜像不建议使用 CMD/ENTRYPOINT 运行启动命令。会导致覆盖系统基础镜像已经使用了 1 号进程的 systemd 服务。

可以参考下述 Dockerfile,新建了 systemd 服务 koa-service,并配置开机启动服务。

FROM yorkyucn/docker-nodejs-base-image:latest 

# 暴露端口
EXPOSE 8080

WORKDIR /data/release/docker-nodejs-base-koa-demo

# 创建目录
RUN mkdir -p /data/release/docker-nodejs-base-koa-demo

# 复制源码
COPY . /data/release/docker-nodejs-base-koa-demo

# 将服务koa.service,拷贝到 systemd
COPY ./koa.service /etc/systemd/system

# 设置可执行权限
RUN chmod +x /etc/systemd/system/koa.service

# 设置 koa.service 开机启动
RUN ln -s /etc/systemd/system/koa.service /etc/systemd/system/multi-user.target.wants

4.3. 配置 koa.service 链接到标题

使用 systemd 启动应用,点击查看配置 koa.service

#!/bin/bash
# 服务说明
[Unit]
# 服务描述
Description=pm2 start docker-nodejs-base-koa-demo
# 前置需要启动的服务
After=sysinit.target

# 服务启动行为
[Service]
# 服务类型
Type=simple
# 服务启动
ExecStart=/usr/local/services/node-v12.19.0-linux-x64/bin/pm2-runtime start /data/release/docker-nodejs-base-koa-demo/ecosystem.config.js --only docker-nodejs-base-koa-demo --env production
# 服务重启
ExecReload=
# 服务停止
ExecStop=
# 设置预加载变量
Environment="PATH=/usr/local/services/node-v12.19.0-linux-x64/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
# 执行用户
User=root
# 执行用户组
Group=root
WorkingDirectory=/data/release/docker-nodejs-base-koa-demo

# 服务开机启动安装目标
[Install]
# 表示该服务所在的 Target
WantedBy=multi-user.targe

4.4. 构建镜像 链接到标题

使用 一,使用 Docker Hub 描述的方法,构建镜像。 点击查看 Demo 镜像

blog/20201121123507_606ab97ff0cc7107689de53ed50284f4.png

五,启动 Demo 容器 链接到标题

5.1. 启动容器 链接到标题

# 拉取镜像
$ docker pull yorkyucn/docker-nodejs-base-koa-demo:latest

# 启动容器
$ docker run -d -p 8080:8080 --privileged yorkyucn/docker-nodejs-base-koa-demo:latest

--privileged,使用该参数,container 内的 root 拥有真正的 root 权限。可以看到很多 host 上的设备,并且可以执行 mount。才可以正常启动 systemd 服务管理

5.2. 进入容器 链接到标题

# 查看容器
$ docker ps
# 进入容器
$ docker exec -it 1ad44142b083 /bin/bash

blog/20201121124236_b31f8d30b77fc57f94a3acc20d5be310.png

blog/20201121124402_9b8f53e47665ea25e3bac9ad4268b1a9.png

5.3. 查看启动应用 链接到标题

进入容器后,查看 Koa 应用。

# 运行 systemd 命令,查看服务状态
$ systemctl status koa.service 

# 运行 pm2 命令,查看启动进程
$ pm2 ls

blog/20201121124609_b3b4e92cd050647da797e870393cefb0.png

blog/20201121124733_8173150b8210e3ec65bf96bcf8fdc3d6.png

参考 链接到标题