07Docker容器化部署企业级应用集群

61 阅读15分钟

Docker容器化部署企业级应用集群

使用Docker容器化部署企业级应用必要性

  • 有利于快速实现企业级应用部署
  • 有利于快速实现企业级应用恢复

安装什么镜像以及应该如何安装,都可以到DockerHub上搜索

使用Docker部署Nginx

# 不在宿主机暴露端口
docker run -d --name nginx-server -v /data/test/nginx-server:/usr/share/nginx/html:ro nginx
3379d8d8f4d23883ed546a35139834be52e8a1c90a5056d459969659152e7b67

docker ps
CONTAINER ID   IMAGE     COMMAND                  CREATED          STATUS          PORTS     NAMES
3379d8d8f4d2   nginx     "/docker-entrypoint.…"   31 seconds ago   Up 31 seconds   80/tcp    nginx-server

docker inspect 3379d8d8f4d2 | grep IPAddress
            "SecondaryIPAddresses": null,
            "IPAddress": "172.17.0.2",
                    "IPAddress": "172.17.0.2",

curl http://172.17.0.2
<html>
<head><title>403 Forbidden</title></head>
<body>
<center><h1>403 Forbidden</h1></center>
<hr><center>nginx/1.21.5</center>
</body>
</html>

echo "nginx is working" > /data/test/nginx-server/index.html

curl http://172.17.0.2
nginx is working
# 在宿主机(docker host)暴露18080端口
docker run -d -p 18080:80 --name nginx-server-port -v /data/test/nginx-server-port:/usr/share/nginx/html:ro nginx

docker ps
CONTAINER ID   IMAGE     COMMAND                  CREATED              STATUS              PORTS                                     NAMES
a25518175112   nginx     "/docker-entrypoint.…"   27 seconds ago       Up 27 seconds       0.0.0.0:18080->80/tcp, :::18080->80/tcp   nginx-server-port

echo "nginx is running" > /data/test/nginx-server-port/index.html

docker inspect a25518175112 | grep IPAddress
            "SecondaryIPAddresses": null,
            "IPAddress": "172.17.0.3",
                    "IPAddress": "172.17.0.3",

curl http://172.17.0.3
nginx is running

# 也可以通过宿主机的ip访问
curl http://localhost:18080
nginx is running

docker top nginx-server-port
UID                 PID                 PPID                C                   STIME               TTY                 TIME                CMD
root                50816               50793               0                   08:59               ?                   00:00:00            nginx: master process nginx -g daemon off;
101                 50861               50816               0                   08:59               ?                   00:00:00            nginx: worker process
...
# 挂载配置文件
# 需要创建一个nginx容器,把配置文件复制出来修改后使用
mkdir -p /data/test/nginxcon/
docker cp nginx-server-port:/etc/nginx/nginx.conf /data/test/nginxcon/
ls /data/test/nginxcon/
nginx.conf

docker run -d \
-p 18082:80 --name nginx-server-conf \
-v /data/test/nginx-server-conf:/usr/share/nginx/html:ro \
-v /data/test/nginxcon/nginx.conf:/etc/nginx/nginx.conf:ro \
nginx

docker top nginx-server-conf
UID                 PID                 PPID                C                   STIME               TTY                 TIME                CMD
root                52709               52686               0                   09:21               ?                   00:00:00            nginx: master process nginx -g daemon off;
101                 52766               52709               0                   09:21               ?                   00:00:00            nginx: worker process

使用Docker部署Tomcat

# 暴露端口运行
docker run -d -p 28080:8080 --rm tomcat:9.0

docker ps
CONTAINER ID   IMAGE        COMMAND             CREATED          STATUS          PORTS                                         NAMES
fe042ada3fd3   tomcat:9.0   "catalina.sh run"   29 seconds ago   Up 28 seconds   0.0.0.0:28080->8080/tcp, :::28080->8080/tcp   cranky_bohr

# 也可以通过宿主机的ip访问
curl http://localhost:28080
<!doctype html><html lang="en"><head><title>HTTP Status 404 – Not Found</title>
...

# 里面为空,可以添加网站文件
docker exec fe042ada3fd3 ls /usr/local/tomcat/webapps
# 暴露端口并挂载网站文件
docker run -d -p 28081:8080 -v /data/test/tomcat-server:/usr/local/tomcat/webapps/ROOT tomcat:9.0

