Appearance
Docker 部署
作为一种非常省事的打包方案,docker 被广泛的应用到了各种领域,其中就包括了迁移各种屎山依赖的软件。启动容器已经成了在软件领域几乎必备的技能了,但是在如何在一个没有公网环境下的服务器安装 docker 并迁移一个服务仍然是一个挑战
Docker 安装
首先,你要面对的问题就是服务器没有 docker,甚至可能没有网...
在线安装
怎么说话的,没有挑战性的东西!
bash
apt remove docker-ce # 删除docker,如果有的话
curl -fsSL https://get.docker.com | bash -s docker --mirror Aliyun # 使用官方脚本安装
离线安装
首先,先看看你的机器是什么架构,什么版本的
bash
cat /proc/version # 看看版本
# cat /etc/os-release # 看看目录下的release note到底是啥
比如说我要安装的机器就是 x64 架构、centos 7.4 系统、内核版本为 3.10.0 的配置
然后去官网下载对应的包: https://download.docker.com/linux
一般来说会显示很多包,该下哪一个呢?我建议是直接下载名称带 docker-ce 的包,它是我们要安装的主包。然后使用 apt / yum / pacman install 一下
你说什么?报错了,那就对了!你把官网给的全部包都下载下来后都还是缺依赖,也没有一个完全可用的环境。所以你需要根据提示的依赖逐层递进,去下载对应的包。如果 docker 的官方仓库没有,可以去看看发行版的官方仓库
12 个包!我陆续下载了 12 个!
text
# 先解决没有依赖问题的散包
docker-compose-plugin
docker-buildx-plugin
docker-scan-plugin
# 非docker官方镜像的依赖
container-selinux # containerd.io的依赖
fuse3-lib # fuse-overlayfs的依赖
fuse-overlayfs # docker-ce-rootless-extras的依赖
slirp4netns # docker-ce-rootless-extras的依赖
# 再来解决了前置依赖的包
docker-ce-cli
docker-ce-selinux
containerd.io
# 这俩主包需要一起装,不然会有循环依赖
docker-ce
docker-ce-rootless-extras
docker 命令
一个最简单的 docker 命令就是 docker run 镜像名,但是参数就很复杂了。我这里参照官方的 help 稍微精简并汉化了说明
bash
docker run --help
Usage: docker run [可选选项] 镜像名 [可选命令] [可选命令参数]
Options:
-d, --detach 在后台运行容器并显示容器ID
--dns list 自定义容器DNS
-e, --env list 配置环境变量
-i, --interactive 接收终端输入
-m, --memory bytes 配置内存用量
--name string 配置镜像名
-p, --publish list 映射容器端口,容器外端口:容器内端口
--restart string 配置容器重启策略,默认不重启
--rm 容器退出后自动删除
-t, --tty 启动虚拟终端
-u, --user string 配置容器内运行程序的用户
-v, --volume list 挂载主机上的目录到容器内
举几个常见的例子
bash
# 临时起一个容器进行测试。因为需要能够接收输入,所以加入了-it参数
docker run --name=test -it debian /bin/bash
# 启动一个nginx镜像并在后台运行。映射了所需的端口和配置文件
docker run --name web -p 80:80 -p 443:443 -v ./config:/config -itd nginx
顺带介绍一些常用的命令
bash
docker search 镜像 # 搜索镜像
docker images # 查看本地镜像列表
docker image rm 镜像名 # 删除镜像
docker start 容器名 # 启动停止的容器
docker ps -a # 查看当前所有的容器
docker attach 容器名 # 进入某个容器,通常用于操控容器内运行的程序,需要配合-it参数
docker exec -it 容器名 命令 # 进入某个容器并执行命令,一般用于获取容器内的shell权限或者执行命令
docker system prune # 删除所有未使用的缓存
将应用打包成 docker 镜像
尝试了一下,其实打包熟练了之后非常简单,就是有一些小坑要注意。尤其是打包镜像时可能由于网络或其他原因需要换源,需要避开 >
这样改变输入的符号,不然可能后面的命令就无法执行。还有就是相当于自动化脚本,像是 apt,yum 这些如果需要确认的必须加 -y
这种同意直接执行的命令
dockerfile
# 基础镜像,必须在第一行
FROM debian:12
# 镜像的标签
LABEL authors="hqshi" env="test"
# 环境变量
ENV local="china" version="test"
# 只在构建时存在的环境变量
ARG build="dev"
# 挂载数据卷
VOLUME /data
# 用户:用户组
USER root:root
# 工作路径,填写绝对路径
WORKDIR /data
# 复制文件到镜像内部
COPY test.py /data
# 运行命令以准备环境,也许需要替换镜像源并安装更多内容(常用工具)
RUN sed -i 's/deb.debian.org/mirrors.tuna.tsinghua.edu.cn/g' /etc/apt/sources.list.d/debian.sources && apt update && apt install python3 python3-pip procps -y
# 启动时运行的命令
CMD python3 test.py
compose 编排
传统 docker 启动容器的方式是使用命令行,该方式无法一次性启动多个服务,也不方便与容器的维护。compose 命令的出现则改变了这一点,通过一个名为 compose.yml 的文件,可以更方便的定制容器运行和编组方案。也便于在升级时重新拉取镜像,而不是回忆半天命令行是怎么写的
bash
docker compose up -d # 拉取并在后台运行服务
docker compose down # 停止服务并销毁相关的网络和容器
docker compose pull # 仅下载服务镜像,在重建容器前先拉取镜像,减少由于下载镜像导致的服务中断时间
一个典型的 docker-compose.yml 文件内容如下
yml
version: "3" # 版本
networks: # 指定网络方案,docker自带了nat的bridge模式和使用宿主网络的host模式
gitea:
name: gitea # 指定网络名称
ipam:
config:
- subnet: 172.24.0.0/24 # 指定子网范围
services:
gitea:
image: gitea/gitea # 默认镜像源是dockerhub,可以指定其他镜像源
container_name: gitea
user: "1000:1000" # 指定运行程序的用户
environment: # 配置环境变量
- USER_UID=1000
- USER_GID=1000
restart: always # 重启方式
privileged: true # 允许特权模式
stdin_open: true # 接收stdin输入
tty: true # 打开一个伪终端
command: ps -aux # 自定义启动命令
devices: # 设备映射
- "/dev/sda:/dev/sda"
dns: # 配置dns
- 1.1.1.1
- 8.8.8.8
networks:
gitea:
ipv4_address: 172.24.0.8 # 指定固定IP,部分需要内部组网的服务需要使用
volumes: # 磁盘映射 外部:内部
- /data/gitea:/data
ports: # 端口映射 外部:内部
- "2222:2222"