layout: post
title: “中间件服务部署-Docker版”
description: “分享”
tag: Docker


0、注意事项

1、权限回收(rabbitmq建议使用命令方式创建用户等信息)

2、严禁使用localhost

3、生产环境常见问题:没有网络、没有yum命令等

1、MySQL

  1. docker pull mysql:5.7
  2. docker pull redis:7.0.0
  3. docker pull rabbitmq:management
  4. docker pull elasticsearch:7.2.0
  5. docker pull nginx:1.19.10-alpine
  1. # 创建目录
  2. mkdir /docker/mysql/{etc,data,logs} -p
  3. # 如果已经存在,清空
  4. rm -rf /docker/mysql/{etc,data,logs}/*
  5. # 创建配置文件
  6. vim /docker/mysql/etc/mysqld.cnf
  7. [mysqld]
  8. pid-file = /var/run/mysqld/mysqld.pid
  9. socket = /var/run/mysqld/mysqld.sock
  10. datadir = /var/lib/mysql
  11. #log-error = /var/log/mysql/error.log
  12. # By default we only accept connections from localhost
  13. #bind-address = 127.0.0.1
  14. # Disabling symbolic-links is recommended to prevent assorted security risks
  15. symbolic-links=0
  16. # mysql日志时间跟随系统时间
  17. log_timestamps=system
  18. character-set-server=utf8
  19. vim /docker/mysql/etc/mysql.cnf
  20. [mysql]
  21. default-character-set=utf8
  22. # 启动日志
  23. docker run -d -p 3306:3306 --name=mysql -v "/docker/mysql/etc/mysqld.cnf":"/etc/mysql/mysql.conf.d/mysqld.cnf" --mount type=bind,src=/docker/mysql/data,dst=/var/lib/mysql \
  24. -v mysql-logs:/var/log/mysql/ \
  25. -e TZ=Asia/Shanghai \
  26. -e MYSQL_ROOT_PASSWORD=Geray@2022 \
  27. --restart always mysql:5.7

-v:挂载配置文件到容器中

—mount:将数据文件从容器中映射到本地

-e TZ=Asia/Shanghai:设置容器中的系统时区

-e MYSQL_ROOT_PASSWORD=Geray@2022:设置mysql密码

—restart always :设置容器的重启策略

修改mysql数据库编码:

  1. # 查看编码
  2. docker exec -it mysql mysql -uroot -p
  3. mysql> show variables like '%char%';
  4. +--------------------------+----------------------------+
  5. | Variable_name | Value |
  6. +--------------------------+----------------------------+
  7. | character_set_client | latin1 |
  8. | character_set_connection | latin1 |
  9. | character_set_database | latin1 |
  10. | character_set_filesystem | binary |
  11. | character_set_results | latin1 |
  12. | character_set_server | latin1 |
  13. | character_set_system | utf8 |
  14. | character_sets_dir | /usr/share/mysql/charsets/ |
  15. +--------------------------+----------------------------+
  16. 8 rows in set (0.00 sec)
  17. mysql>
  18. # 修改编码:(修改配置文件mysqld : character-set-server=utf8)
  19. # 添加mysql的[mysql]组文件挂载并重新配置容器启动查看
  20. [mysql]
  21. default-character-set=utf8
  22. # 启动日志
  23. docker run -d -p 3306:3306 --name=mysql -v "/docker/mysql/etc/mysqld.cnf":"/etc/mysql/mysql.conf.d/mysqld.cnf" -v "/docker/mysql/etc/mysql.cnf":"/etc/mysql/conf.d/mysql.cnf" --mount type=bind,src=/docker/mysql/data,dst=/var/lib/mysql \
  24. -e TZ=Asia/Shanghai \
  25. -e MYSQL_ROOT_PASSWORD=Geray@2022 \
  26. --restart always mysql:5.7
  27. mysql> show variables like '%char%';
  28. +--------------------------+----------------------------+
  29. | Variable_name | Value |
  30. +--------------------------+----------------------------+
  31. | character_set_client | utf8 |
  32. | character_set_connection | utf8 |
  33. | character_set_database | utf8 |
  34. | character_set_filesystem | binary |
  35. | character_set_results | utf8 |
  36. | character_set_server | utf8 |
  37. | character_set_system | utf8 |
  38. | character_sets_dir | /usr/share/mysql/charsets/ |
  39. +--------------------------+----------------------------+
  40. 8 rows in set (0.01 sec)

创建用户并授权

  1. CREATE USER 'username'@'host' IDENTIFIED BY 'password';
  2. # 创建用户
  3. CREATE USER 'ump'@'%' IDENTIFIED BY 'Gsww_2022';
  4. FLUSH PRIVILEGES;
  • username:你将创建的用户名
  • host:指定该用户在哪个主机上可以登陆,如果是本地用户可用localhost,如果想让该用户可以从任意远程主机登陆,可以使用通配符%
  • password:该用户的登陆密码,密码可以为空,如果为空则该用户可以不需要密码登陆服务器
  1. GRANT privileges ON databasename.tablename TO 'username'@'host'
  2. # 授权
  3. GRANT ALL ON *.* TO 'ump'@'%';
  4. FLUSH PRIVILEGES;
  • privileges:用户的操作权限,如SELECTINSERTUPDATE等,如果要授予所的权限则使用ALL
  • databasename:数据库名
  • tablename:表名,如果要授予该用户对所有数据库和表的相应操作权限则可用*表示,如*.*

更简单的Podman

  1. podman run --name mysql-server -t \
  2. -e MYSQL_DATABASE="zabbix" \
  3. -e MYSQL_USER="aa" \
  4. -e MYSQL_PASSWORD="cc" \
  5. -e MYSQL_ROOT_PASSWORD="cc" \
  6. -v /data/zabbix/:/var/lib/mysql/:Z \
  7. --restart=always \
  8. --pod=zabbix \
  9. -d mysql:8.0 \
  10. --character-set-server=utf8 --collation-server=utf8_bin \
  11. --default-authentication-plugin=mysql_native_password

2、Redis

redis.conf(7.0.0模板)

  1. #删除注释行和空行
  2. sed -i '/^#/d;/^$/d' redis.conf
  1. cat > /docker/redis/conf/redis.conf << EOF
  2. #bind 127.0.0.1 -::1 # 注释掉
  3. protected-mode yes
  4. port 6379
  5. tcp-backlog 511
  6. timeout 0
  7. tcp-keepalive 300
  8. daemonize no
  9. pidfile /var/run/redis_6379.pid
  10. loglevel notice
  11. logfile ""
  12. databases 16
  13. always-show-logo no
  14. set-proc-title yes
  15. proc-title-template "{title} {listen-addr} {server-mode}"
  16. stop-writes-on-bgsave-error yes
  17. rdbcompression yes
  18. rdbchecksum yes
  19. dbfilename dump.rdb
  20. rdb-del-sync-files no
  21. dir ./
  22. replica-serve-stale-data yes
  23. replica-read-only yes
  24. repl-diskless-sync yes
  25. repl-diskless-sync-delay 5
  26. repl-diskless-sync-max-replicas 0
  27. repl-diskless-load disabled
  28. repl-disable-tcp-nodelay no
  29. replica-priority 100
  30. acllog-max-len 128
  31. lazyfree-lazy-eviction no
  32. lazyfree-lazy-expire no
  33. lazyfree-lazy-server-del no
  34. replica-lazy-flush no
  35. lazyfree-lazy-user-del no
  36. lazyfree-lazy-user-flush no
  37. oom-score-adj no
  38. oom-score-adj-values 0 200 800
  39. disable-thp yes
  40. appendonly no
  41. appendfilename "appendonly.aof"
  42. appenddirname "appendonlydir"
  43. appendfsync everysec
  44. no-appendfsync-on-rewrite no
  45. auto-aof-rewrite-percentage 100
  46. auto-aof-rewrite-min-size 64mb
  47. aof-load-truncated yes
  48. aof-use-rdb-preamble yes
  49. aof-timestamp-enabled no
  50. slowlog-log-slower-than 10000
  51. slowlog-max-len 128
  52. latency-monitor-threshold 0
  53. notify-keyspace-events ""
  54. hash-max-listpack-entries 512
  55. hash-max-listpack-value 64
  56. list-max-listpack-size -2
  57. list-compress-depth 0
  58. set-max-intset-entries 512
  59. zset-max-listpack-entries 128
  60. zset-max-listpack-value 64
  61. hll-sparse-max-bytes 3000
  62. stream-node-max-bytes 4096
  63. stream-node-max-entries 100
  64. activerehashing yes
  65. client-output-buffer-limit normal 0 0 0
  66. client-output-buffer-limit replica 256mb 64mb 60
  67. client-output-buffer-limit pubsub 32mb 8mb 60
  68. hz 10
  69. dynamic-hz yes
  70. aof-rewrite-incremental-fsync yes
  71. rdb-save-incremental-fsync yes
  72. jemalloc-bg-thread yes
  73. requirepass Gsww_2022
  74. EOF
  1. mkdir -p /docker/redis/{conf,data}
  2. # 通过docker inspect redis命令查看镜像中的redis版本和使用的软件包来下载获取对应版本的配置文件
  3. # 修改配置文件
  4. requirepass Gsww_2022 #密码
  5. #bind 127.0.0.1 #注释掉(或者修改为0.0.0.0)
  6. protected-mode yes #启用保护模式
  1. # 添加域名解析
  2. vim /etc/hosts
  3. # GitHub Start
  4. 52.74.223.119 github.com
  5. 192.30.253.119 gist.github.com
  6. 54.169.195.247 api.github.com
  7. 185.199.111.153 assets-cdn.github.com
  8. 151.101.76.133 raw.githubusercontent.com
  9. 151.101.108.133 user-images.githubusercontent.com
  10. 151.101.76.133 gist.githubusercontent.com
  11. 151.101.76.133 cloud.githubusercontent.com
  12. 151.101.76.133 camo.githubusercontent.com
  13. 151.101.76.133 avatars0.githubusercontent.com
  14. 151.101.76.133 avatars1.githubusercontent.com
  15. 151.101.76.133 avatars2.githubusercontent.com
  16. 151.101.76.133 avatars3.githubusercontent.com
  17. 151.101.76.133 avatars4.githubusercontent.com
  18. 151.101.76.133 avatars5.githubusercontent.com
  19. 151.101.76.133 avatars6.githubusercontent.com
  20. 151.101.76.133 avatars7.githubusercontent.com
  21. 151.101.76.133 avatars8.githubusercontent.com
  22. # GitHub End
  1. docker run -d -v /docker/redis/conf/:/etc/redis/ -v /docker/redis/data:/data --privileged=true -p 6379:6379 --restart always -e TZ=Asia/Shanghai --name redis redis:7.0.0 redis-server /etc/redis/redis.conf --appendonly yes

包含您的文件/docker/redis/conf/的本地目录在哪里。redis.conf使用这种方法意味着您不需要为您的 redis 容器提供 Dockerfile。

映射目录应该是可写的,因为根据配置和操作模式,Redis 可能需要创建额外的配置文件或重写现有的配置文件。

  1. # 测试
  2. docker exec -it redis redis-cli

3、Rabbitmq

配置文件:

  1. cat > /docker/rabbitmq/conf/rabbitmq-env.conf << EOF
  2. RABBITMQ_NODENAME=rabbitmq001
  3. #RABBITMQ_NODE_IP_ADDRESS=192.168.6.21
  4. RABBITMQ_NODE_PORT=5672
  5. #RABBITMQ_MNESIA_BASE=/opt/rabbitmq/data
  6. #RABBITMQ_LOG_BASE=/var/log
  7. EOF
  8. cat > /docker/rabbitmq/conf/rabbitmq.config <<EOF
  9. [
  10. {rabbit,
  11. [
  12. {tcp_listeners, [5672]},
  13. {dump_log_write_threshold, [1000]},
  14. {vm_memory_high_watermark, 0.5},
  15. {disk_free_limit, "200MB"},
  16. {hipe_compile,true}
  17. ]
  18. }
  19. ].
  20. EOF
  1. mkdir -p /docker/rabbitmq/{conf,data,logs}
  2. rm -rf /docker/rabbitmq/{data,logs}/*
  3. docker run -d --name rabbitmq -p 15672:15672 -p 5672:5672 -v /docker/rabbitmq/conf:/opt/rabbitmq/etc/rabbitmq -v /docker/rabbitmq/data:/var/lib/rabbitmq -e RABBITMQ_DEFAULT_USER=admin -e RABBITMQ_DEFAULT_PASS=Geray@2022 -v /etc/localtime:/etc/localtime:ro --restart always rabbitmq:management
  4. docker exec -it rabbitmq bash

配置账号密码

  1. # 创建账号和密码(用户存在可以跳过改步骤)
  2. docker exec -it rabbitmq rabbitmqctl add_user admin Geray_2022
  3. # 设置用户角色
  4. docker exec -it rabbitmq rabbitmqctl set_user_tags admin administrator
  5. # 设置用户权限
  6. # 用户 user_admin 具有/vhost1 这个 virtual host 中所有资源的配置、写、读权限
  7. # 格式:set_permissions [-p <vhostpath>] <user> <conf> <write> <read>
  8. # 给/这个vhost设置了admin权限
  9. docker exec -it rabbitmq rabbitmqctl set_permissions -p "/" admin ".*" ".*" ".*"
  10. # 更改密码
  11. docker exec -it rabbitmq rabbitmqctl change_password admin Gsww_2022
  12. # 当前用户和角色
  13. docker exec -it rabbitmq rabbitmqctl list_users

追加启动策略

  1. # 查看容器启动时间
  2. docker inspect -f "{{ .State.StartedAt }}" rabbitmq
  3. # 重启次数
  4. docker inspect -f "{{ .RestartCount }}" rabbitmq
  5. # 重启策略
  6. docker inspect rabbitmq | grep -i -A 3 restartPolicy
  7. # 重新设置容器的重启策略
  8. docker container update --restart=always rabbitmq

4、ES

1. 优化系统:

  1. # 设置虚拟内存大小,Elasticsearch使用了 NioFs(非阻塞文件系统)和 MMapFs(内存映射文件系统)。
  2. # 配置最大映射数量,以便有足够的虚拟内存可用于mmapped文件
  3. echo "vm.max_map_count=262144" >> /etc/sysctl.conf
  4. # 禁止内存与硬盘交换
  5. echo "vm.swappiness=1" >> /etc/sysctl.conf
  6. # 是配置生效
  7. sysctl -p

es至少需要的内存权限为:262144,默认用户的内存权限为:65530

修改该配置是为了防止es在启动时出现下面的错误

  1. max virtual memory areas vm.max_map_count [65530] is too low, increase to at least [262144]

创建es账号

es不能使用root账号启动

  1. useradd es
  2. passwd es

2. 启动

  1. docker pull elasticsearch:7.2.0
  2. #启动镜像
  3. docker run -d --name es \
  4. -v es-conf:/usr/share/elasticsearch/config/ \
  5. -v es-data:/usr/share/elasticsearch/data/ \
  6. -v es-log:/usr/share/elasticsearch/logs/ \
  7. -v es-plugins:/usr/share/elasticsearch/plugins/ \
  8. -v /etc/localtime:/etc/localtime:ro \
  9. -e ES_JAVA_OPTS="-Xms512m -Xmx512m" \
  10. -e "discovery.type=single-node" \
  11. -e TZ=Asia/Shanghai \
  12. -p 9200:9200 -p 9300:9300 \
  13. --restart=always \
  14. elasticsearch:7.2.0

ES_JAVA_OPTS设置了ES的启动内存,自己按需修改
discovery.type=single-node表示该es为单节点,不加这个的话,你的es健康状态会显示为黄色

3. 修改配置文件

  1. # 添加配置文件
  2. cat > /var/lib/docker/volumes/es-conf/_data/elasticsearch.yml << EOF
  3. # 集群名
  4. cluster.name: docker-cluster-es
  5. # 节点名
  6. node.name: node
  7. # 监听ip
  8. network.host: 0.0.0.0
  9. # 开启x-pack插件,用于添加账号密码
  10. xpack.security.enabled: true
  11. EOF

修改JVM内存参数(本地环境资源有限)

生产环境建议配置物理内存的50%,但不要超过32G

  1. sed -i "s/Xms1g/Xms512m/g" /var/lib/docker/volumes/es-conf/_data/jvm.options
  2. sed -i "s/Xmx1g/Xmx512m/g" /var/lib/docker/volumes/es-conf/_data/jvm.options

4. 重启容器

  1. docker restart es

5. 设置密码

  1. # 交互式配置密码
  2. docker exec -it es elasticsearch-setup-passwords interactive

根据提示,先输入y,然后输入密码,这里会要求输入多次,主要是需要给好几个系统添加密码,用户默认elastic(Gsww_2022)

测试访问:http://192.168.6.22:9200

5、Nginx

  1. docker pull nginx:1.19.10-alpine
  2. docker run -d --name nginx \
  3. -p 80:80 \
  4. -v nginx-conf:/etc/nginx/ \
  5. -v nginx-data:/usr/share/nginx/ \
  6. -e TZ=Asia/Shanghai \
  7. --restart=always \
  8. nginx:1.19.10-alpine

6、Dockerfile

1. jdk

  1. FROM alpine:latest
  2. #MAINTAINER "Geray <1690014753@qq.com>"
  3. # 打标签
  4. LABEL version="1.0" \
  5. description="alpine:latest" \
  6. maintainer="geray<1690014753@qq.com>"
  7. # 配置apk包加速镜像为阿里
  8. RUN sed -i 's/dl-cdn.alpinelinux.org/mirrors.aliyun.com/g' /etc/apk/repositories
  9. RUN apk update \
  10. # && apk add s6 \
  11. # && apk add nghttp2-dev \
  12. && apk add ca-certificates \
  13. && apk add wget \
  14. # && apk add curl \
  15. # && apk add tcpdump \
  16. # && apk add bash-completion \
  17. # && apk add iputils \
  18. # && apk add iproute2 \
  19. && apk add libc6-compat \
  20. && apk add -U tzdata \
  21. && rm -rf /var/cache/apk/* \
  22. # 设置操作系统时区
  23. && rm -rf /etc/localtime \
  24. && ln -s /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
  25. # 设置时区变量
  26. ENV TIME_ZONE Asia/Shanghai
  27. # 设置 语言支持
  28. ENV LANG=zh_CN.UTF-8
  29. # 配置 应用工作目录
  30. WORKDIR /data/
  31. VOLUME /data/
  32. COPY jdk1.8.0_281/ /data/
  33. # 设置jdk环境变量
  34. ENV JAVA_VERSION=1.8.0_281 \
  35. JAVA_HOME=/data/jdk1.8.0_281 \
  36. JRE_HOME=$JAVA_HOME/jre \
  37. CLASSPATH=.:${JAVA_HOME}/jre/lib/rt.jar:${JAVA_HOME}/lib/dt.jar:${JAVA_HOME}/lib/tools.jar \
  38. PATH=$PATH:${JAVA_HOME}/bin
  39. # 配置 对外端口
  40. #EXPOSE 11000
  41. # 设置启动时预期的命令参数, 可以被 docker run 的参数覆盖掉.
  42. #CMD ["bash", "sleep 20m"]

zip glibc 是GNU发布的libc库,即c运行库。. glibc 是linux系统中最底层的api,几乎其它任何运行库都会依赖于 glibc, 在制作docker alpine镜像可以需要用到他.(docker官方推荐java是基于glibc库,而alpine默认只提供mini libc,故需要安装glibc库)

下载glibc安装包glibc-2.29-r0.apkglibc-bin-2.29-r0.apkglibc-i18n-2.29-r0.apk到文件夹下,下载地址:

https://github.com/sgerrand/alpine-pkg-glibc/releases

构建:

  1. docker build -t jdk:1.8-alpine .
名称 说明 实例
s6 s6是一个unix服务管理器(更像runit和supervisord)。 虽然Docker容器应该有一个明确的焦点,但通常情况下,您需要在容器中运行多个进程。 consur就是一个很好的例子;您需要consur代理来加入consur集群和主服务. 如Nginx或js节点. 日志管理也是可能需要运行另一个进程的一个关键考虑因素。
iputils iputils软件包是Linux
环境下一些实用的网络工具的集合
iproute2 iproute2是linux下管理控制TCP/IP网络和流量控制的新一代工具包,旨在替代老派的工具链net-tools,即大家比较熟悉的ifconfig,arp,route,netstat等命令。
libc6-compat 这个包提供了一个轻量级的glibc兼容层。对于简单的应用程序,这可能就足够了。
ca-certificates 我们在构建 docker
镜像时一般使用的是 alpine linux
系统,默认是不带 ca-certificates
根证书的,导致无法识别外部 https 携带的数字证书。

附件:镜像加速

  1. cat > /etc/docker/daemon.json << EOF
  2. {
  3. "registry-mirrors": [
  4. "https://hub-mirror.c.163.com",
  5. "https://mirror.baidubce.com",
  6. "https://docker.mirrors.ustc.edu.cn",
  7. "https://3fc19s4g.mirror.aliyuncs.com"
  8. ]
  9. }
  10. EOF