docker ps
CONTAINER ID   IMAGE        COMMAND             CREATED          STATUS          PORTS                                         NAMES
f5a00041b23e   tomcat:9.0   "catalina.sh run"   23 seconds ago   Up 22 seconds   0.0.0.0:28081->8080/tcp, :::28081->8080/tcp   cool_napier

echo "tomcat running" > /data/test/tomcat-server/index.html

# 也可以通过宿主机的ip访问
curl localhost:28081
tomcat running

使用Docker部署MySQL

单节点MySQL部署

docker run -p 23306:3306 \
 --name mysql \
 -v /data/test/mysql/log:/var/log/mysql \
 -v /data/test/mysql/data:/var/lib/mysql \
 -v /data/test/mysql/conf:/etc/mysql \
 -e MYSQL_ROOT_PASSWORD=root \
 -d \
 mysql:5.7
 
docker ps
CONTAINER ID   IMAGE       COMMAND                  CREATED         STATUS         PORTS                                                    NAMES
1c110af77128   mysql:5.7   "docker-entrypoint.s…"   6 seconds ago   Up 6 seconds   33060/tcp, 0.0.0.0:23306->3306/tcp, :::23306->3306/tcp   mysql

# 通过容器中客户端访问
docker exec -it mysql mysql -uroot -proot

# 在docker host上访问
mysql -h 127.0.0.1 -uroot -proot -P 23306

MySQL主从复制集群部署

MySQL主节点部署
# 停止并删除上面部署的mysql容器
docker stop mysql
docker remove mysql

docker run -p 23306:3306 \
 --name mysql-master \
 -v /data/test/mysql-master/log:/var/log/mysql \
 -v /data/test/mysql-master/data:/var/lib/mysql \
 -v /data/test/mysql-master/conf:/etc/mysql \
 -e MYSQL_ROOT_PASSWORD=root \
 -d mysql:5.7
 
docker ps
CONTAINER ID   IMAGE       COMMAND                  CREATED         STATUS         PORTS                                                    NAMES
a22fe2169bb5   mysql:5.7   "docker-entrypoint.s…"   7 seconds ago   Up 6 seconds   33060/tcp, 0.0.0.0:23306->3306/tcp, :::23306->3306/tcp   mysql-master
MySQL主节点配置
# 添加 /data/test/mysql-master/conf/my.cnf 这个配置文件,内容如下
[client]
default-character-set=utf8

[mysql]
default-character-set=utf8

[mysqld]
init_connect='SET collation_connection = utf8_unicode_ci'
init_connect='SET NAMES utf8'
character-set-server=utf8
collation-server=utf8_unicode_ci
skip-character-set-client-handshake
skip-name-resolve

server_id=1
log-bin=mysql-bin
read-only=0
# 同步的库
binlog-do-db=test

replicate-ignore-db=mysql
replicate-ignore-db=sys
replicate-ignore-db=information_schema
replicate-ignore-db=performance_schema
MySQL从节点部署
docker run -p 23307:3306 \
 --name mysql-slave \
 -v /data/test/mysql-slave/log:/var/log/mysql \
 -v /data/test/mysql-slave/data:/var/lib/mysql \
 -v /data/test/mysql-slave/conf:/etc/mysql \
 -e MYSQL_ROOT_PASSWORD=root \
 -d \
 --link mysql-master:mysql-master \
 mysql:5.7
 
docker ps
CONTAINER ID   IMAGE       COMMAND                  CREATED              STATUS              PORTS                                                    NAMES
aabf03a1d2ba   mysql:5.7   "docker-entrypoint.s…"   11 seconds ago       Up 10 seconds       33060/tcp, 0.0.0.0:23307->3306/tcp, :::23307->3306/tcp   mysql-slave
a22fe2169bb5   mysql:5.7   "docker-entrypoint.s…"   About a minute ago   Up About a minute   33060/tcp, 0.0.0.0:23306->3306/tcp, :::23306->3306/tcp   mysql-master
MySQL从节点配置
# 添加 /data/test/mysql-slave/conf/my.cnf 这个配置文件,内容如下
[client]
default-character-set=utf8

[mysql]
default-character-set=utf8

