1. 前言
前面學習了 SpringCloudAlibaba之服務註冊與發現Nacos 以及 SpringCloudAlibaba之配置中心Nacos,其中Nacos服務都部署在本地,那麼如今把它部署到服務器上。html
在服務器上部署Nacos,有多種方式,mysql
單機:nginx
方式一: 拷貝三份編譯後的 Nacos Server,分別修改端口,以及編寫 cluster.conf 文件
方式二: 啓動三個 Nacos Server 的 Docker 容器
方式三: 使用 docker-compose 編排三個 Nacos Server 服務
三臺及以上:git
方式一: 每臺都拷貝一份編譯後的 Nacos Server,以及編寫 cluster.conf 文件
方式二: 每臺都啓動一個 Nacos Server 的 Docker 容器
方式三: 每臺都使用 docker-compose 編排一個 Nacos Server 服務
最方便的固然是使用 docker-compose 來編排服務,本篇博客也是使用的 docker-compose 方式(單機)。這裏除了會編排三個 Nacos Server 服務,還會增長 MySQL 服務和 Nginx 服務,這也是官方推薦的部署架構:github
至少使用三個Nacos節點
使用MySQL做爲數據源,方便觀察數據存儲的基本狀況
使用Nginx做爲統一入口,擴展節點的時候不影響後端應用spring
2. 源碼
GitHub 地址:https://github.com/intomylife/Dockersql
Docker Hub 地址:https://hub.docker.com/r/intomylifedocker
3. 部署
整個部署所須要的文件都在 build 目錄中數據庫
build/
├── hostname
│ ├── config
│ │ ├── mysql
│ │ │ └── my.cnf
│ │ └── nginx
│ │ └── nginx.conf
│ ├── data
│ │ ├── mysql
│ │ ├── nacos
│ │ └── nginx
│ ├── docker-compose-all.yaml
│ ├── docker-compose-config.yaml
│ ├── docker-compose-discovery.yaml
│ ├── docker-compose.yaml
│ ├── env
│ │ ├── mysql
│ │ │ └── mysql.env
│ │ └── nacos
│ │ └── nacos.env
│ ├── .env
│ ├── init
│ │ └── mysql
│ │ └── init.sql
│ ├── log
│ │ ├── mysql
│ │ ├── nacos1
│ │ ├── nacos2
│ │ ├── nacos3
│ │ └── nginx
│ ├── start.sh
│ └── stop.sh
└── ip
├── config
│ ├── mysql
│ │ └── my.cnf
│ └── nginx
│ └── nginx.conf
├── data
│ ├── mysql
│ ├── nacos
│ └── nginx
├── docker-compose-all.yaml
├── docker-compose-config.yaml
├── docker-compose-discovery.yaml
├── docker-compose.yaml
├── env
│ ├── mysql
│ │ └── mysql.env
│ └── nacos
│ └── nacos.env
├── .env
├── init
│ └── mysql
│ └── init.sql
├── log
│ ├── mysql
│ ├── nacos1
│ ├── nacos2
│ ├── nacos3
│ └── nginx
├── start.sh
└── stop.sh
hostname和ip兩個目錄分別對應 PREFER_HOST_MODE 兩種模式
兩種模式對應的部署方式徹底同樣,只有配置上有些許不一樣;下面以hostname爲例詳細說明
3.1 config
服務的配置文件後端
3.1.1 mysql - my.cnf
[client]
default-character-set=utf8mb4
[mysqld]
character-set-client-handshake = FALSE
character-set-server = utf8mb4
collation-server = utf8mb4_unicode_ci
# 數據庫惟一 ID,主從的標識號絕對不能重複。
server-id = 1
# 開啓 bin-log,並指定文件目錄和文件名前綴
log-bin=/var/log/mysql/binlog
# bin-log 日誌文件格式,設置爲 MIXED 能夠防止主鍵重複。
binlog_format = mixed
[mysql]
default-character-set=utf8mb4
配置了字符集編碼
開啓了 bin-log
3.1.2 nginx - nginx.conf
... 省略部分 ...
upstream dispense {
server nacos1:8848;
server nacos2:8848;
server nacos3:8848;
}
server {
listen 9000;
server_name localhost;
#charset koi8-r;
#access_log logs/host.access.log main;
location / {
proxy_pass http://dispense;
index index.html index.htm;
}
... 省略部分 ...
}
... 省略部分 ...
修改監聽端口爲 9000
請求會被負載均衡到三個 Nacos Server 服務上
3.2 data
持久化服務產生的數據
3.3 env
服務中獨立而又重複的配置
3.3.1 mysql - mysql.env
TZ=Asia/Shanghai
MYSQL_ROOT_HOST=%
1
2
配置了容器的時區
被容許鏈接的地址,%表示所有
3.3.2 nacos - nacos.env
TZ=Asia/Shanghai
JVM_XMS=512m
JVM_XMX=512m
JVM_XMN=256m
MODE=cluster
PREFER_HOST_MODE=hostname
NACOS_SERVERS=nacos1:8848 nacos2:8848 nacos3:8848
NACOS_AUTH_ENABLE=true
MYSQL_SERVICE_HOST=mysql
MYSQL_SERVICE_DB_NAME=nacos_config
配置了容器的時區
指定JVM各類內存大小
MODE 指定Nacos啓動的模式,cluster 表示集羣模式
PREFER_HOST_MODE 在我理解,代表Nacos會以什麼方式來尋找本身的集羣「夥伴」(peers),一共有兩種方式:hostname / ip;① 若是指定爲 ip,那麼 NACOS_SERVERS 也必須指定的是一組 ip(全部Nacos的集羣節點),注意這裏比較坑的是,它默認會取Docker的 ip(docker0:172.17.0.1/16),這樣會致使 ip 地址不固定,更者若是是多臺服務器就壓根不會在同一個網絡中,因此還須要配置 NACOS_SERVER_IP 內網地址用來顯示指定 ip;② 若是指定爲 hostname,那麼 NACOS_SERVERS 也必須指定的是一組 hostname(全部Nacos的集羣節點),因此還須要配置docker-compose中service的 hostname 用來顯示指定主機名
NACOS_AUTH_ENABLE 開啓密碼驗證,即在後端應用中若是要鏈接 Nacos Server,就必需要配置有效的用戶名和密碼才容許鏈接
最後兩個指定了鏈接 MySQL 的配置信息
3.4 .env
docker-compose 默認引入的文件,裏面配置默認的環境變量
## version
MYSQL_VERSION=5.7
NACOS_VERSION=1.2.1
NGINX_VERSION=1.8
FIRST_VERSION=1.0.0
SECOND_VERSION=1.0.0
CONSUMER_VERSION=1.0.0
ORDER_VERSION=1.0.0
USER_VERSION=1.0.0
## pwd
MYSQL_SERVICE_USER=root
MYSQL_ROOT_PASSWORD=123456
NACOS_USER=nacos
NACOS_PASSWORD=nacos
## env
ORDER_ENV=dev
USER_ENV=dev
此文件的目的就是爲了簡化咱們的配置,避免修改多處重複的配置信息
3.5 init
服務的初始化數據
3.5.1 mysql - init.sql
-- 建立數據庫
DROP database IF EXISTS `nacos_config`;
CREATE DATABASE `nacos_config` default character set utf8mb4 collate utf8mb4_unicode_ci;
-- 切換數據庫
USE nacos_config;
/******************************************/
/* 數據庫全名 = nacos_config */
/* 表名稱 = config_info */
/******************************************/
CREATE TABLE `config_info` (
`id` bigint(20) NOT NULL AUTO_INCREMENT COMMENT 'id',
`data_id` varchar(255) NOT NULL COMMENT 'data_id',
`group_id` varchar(255) DEFAULT NULL,
`content` longtext NOT NULL COMMENT 'content',
`md5` varchar(32) DEFAULT NULL COMMENT 'md5',
`gmt_create` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '建立時間',
`gmt_modified` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '修改時間',
`src_user` text COMMENT 'source user',
`src_ip` varchar(20) DEFAULT NULL COMMENT 'source ip',
`app_name` varchar(128) DEFAULT NULL,
`tenant_id` varchar(128) DEFAULT '' COMMENT '租戶字段',
`c_desc` varchar(256) DEFAULT NULL,
`c_use` varchar(64) DEFAULT NULL,
`effect` varchar(64) DEFAULT NULL,
`type` varchar(64) DEFAULT NULL,
`c_schema` text,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_configinfo_datagrouptenant` (`data_id`,`group_id`,`tenant_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin COMMENT='config_info';
... 省略部分 ...
MySQL 的初始化 sql 語句
因爲 Nacos Server 的數據源使用的是 MySQL,因此須要建這些基礎表和插入一些基礎數據
3.6 log
映射出服務的日誌信息
3.7 .yaml
先來總體看一下,相似文件一共有四個:docker-compose.yaml,docker-compose-discovery.yaml,docker-compose-config.yaml,docker-compose-all.yaml
這些文件都有什麼?
部署的核心是 Nacos Server 集羣,相關內容所有在 docker-compose.yaml 文件中;而其餘文件,都是用來部署後端應用的,它們主要測試 Nacos Server 集羣是否真正部署成功;這些後端應用又包括Nacos的服務註冊發現和配置中心,分別在 docker-compose-discovery.yaml 和 docker-compose-config.yaml 文件中;最後 docker-compose-all.yaml 文件包含 docker-compose-discovery.yaml + docker-compose-config.yaml 兩個文件的內容
爲何拆分開?
本來都寫在一個 .yaml,然而在啓動的時候發現,配置中心服務啓動老是失敗,由於 Nacos Server 還未徹底啓動,配置中心服務獲取不到對應的配置信息,就啓動失敗;那麼拆開後,就可使用腳原本控制啓動的順序
3.7.1 docker-compose.yaml
這次部署的核心文件
version: '3'
services:
mysql:
container_name: mysql
image: mysql:${MYSQL_VERSION}
env_file:
- env/mysql/mysql.env
environment:
MYSQL_ROOT_PASSWORD: ${MYSQL_ROOT_PASSWORD}
ports:
- "3306:3306"
volumes:
- ./config/mysql/my.cnf:/etc/mysql/conf.d/my.cnf
- ./init/mysql/:/docker-entrypoint-initdb.d/
- ./data/mysql/:/var/lib/mysql/
- ./log/mysql/:/var/log/mysql/
command: [
'--character-set-server=utf8mb4',
'--collation-server=utf8mb4_unicode_ci'
]
restart: always
nacos1:
hostname: nacos1
container_name: nacos1
image: nacos/nacos-server:${NACOS_VERSION}
env_file:
- env/nacos/nacos.env
environment:
MYSQL_SERVICE_USER: ${MYSQL_SERVICE_USER}
MYSQL_SERVICE_PASSWORD: ${MYSQL_ROOT_PASSWORD}
ports:
- "8000:8848"
volumes:
- ./data/nacos/:/home/nacos/data/
- ./log/nacos1/:/home/nacos/logs/
depends_on:
- mysql
restart: always
nacos2:
hostname: nacos2
container_name: nacos2
image: nacos/nacos-server:${NACOS_VERSION}
env_file:
- env/nacos/nacos.env
environment:
MYSQL_SERVICE_USER: ${MYSQL_SERVICE_USER}
MYSQL_SERVICE_PASSWORD: ${MYSQL_ROOT_PASSWORD}
ports:
- "8001:8848"
volumes:
- ./data/nacos/:/home/nacos/data/
- ./log/nacos2/:/home/nacos/logs/
depends_on:
- mysql
restart: always
nacos3:
hostname: nacos3
container_name: nacos3
image: nacos/nacos-server:${NACOS_VERSION}
env_file:
- env/nacos/nacos.env
environment:
MYSQL_SERVICE_USER: ${MYSQL_SERVICE_USER}
MYSQL_SERVICE_PASSWORD: ${MYSQL_ROOT_PASSWORD}
ports:
- "8002:8848"
volumes:
- ./data/nacos/:/home/nacos/data/
- ./log/nacos3/:/home/nacos/logs/
depends_on:
- mysql
restart: always
nginx:
container_name: nginx
image: nginx:${NGINX_VERSION}
environment:
TZ: Asia/Shanghai
ports:
- "9000:9000"
volumes:
- ./config/nginx/nginx.conf:/etc/nginx/nginx.conf
- ./data/nginx/:/usr/share/nginx/html/
- ./log/nginx/:/var/log/nginx/
depends_on:
- nacos1
- nacos2
- nacos3
restart: always
三個Nacos節點,使用MySQL做爲數據源,使用Nginx做爲統一入口
${} 用來獲取 .env 文件中的環境變量
env_file 指定環境變量文件,可同時引入多個環境變量,與 environment 中的環境變量結合使用;想知道哪些環境變量生效了,使用 docker-compose -f 文件名 config 命令來查看指定文件的具體內容
重點看下兩種模式下,Nacos 的配置有哪些不一樣,分別進入到 hostname 目錄和 ip 目錄中,使用 docker-compose -f docker-compose.yaml config 命令來查看具體內容,片斷以下:
hostname:
... 省略部分 ...
nacos1:
container_name: nacos1
depends_on:
- mysql
environment:
JVM_XMN: 256m
JVM_XMS: 512m
JVM_XMX: 512m
MODE: cluster
MYSQL_SERVICE_DB_NAME: nacos_config
MYSQL_SERVICE_HOST: mysql
MYSQL_SERVICE_PASSWORD: '123456'
MYSQL_SERVICE_USER: root
NACOS_AUTH_ENABLE: "true"
NACOS_SERVERS: nacos1:8848 nacos2:8848 nacos3:8848
PREFER_HOST_MODE: hostname
TZ: Asia/Shanghai
hostname: nacos1
image: nacos/nacos-server:1.2.1
ports:
- 8000:8848/tcp
restart: always
volumes:
- /usr/local/build/hostname/data/nacos:/home/nacos/data:rw
- /usr/local/build/hostname/log/nacos1:/home/nacos/logs:rw
... 省略部分 ...
ip:
... 省略部分 ...
nacos1:
container_name: nacos1
depends_on:
- mysql
environment:
JVM_XMN: 256m
JVM_XMS: 512m
JVM_XMX: 512m
MODE: cluster
MYSQL_SERVICE_DB_NAME: nacos_config
MYSQL_SERVICE_HOST: mysql
MYSQL_SERVICE_PASSWORD: '123456'
MYSQL_SERVICE_USER: root
NACOS_APPLICATION_PORT: '8000'
NACOS_AUTH_ENABLE: "true"
NACOS_SERVERS: xxx.xxx.xxx.xxx:8000 xxx.xxx.xxx.xxx:8001 xxx.xxx.xxx.xxx:8002
NACOS_SERVER_IP: xxx.xxx.xxx.xxx
PREFER_HOST_MODE: ip
TZ: Asia/Shanghai
image: nacos/nacos-server:1.2.1
ports:
- 8000:8000/tcp
restart: always
volumes:
- /usr/local/build/ip/data/nacos:/home/nacos/data:rw
- /usr/local/build/ip/log/nacos1:/home/nacos/logs:rw
... 省略部分 ...
相同點:
指定JVM各類內存大小
指定MODE爲集羣模式
指定了MySQL鏈接信息
開啓了密碼驗證
配置了容器的時區
映射了日誌目錄和數據目錄
不一樣點:
最大的不一樣點,就是 PREFER_HOST_MODE 選擇的模式:hostname / ip
hostname 模式: 須要配置service服務的 hostname -> hostname: nacos1;在指定 NACOS_SERVERS 集羣地址時,就是一組 hostname -> nacos1:8848 nacos2:8848 nacos3:8848
ip 模式: 須要配置 NACOS_SERVER_IP -> NACOS_SERVER_IP: xxx.xxx.xxx.xxx;在指定 NACOS_SERVERS 集羣地址時,就是一組 ip -> xxx.xxx.xxx.xxx:8000 xxx.xxx.xxx.xxx:8001 xxx.xxx.xxx.xxx:8002。這裏須要注意的是,因爲是在一臺服務器中,那麼端口是不能重複的,因此這時還要指定每個 Nacos Server 的端口,即配置 NACOS_APPLICATION_PORT
端口映射的不一樣
注:ip 模式具體的地址和端口都在 build/ip/.env 文件中配置;若是這裏修改了端口,那麼同時也須要在 build/ip/config/nginx/nginx.conf 文件中修改負載中對應server的端口
3.7.2 docker-compose-all.yaml
用於測試 Nacos Server 集羣的後端應用
docker-compose-all.yaml = docker-compose-discovery.yaml + docker-compose-config.yaml
version: '3'
services:
first:
container_name: first
image: intomylife/nacos-cluster-first:${FIRST_VERSION}
environment:
TZ: Asia/Shanghai
spring.cloud.nacos.discovery.server-addr: nginx:9000
spring.cloud.nacos.discovery.username: ${NACOS_USER}
spring.cloud.nacos.discovery.password: ${NACOS_PASSWORD}
ports:
- "8090:8090"
restart: always
second:
container_name: second
image: intomylife/nacos-cluster-second:${SECOND_VERSION}
environment:
TZ: Asia/Shanghai
spring.cloud.nacos.discovery.server-addr: nginx:9000
spring.cloud.nacos.discovery.username: ${NACOS_USER}
spring.cloud.nacos.discovery.password: ${NACOS_PASSWORD}
ports:
- "8091:8091"
restart: always
consumer:
container_name: consumer
image: intomylife/nacos-cluster-consumer:${CONSUMER_VERSION}
environment:
TZ: Asia/Shanghai
spring.cloud.nacos.discovery.server-addr: nginx:9000
spring.cloud.nacos.discovery.username: ${NACOS_USER}
spring.cloud.nacos.discovery.password: ${NACOS_PASSWORD}
ports:
- "8080:8080"
restart: always
order:
container_name: order
image: intomylife/nacos-cluster-order:${ORDER_VERSION}
environment:
TZ: Asia/Shanghai
spring.cloud.nacos.config.server-addr: nginx:9000
spring.cloud.nacos.config.username: ${NACOS_USER}
spring.cloud.nacos.config.password: ${NACOS_PASSWORD}
spring.cloud.nacos.config.group: ${ORDER_ENV}
spring.cloud.nacos.discovery.server-addr: nginx:9000
spring.cloud.nacos.discovery.username: ${NACOS_USER}
spring.cloud.nacos.discovery.password: ${NACOS_PASSWORD}
ports:
- "10000:10000"
restart: always
user:
container_name: user
image: intomylife/nacos-cluster-user:${USER_VERSION}
environment:
TZ: Asia/Shanghai
spring.cloud.nacos.config.server-addr: nginx:9000
spring.cloud.nacos.config.username: ${NACOS_USER}
spring.cloud.nacos.config.password: ${NACOS_PASSWORD}
spring.cloud.nacos.config.group: ${USER_ENV}
spring.cloud.nacos.discovery.server-addr: nginx:9000
spring.cloud.nacos.discovery.username: ${NACOS_USER}
spring.cloud.nacos.discovery.password: ${NACOS_PASSWORD}
ports:
- "11000:11000"
restart: always
first,second和consumer服務是一組,實現了服務的註冊與發現功能
order和user服務是一組,實現了配置中心功能
源碼在這裏獲取
3.8 .sh
啓動腳本和中止腳本
3.8.1 start.sh
#!/bin/bash
## $() - 方法,${} - 變量
## 獲取入參,啓動類型
start_type=$1
## 輸出看一眼
echo start_type: ${start_type}
## 參數校驗
if [ "$start_type" == "discovery" ]||[ "$start_type" == "config" ]||[ "$start_type" == "all" ];
then
## 先啓動基礎服務
docker-compose -f docker-compose.yaml up -d
## 循環十次檢查基礎服務是否啓動完成
for((i=1;i<=10;i++));
do
## 檢查服務是否啓動完成
code=$(curl -o /dev/null -s -w %{http_code} 127.0.0.1:9000/nacos)
if [ ${code} == '302' ];
then
echo 'check --- success --- ' ${code};
break;
else
echo 'check --- loading --- ' ${code};
fi
## 三秒中檢查一次
sleep 3;
done
## 檢查結束或檢查終止,再次獲取服務狀態碼
code=$(curl -o /dev/null -s -w %{http_code} 127.0.0.1:9000/nacos)
if [ ${code} == '302' ];
then
## 啓動完成,接着啓動後端應用服務
docker-compose -f docker-compose-$start_type.yaml up -d
echo 'success';
else
## 啓動失敗,可能出錯了,中止基礎服務
docker-compose -f docker-compose.yaml down
echo 'fail';
fi
else
## 參數有誤
echo 'end';
fi
啓動腳本
腳本還會獲取一個入參,這個入參分別對應不一樣組合的後端應用服務:discovery,config,all
考慮到服務較多,若是你只想單純的部署 Nacos Server 集羣,那麼就不須要關注這個啓動腳本,直接docker-compose up -d便可
這個腳本爲了解決配置中心服務啓動失敗問題,其中就循環檢查 Nginx 服務的狀態碼,只有基礎服務(Nacos Server 集羣)徹底啓動成功,纔會啓動後端應用
3.8.2 stop.sh
#!/bin/bash
## $() - 方法,${} - 變量
## 中止服務
docker-compose -f docker-compose.yaml -f docker-compose-all.yaml down
中止腳本
3.9 啓動
3.9.1 啓動前的準備
獲取源碼
整個 build 目錄上傳到服務器上
以 hostname 模式爲例,進入到 hostname 目錄cd build/hostname
啓動腳本賦予執行權限chmod +x start.sh
中止腳本賦予執行權限chmod +x stop.sh
日誌目錄賦予讀寫執權限chmod -R 777 log/
3.9.2 啓動
若是隻須要 Nacos Server 集羣,那麼在 hostname 目錄下執行命令docker-compose up -d
若是須要 Nacos Server 集羣 + 服務註冊與發現,那麼在 hostname 目錄下執行命令./start.sh discovery
若是須要 Nacos Server 集羣 + 配置中心,那麼在 hostname 目錄下執行命令./start.sh config
若是都須要,那麼在 hostname 目錄下執行命令./start.sh all
整個啓動過程大概在一分鐘左右
等待出現success表示啓動成功,接下來進行訪問(若是有防火牆,注意開放端口:3306,8000,8001,8002,9000,8090,8091,8080,10000,11000)
訪問地址 ip:9000/nacos,進入到 Nacos Server 主頁面
帳號密碼:nacos, nacos
進入 集羣管理 - 節點列表 頁面,有以下數據,則表示集羣搭建成功
節點Ip 節點狀態 集羣任期 Leader止時(ms) 心跳止時(ms)
nacos1:8848 LEADER 1 13849 2500
nacos2:8848 FOLLOWER 1 14338 2500
nacos3:8848 FOLLOWER 1 12273 2500
測試服務註冊與發現,屢次訪問地址 ip:8080/feign,能夠發現輪流輸出Hello Spring Cloud Alibaba!!! port:8090和Hello Spring Cloud Alibaba!!! port:8091
測試配置中心,訪問地址 ip:10000/info,能夠看到輸出內容dataInfo: order-config-dev.yml, group: dev, extName: mysql-dev
若是你還想在本地項目鏈接此 Nacos Server 集羣,那麼下載源碼,修改配置文件中的server-addr爲你的 ip:9000 便可
若是想測試 ip 模式,那麼須要先在 build/ip/.env 文件中的 NACOS_SERVER_IP 處配置你本身的內網 ip;而後再進入到 ip 目錄,執行上面相同的命令
3.9.3 中止
在 hostname 目錄下執行命令./stop.sh
4. 參考
https://nacos.io/zh-cn/docs/quick-start-docker.html
https://nacos.io/zh-cn/docs/cluster-mode-quick-start.html
https://github.com/nacos-group/nacos-docker
但願可以幫助到你