NATS 支持多种集群部署方式,以下是主流部署方案:
一、Docker Compose:3节点JetStream集群
- 文件结构
sql
$ tree .
.
|-- docker-compose.yml
|-- nats-1.conf
|-- nats-2.conf
`-- nats-3.conf
0 directories, 4 files
- docker-compose.yml
bash
# 定义 Docker Compose 的服务列表
services:
# 第一个 NATS 服务实例
nats-1:
# 使用 NATS 2.10 版本的官方镜像
image: nats:2.10
# 容器名称设置为 nats-1
container_name: nats-1
# 启动命令,指定使用配置文件 /etc/nats/nats.conf
command: ["-c", "/etc/nats/nats.conf"]
# 挂载配置文件和数据卷
volumes:
# 将本地配置文件挂载到容器内的配置路径
- ./nats-1.conf:/etc/nats/nats.conf
# 挂载数据卷用于持久化存储
- nats1-data:/data
# 端口映射配置
ports:
# 映射 NATS 客户端连接端口
- "4222:4222"
# 映射 HTTP 监控端口
- "8222:8222"
# 第二个 NATS 服务实例
nats-2:
# 使用 NATS 2.10 版本的官方镜像
image: nats:2.10
# 容器名称设置为 nats-2
container_name: nats-2
# 启动命令,指定使用配置文件 /etc/nats/nats.conf
command: ["-c", "/etc/nats/nats.conf"]
# 挂载配置文件和数据卷
volumes:
# 将本地配置文件挂载到容器内的配置路径
- ./nats-2.conf:/etc/nats/nats.conf
# 挂载数据卷用于持久化存储
- nats2-data:/data"
# 第三个 NATS 服务实例
nats-3:
# 使用 NATS 2.10 版本的官方镜像
image: nats:2.10
# 容器名称设置为 nats-3
container_name: nats-3
# 启动命令,指定使用配置文件 /etc/nats/nats.conf
command: ["-c", "/etc/nats/nats.conf"]
# 挂载配置文件和数据卷
volumes:
# 将本地配置文件挂载到容器内的配置路径
- ./nats-3.conf:/etc/nats/nats.conf
# 挂载数据卷用于持久化存储
- nats3-data:/data"
# 定义数据卷,用于持久化存储数据
volumes:
# 第一个 NATS 实例的数据卷
nats1-data:
# 第二个 NATS 实例的数据卷
nats2-data:
# 第三个 NATS 实例的数据卷
nats3-data:
- 配置文件
3.1 nats-1.conf
perl
# NATS 客户端连接端口
port: 4222
# HTTP 监控端口
http: 8222
# 服务器名称,用于集群标识
server_name: nats-1
# 集群配置
cluster {
# 集群名称,所有节点必须使用相同的名称
name: nats-cluster
# 集群监听地址和端口,0.0.0.0 表示监听所有网络接口
listen: 0.0.0.0:6222
# 路由配置,定义与其他节点的连接
routes = [
# 连接到 nats-2 节点
nats://nats-2:6222
# 连接到 nats-3 节点
nats://nats-3:6222
]
}
# JetStream 配置,NATS 的持久化消息流引擎
jetstream {
# JetStream 数据存储目录
store_dir: /data/jetstream
}
3.2 nats-2.conf
perl
# NATS 客户端连接端口
port: 4222
# HTTP 监控端口
http: 8222
# 服务器名称,用于集群标识
server_name: nats-2
# 集群配置
cluster {
# 集群名称,所有节点必须使用相同的名称
name: nats-cluster
# 集群监听地址和端口,0.0.0.0 表示监听所有网络接口
listen: 0.0.0.0:6222
# 路由配置,定义与其他节点的连接
routes = [
# 连接到 nats-1 节点
nats://nats-1:6222
# 连接到 nats-3 节点
nats://nats-3:6222
]
}
# JetStream 配置,NATS 的持久化消息流引擎
jetstream {
# JetStream 数据存储目录
store_dir: /data/jetstream
}
3.3 nats-3.conf
perl
# NATS 客户端连接端口
port: 4222
# HTTP 监控端口
http: 8222
# 服务器名称,用于集群标识
server_name: nats-3
# 集群配置
cluster {
# 集群名称,所有节点必须使用相同的名称
name: nats-cluster
# 集群监听地址和端口,0.0.0.0 表示监听所有网络接口
listen: 0.0.0.0:6222
# 路由配置,定义与其他节点的连接
routes = [
# 连接到 nats-1 节点
nats://nats-1:6222
# 连接到 nats-2 节点
nats://nats-2:6222
]
}
# JetStream 配置,NATS 的持久化消息流引擎
jetstream {
# JetStream 数据存储目录
store_dir: /data/jetstream
}
启动:
js
docker-compose up -d

验证集群:
bash
$ curl http://localhost:8222/varz
{
"server_id": "NC57O2W7KMMU7I5M7SKCK5W7KOCH73HLQISTTCSAI7HYFGFUAKGOMXDU",
"server_name": "nats-1",
"version": "2.10.29",
"proto": 1,
"git_commit": "f91ddd8",
"go": "go1.24.2",
"host": "0.0.0.0",
"port": 4222,
"connect_urls": [
"172.20.0.3:4222",
"172.20.0.2:4222",
"172.20.0.4:4222"
],
"max_connections": 65536,
"ping_interval": 120000000000,
"ping_max": 2,
"http_host": "0.0.0.0",
"http_port": 8222,
"http_base_path": "",
"https_port": 0,
"auth_timeout": 2,
"max_control_line": 4096,
"max_payload": 1048576,
"max_pending": 67108864,
"cluster": {
"name": "nats-cluster",
"addr": "0.0.0.0",
"cluster_port": 6222,
"auth_timeout": 2,
"urls": [
"nats-2:6222",
"nats-3:6222"
],
"tls_timeout": 2,
"pool_size": 3
},
"gateway": {},
"leaf": {},
"mqtt": {},
"websocket": {},
"jetstream": {
"config": {
"max_memory": 5329022976,
"max_storage": 744904350720,
"store_dir": "/data/jetstream/jetstream",
"sync_interval": 120000000000
},
"stats": {
"memory": 0,
"storage": 0,
"reserved_memory": 0,
"reserved_storage": 0,
"accounts": 1,
"ha_assets": 1,
"api": {
"total": 0,
"errors": 0
}
},
"meta": {
"name": "nats-cluster",
"leader": "nats-3",
"peer": "bkCGheKT",
"cluster_size": 3,
"pending": 0
}
},
"tls_timeout": 2,
"write_deadline": 10000000000,
"start": "2026-01-01T14:25:02.59602819Z",
"now": "2026-01-01T14:26:27.828817619Z",
"uptime": "1m25s",
"mem": 17694720,
"cores": 16,
"gomaxprocs": 16,
"cpu": 0,
"connections": 0,
"total_connections": 0,
"routes": 8,
"remotes": 2,
"leafnodes": 0,
"in_msgs": 115,
"out_msgs": 114,
"in_bytes": 45074,
"out_bytes": 41878,
"slow_consumers": 0,
"subscriptions": 196,
"http_req_stats": {
"/varz": 1
},
"config_load_time": "2026-01-01T14:25:02.59602819Z",
"system_account": "$SYS",
"slow_consumer_stats": {
"clients": 0,
"routes": 0,
"gateways": 0,
"leafs": 0
}
}
- Go客户端连接集群方式
css
nc, err := nats.Connect(
"nats://nats-1:4222,nats://nats-2:4222,nats://nats-3:4222",
)
二、K8s部署(生产推荐)
在K8s中部署NATS集群,最推荐的方式是适用StatefulSet。因为NATS节点需要稳定的网络标识来建立集群内部路由,并且在开启JetStream持久化的时候需要挂载稳定的存储卷PVC。
- 定义配置
makefile
# API 版本,使用 v1
apiVersion: v1
# 资源类型为 ConfigMap,用于存储配置数据
kind: ConfigMap
metadata:
# ConfigMap 的名称
name: nats-config
data:
# 配置文件名称为 nats.conf
nats.conf: |
# 监听客户端连接
port: 4222
# HTTP 监控端口
monitor_port: 8222
# 集群配置
cluster {
# 集群内部通信端口
port: 6222
# 使用 K8s Headless Service 的 DNS 名称进行自动发现
routes [
# 连接到第一个 NATS 节点
"nats://nats-0.nats-headless.default.svc.cluster.local:6222"
# 连接到第二个 NATS 节点
"nats://nats-1.nats-headless.default.svc.cluster.local:6222"
# 连接到第三个 NATS 节点
"nats://nats-2.nats-headless.default.svc.cluster.local:6222"
]
}
# 开启 JetStream 持久化
jetstream {
# JetStream 数据存储目录
store_dir: "/data/jetstream"
# 最大内存使用量
max_mem: 1G
# 最大文件存储量
max_file: 10G
}
- 定义服务
makefile
---
# 无头服务,用于集群内部发现
apiVersion: v1
# 资源类型为 Service
kind: Service
metadata:
# Service 名称
name: nats-headless
spec:
# 设置为 None,表示这是一个 Headless Service
clusterIP: None
# 选择器,匹配标签为 app: nats 的 Pod
selector:
app: nats
# 端口配置
ports:
# 集群通信端口
- name: cluster
port: 6222
---
# 客户端访问服务
apiVersion: v1
# 资源类型为 Service
kind: Service
metadata:
# Service 名称
name: nats-client
spec:
# 选择器,匹配标签为 app: nats 的 Pod
selector:
app: nats
# 端口配置
ports:
# 客户端连接端口
- name: client
port: 4222
# HTTP 监控端口
- name: monitor
port: 8222
- 定义控制器
makefile
# API 版本,使用 apps/v1
apiVersion: apps/v1
# 资源类型为 StatefulSet,用于管理有状态应用
kind: StatefulSet
metadata:
# StatefulSet 的名称
name: nats
spec:
# 关联的 Headless Service 名称
serviceName: "nats-headless"
# 副本数量,部署 3 个 NATS 节点
replicas: 3
# 选择器,用于匹配 Pod
selector:
matchLabels:
# 匹配标签为 app: nats 的 Pod
app: nats
# Pod 模板定义
template:
metadata:
# Pod 的标签
labels:
app: nats
spec:
# 容器配置
containers:
# NATS 容器
- name: nats
# 使用 NATS 2.10 Alpine 版本镜像
image: nats:2.10-alpine
# 启动参数,指定配置文件路径
args: ["-c", "/etc/nats-config/nats.conf"]
# 容器端口配置
ports:
# 客户端连接端口
- containerPort: 4222
name: client
# 集群通信端口
- containerPort: 6222
name: cluster
# HTTP 监控端口
- containerPort: 8222
name: monitor
# 卷挂载配置
volumeMounts:
# 挂载 ConfigMap 配置
- name: config
mountPath: /etc/nats-config
# 挂载数据持久化卷
- name: nats-data
mountPath: /data/jetstream
# 卷配置
volumes:
# ConfigMap 卷
- name: config
configMap:
name: nats-config
# 自动为每个副本创建 10Gi 的磁盘存储
volumeClaimTemplates:
# 数据卷声明模板
- metadata:
# 数据卷名称
name: nats-data
spec:
# 访问模式,单节点读写
accessModes: [ "ReadWriteOnce" ]
# 资源请求
resources:
requests:
# 存储空间请求 10Gi
storage: 10Gi
- 运行
powershell
#!/bin/bash
#删除
kubectl delete -f deploy.yaml
kubectl delete -f server.yaml
kubectl delete -f storageclass.yaml
kubectl delete -f pv-0.yaml
kubectl delete -f pv-1.yaml
kubectl delete -f pv-2.yaml
kubectl delete -f configmap.yaml
#部署
kubectl apply -f configmap.yaml
kubectl apply -f pv-0.yaml
kubectl apply -f pv-1.yaml
kubectl apply -f pv-2.yaml
kubectl apply -f storageclass.yaml
kubectl apply -f server.yaml
kubectl apply -f deploy.yaml
kubectl get pods -l app=nats
- 验证
apache
kubectl get pods -l app=nats
NAME READY STATUS RESTARTS AGE
nats-0 1/1 Running 0 0s
nats-1 1/1 Running 0 0s
nats-2 1/1 Running 0 0s
- Go客户端连接k8s集群方式
javascript
nats://nats.<namespace>.svc.cluster.local:4222
三、直接用Helm
bash
helm repo add nats https://nats-io.github.io/k8s/helm/charts/
helm install nats nats/nats \
--set cluster.enabled=true \
--set jetstream.enabled=true
验证
apache
kubectl get pods -l app=nats
NAME READY STATUS RESTARTS AGE
nats-0 1/1 Running 0 0s
nats-1 1/1 Running 0 0s
nats-2 1/1 Running 0 0s
*源码地址*
1、公众号"Codee君"回复"每日一Go"获取源码
2、pan.baidu.com/s/1B6pgLWfS...
友情链接:加班费计算器(vx小程序搜索"加班计")
如果您喜欢这篇文章,请您(点赞、分享、亮爱心),万分感谢!