[mysqld]
init_connect='SET collation_connection = utf8_unicode_ci'
init_connect='SET NAMES utf8'
character-set-server=utf8
collation-server=utf8_unicode_ci
skip-character-set-client-handshake
skip-name-resolve

server_id=2
log-bin=mysql-bin
read-only=1
binlog-do-db=test

replicate-ignore-db=mysql
replicate-ignore-db=sys
replicate-ignore-db=information_schema
replicate-ignore-db=performance_schema
master节点配置
# 先登录mysql主节点
mysql -h 127.0.0.1 -uroot -proot -P 23306
# 授权
grant replication slave on *.* to 'backup'@'%' identified by '123456';
Query OK, 0 rows affected, 1 warning (0.00 sec)
# 重启容器,使用配置生效
docker restart mysql-master

mysql -h 127.0.0.1 -uroot -proot -P 23306
# 查看状态
show master status\G
*************************** 1. row ***************************
             File: mysql-bin.000001
         Position: 154
     Binlog_Do_DB: test
 Binlog_Ignore_DB: 
Executed_Gtid_Set: 
1 row in set (0.00 sec)
slave节点配置
docker restart mysql-slave
# 登录
mysql -h 127.0.0.1 -uroot -proot -P 23307
# 下面在mysql客户端执行命令
# 添加主节点配置,host与port需要对应起来,这里host使用的是docker --link指定的别名,因此端口需要用容器中mysql的端口
change master to master_host='mysql-master', master_user='backup', master_password='123456', master_log_file='mysql-bin.000001', master_log_pos=154, master_port=3306;
Query OK, 0 rows affected, 2 warnings (0.01 sec)

start slave;
Query OK, 0 rows affected (0.01 sec)

show slave status\G
*************************** 1. row ***************************
               Slave_IO_State: Waiting for master to send event
                  Master_Host: mysql-master
                  Master_User: backup
                  Master_Port: 3306
                Connect_Retry: 60
              Master_Log_File: mysql-bin.000001
          Read_Master_Log_Pos: 154
               Relay_Log_File: aabf03a1d2ba-relay-bin.000002
                Relay_Log_Pos: 320
        Relay_Master_Log_File: mysql-bin.000001
             Slave_IO_Running: Yes
            Slave_SQL_Running: Yes
              Replicate_Do_DB: 
          Replicate_Ignore_DB: mysql,sys,information_schema,performance_schema
           Replicate_Do_Table: 
       Replicate_Ignore_Table: 
      Replicate_Wild_Do_Table: 
  Replicate_Wild_Ignore_Table: 
                   Last_Errno: 0
                   Last_Error: 
                 Skip_Counter: 0
          Exec_Master_Log_Pos: 154
              Relay_Log_Space: 534
              Until_Condition: None
               Until_Log_File: 
                Until_Log_Pos: 0
           Master_SSL_Allowed: No
           Master_SSL_CA_File: 
           Master_SSL_CA_Path: 
              Master_SSL_Cert: 
            Master_SSL_Cipher: 
               Master_SSL_Key: 
        Seconds_Behind_Master: 0
Master_SSL_Verify_Server_Cert: No
                Last_IO_Errno: 0
                Last_IO_Error: 
               Last_SQL_Errno: 0
               Last_SQL_Error: 
  Replicate_Ignore_Server_Ids: 
             Master_Server_Id: 1
                  Master_UUID: dfb4a38b-5063-11ee-bfeb-0242ac110002
             Master_Info_File: /var/lib/mysql/master.info
                    SQL_Delay: 0
          SQL_Remaining_Delay: NULL
      Slave_SQL_Running_State: Slave has read all relay log; waiting for more updates
           Master_Retry_Count: 86400
                  Master_Bind: 
      Last_IO_Error_Timestamp: 
     Last_SQL_Error_Timestamp: 
               Master_SSL_Crl: 
           Master_SSL_Crlpath: 
           Retrieved_Gtid_Set: 
            Executed_Gtid_Set: 
                Auto_Position: 0
         Replicate_Rewrite_DB: 
                 Channel_Name: 
           Master_TLS_Version: 
1 row in set (0.00 sec)
验证MySQL集群可用性
# 在master节点添加test数据库
mysql -h 127.0.0.1 -uroot -proot -P 23306

create database test;
Query OK, 1 row affected (0.01 sec)

# 在slave节点查看同步情况
mysql -h 127.0.0.1 -uroot -proot -P 23307

show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| sys                |
| test               |
+--------------------+
5 rows in set (0.00 sec)

使用Docker部署Oracle

docker pull oracleinanutshell/oracle-xe-11g
# 49160 为ssh端口,49161 为sqlplus端口,49162 为oem端口
docker run -h oracle --name oracle -d -p 49160:22 -p 49161:1521 -p 49162:8080 oracleinanutshell/oracle-xe-11g

docker ps
CONTAINER ID   IMAGE                             COMMAND                  CREATED         STATUS         PORTS                                                                                                                               NAMES
d02c1acfab9b   oracleinanutshell/oracle-xe-11g   "/bin/sh -c '/usr/sb…"   5 seconds ago   Up 3 seconds   0.0.0.0:49160->22/tcp, :::49160->22/tcp, 0.0.0.0:49161->1521/tcp, :::49161->1521/tcp, 0.0.0.0:49162->8080/tcp, :::49162->8080/tcp   oracle

oracle数据库连接信息,port:49161,sid:xe,username:system,password:oracle。SYS用户密码为:oracle

可以使用上面的信息在oracle客户端进行验证

使用Docker部署ElasticSearch和Kibana

ES部署

docker pull elasticsearch:7.17.13
mkdir -p /data/test/es/config
mkdir -p /data/test/es/data
echo "http.host: 0.0.0.0" >> /data/test/es/config/elasticsearch.yml
chmod -R 777 /data/test/es/

docker run --name elasticsearch -p 29200:9200 -p 29300:9300 \
-e "discovery.type=single-node" \
-e ES_JAVA_OPTS="-Xms64m -Xmx512m" \
-v /data/test/es/config/elasticsearch.yml:/usr/share/elasticsearch/config/elasticsearch.yml \
-v /data/test/es/data:/usr/share/elasticsearch/data \
-v /data/test/es/plugins:/usr/share/elasticsearch/plugins \
-d elasticsearch:7.17.13

docker ps
CONTAINER ID   IMAGE                   COMMAND                  CREATED         STATUS         PORTS                                                                                      NAMES
658fede869f9   elasticsearch:7.17.13   "/bin/tini -- /usr/l…"   9 seconds ago   Up 8 seconds   0.0.0.0:29200->9200/tcp, :::29200->9200/tcp, 0.0.0.0:29300->9300/tcp, :::29300->9300/tcp   elasticsearch

curl http://127.0.0.1:29200
{
  "name" : "658fede869f9",
  "cluster_name" : "elasticsearch",
  "cluster_uuid" : "B6zpssXYQIm-swbFD2OQXQ",
  "version" : {
    "number" : "7.17.13",
    "build_flavor" : "default",
    "build_type" : "docker",
    "build_hash" : "2b211dbb8bfdecaf7f5b44d356bdfe54b1050c13",
    "build_date" : "2023-08-31T17:33:19.958690787Z",
    "build_snapshot" : false,
    "lucene_version" : "8.11.1",
    "minimum_wire_compatibility_version" : "6.8.0",
    "minimum_index_compatibility_version" : "6.0.0-beta1"
  },
  "tagline" : "You Know, for Search"
}

Kibana部署

docker pull kibana:7.17.13
# ip使用换成自己的
docker run --name kibana -e ELASTICSEARCH_HOSTS=http://172.25.10.66:29200 -p 25601:5601 -d kibana:7.17.13

docker ps
CONTAINER ID   IMAGE                   COMMAND                  CREATED              STATUS              PORTS                                                                                      NAMES
a82f39c6985a   kibana:7.17.13          "/bin/tini -- /usr/l…"   About a minute ago   Up About a minute   0.0.0.0:25601->5601/tcp, :::25601->5601/tcp                                                kibana

# 下面有html的输出表示部署成功,可以在浏览器中直接验证
curl http://127.0.0.1:25601/app/home | more

使用Docker部署Redis

mkdir -p /data/test/redis/conf
touch /data/test/redis/conf/redis.conf

docker run -p 26379:6379 --name redis -v /data/test/redis/data:/data \
-v /data/test/redis/conf:/etc/redis \
-d redis redis-server /etc/redis/redis.conf

docker ps
CONTAINER ID   IMAGE     COMMAND                  CREATED          STATUS          PORTS                                         NAMES
17b692db5b93   redis     "docker-entrypoint.s…"   21 seconds ago   Up 21 seconds   0.0.0.0:26379->6379/tcp, :::26379->6379/tcp   redis
# 登录redis容器
docker exec -it redis bash
# 登录redis客户端
redis-cli

Redis集群

安装redis-cluster;3主3从方式,从为了同步备份,主进行slot数据分片

# 先删除上面创建的redis容器,并删除相关数据
docker stop redis
docker remove redis
rm -rf /data/test/redis

编辑运行多个redis容器脚本文件,redis-cluster.sh脚本文件如下

for port in $(seq 8001 8006); \
do \
mkdir -p /data/test/redis/node-${port}/conf
touch /data/test/redis/node-${port}/conf/redis.conf
cat << EOF >/data/test/redis/node-${port}/conf/redis.conf
port ${port}
cluster-enabled yes
cluster-config-file nodes.conf
cluster-node-timeout 10000
cluster-announce-ip 172.25.10.66
cluster-announce-port ${port}
cluster-announce-bus-port 1${port}
appendonly yes
EOF
docker run -p ${port}:${port} -p 1${port}:1${port} --name redis-${port} \
-v /data/test/redis/node-${port}/data:/data \
-v /data/test/redis/node-${port}/conf/redis.conf:/etc/redis/redis.conf \
-d redis:5.0.7 redis-server /etc/redis/redis.conf; \
done
# 执行脚本
sh redis-cluster.sh
# 查看已运行容器
docker ps
CONTAINER ID   IMAGE         COMMAND                  CREATED          STATUS          PORTS                                                                                                NAMES
91df86222b2b   redis:5.0.7   "docker-entrypoint.s…"   20 seconds ago   Up 20 seconds   0.0.0.0:8006->8006/tcp, :::8006->8006/tcp, 6379/tcp, 0.0.0.0:18006->18006/tcp, :::18006->18006/tcp   redis-8006
ee04052c65e8   redis:5.0.7   "docker-entrypoint.s…"   20 seconds ago   Up 20 seconds   0.0.0.0:8005->8005/tcp, :::8005->8005/tcp, 6379/tcp, 0.0.0.0:18005->18005/tcp, :::18005->18005/tcp   redis-8005
6269aa9bedf2   redis:5.0.7   "docker-entrypoint.s…"   21 seconds ago   Up 20 seconds   0.0.0.0:8004->8004/tcp, :::8004->8004/tcp, 6379/tcp, 0.0.0.0:18004->18004/tcp, :::18004->18004/tcp   redis-8004
e50e91a01cb0   redis:5.0.7   "docker-entrypoint.s…"   21 seconds ago   Up 21 seconds   0.0.0.0:8003->8003/tcp, :::8003->8003/tcp, 6379/tcp, 0.0.0.0:18003->18003/tcp, :::18003->18003/tcp   redis-8003
f9d7301edae5   redis:5.0.7   "docker-entrypoint.s…"   21 seconds ago   Up 21 seconds   0.0.0.0:8002->8002/tcp, :::8002->8002/tcp, 6379/tcp, 0.0.0.0:18002->18002/tcp, :::18002->18002/tcp   redis-8002
adc6ae81faa5   redis:5.0.7   "docker-entrypoint.s…"   22 seconds ago   Up 21 seconds   0.0.0.0:8001->8001/tcp, :::8001->8001/tcp, 6379/tcp, 0.0.0.0:18001->18001/tcp, :::18001->18001/tcp   redis-8001
# 登录redis容器
docker exec -it redis-8001 bash

# 创建redis-cluster,回车之后需要输入yes
redis-cli --cluster create 172.25.10.66:8001 172.25.10.66:8002 172.25.10.66:8003 172.25.10.66:8004 172.25.10.66:8005 172.25.10.66:8006 --cluster-replicas 1
>>> Performing hash slots allocation on 6 nodes...
Master[0] -> Slots 0 - 5460
Master[1] -> Slots 5461 - 10922
Master[2] -> Slots 10923 - 16383
Adding replica 172.25.10.66:8005 to 172.25.10.66:8001
Adding replica 172.25.10.66:8006 to 172.25.10.66:8002
Adding replica 172.25.10.66:8004 to 172.25.10.66:8003
>>> Trying to optimize slaves allocation for anti-affinity
[WARNING] Some slaves are in the same host as their master
M: f6c273da4764283f7831470675fdf43888f379ba 172.25.10.66:8001
   slots:[0-5460] (5461 slots) master
M: c8e451f7a7a1633f7f63181f53444ad1d9af686e 172.25.10.66:8002
   slots:[5461-10922] (5462 slots) master
M: 5b102896f60d9385092efa1bb7e0fcb2465a6546 172.25.10.66:8003
   slots:[10923-16383] (5461 slots) master
S: 6c63c2f08411e1fc180817f5034e04af7c3f7c0b 172.25.10.66:8004
   replicates c8e451f7a7a1633f7f63181f53444ad1d9af686e
S: 890e44e5d41797e60b0eb937e8704c1fe654c1d7 172.25.10.66:8005
   replicates 5b102896f60d9385092efa1bb7e0fcb2465a6546
S: c3d8910113ee4f06984e525c03736e7c980c49ee 172.25.10.66:8006
   replicates f6c273da4764283f7831470675fdf43888f379ba
Can I set the above configuration? (type 'yes' to accept): yes
>>> Nodes configuration updated
>>> Assign a different config epoch to each node
>>> Sending CLUSTER MEET messages to join the cluster
Waiting for the cluster to join
....
>>> Performing Cluster Check (using node 172.25.10.66:8001)
M: f6c273da4764283f7831470675fdf43888f379ba 172.25.10.66:8001
   slots:[0-5460] (5461 slots) master
   1 additional replica(s)
M: c8e451f7a7a1633f7f63181f53444ad1d9af686e 172.25.10.66:8002
   slots:[5461-10922] (5462 slots) master
   1 additional replica(s)
S: 890e44e5d41797e60b0eb937e8704c1fe654c1d7 172.25.10.66:8005
   slots: (0 slots) slave
   replicates 5b102896f60d9385092efa1bb7e0fcb2465a6546
S: 6c63c2f08411e1fc180817f5034e04af7c3f7c0b 172.25.10.66:8004
   slots: (0 slots) slave
   replicates c8e451f7a7a1633f7f63181f53444ad1d9af686e
M: 5b102896f60d9385092efa1bb7e0fcb2465a6546 172.25.10.66:8003
   slots:[10923-16383] (5461 slots) master
   1 additional replica(s)
S: c3d8910113ee4f06984e525c03736e7c980c49ee 172.25.10.66:8006
   slots: (0 slots) slave
   replicates f6c273da4764283f7831470675fdf43888f379ba
[OK] All nodes agree about slots configuration.
>>> Check for open slots...
>>> Check slots coverage...
[OK] All 16384 slots covered.

使用Docker部署RabbitMQ

# 部署带管理控制台的RabbitMQ
docker run -d --name rabbitmq -p 5671:5671 -p 5672:5672 -p 4369:4369 -p 25672:25672 -p 15671:15671 -p 15672:15672 -v /data/test/rabbitmq:/var/lib/rabbitmq rabbitmq:management

docker ps
CONTAINER ID   IMAGE                 COMMAND                  CREATED         STATUS         PORTS                                                                                                                                                                                                                                             NAMES
58ce897d751c   rabbitmq:management   "docker-entrypoint.s…"   2 minutes ago   Up 2 minutes   0.0.0.0:4369->4369/tcp, :::4369->4369/tcp, 0.0.0.0:5671-5672->5671-5672/tcp, :::5671-5672->5671-5672/tcp, 0.0.0.0:15671-15672->15671-15672/tcp, :::15671-15672->15671-15672/tcp, 0.0.0.0:25672->25672/tcp, :::25672->25672/tcp, 15691-15692/tcp   rabbitmq

# 返回html,可以通过ip在浏览器中访问
curl 127.0.0.1:15672

端口说明:4369, 25672 (Erlang发现&集群端口);5672, 5671 (AMQP端口);15672 (web管理后台端口);61613, 61614 (STOMP协议端口);1883, 8883 (MQTT协议端口)