KWDB 数据库可高效处理海量且连续的数据流,但对于运维人员来说,根据业务需求进行硬件规划是确保系统稳定、高效运行的基础。本文将深入探讨 KWDB 集群规划,帮助运维人员从容应对数据增长和性能挑战,我们将从以下几个方面进行介绍:
- 拓扑结构:介绍 KWDB 数据库在延迟、弹性方面的考量。
- 硬件资源:介绍 KWDB 数据库在业务规模和性能角度,对 CPU、内存、存储和网络要求。
- 安全性:从安全方面,介绍 KWDB 集群规划时应该注意的事项。
拓扑结构
在计划部署时,应选择最能满足延迟和弹性要求的拓扑模式:
- 为了提高可用性和降低数据丢失的风险,建议在一台服务器上只运行一个节点。由于 KWDB 跨节点复制,如果一台计算机运行多个节点,当计算机发生故障会增加数据丢失的可能性。
- KWDB 集群模式下的数据副本数为3,为确保集群的稳定运行,需要保证集群中正常运行的节点数大于集群的副本数。
- 为保证 KWDB 集群正常运行,需要保证每个数据库节点都可以互相访问。
- KWDB 在面临节点故障时会自动进行数据迁移和补足,需要保证节点之间有足够的网络带宽。
综上,KWDB 建议每个节点都使用独立的服务器,在集群模式下至少有三个节点,各节点可以对等高速访问。
硬件资源
每个节点需要配备必要的 CPU、内存、网络和存储等资源。在部署集群前需要检查各个硬件设备。
下面列出了 KWDB 安装部署所需的硬件规格要求。在实际部署时,用户需要根据实际的业务规模和性能要求,进行硬件资源的规划。
CPU 和内存
单节点配置建议不低于4核8G。越高的 CPU 和内存意味着越好的数据读写、复杂工作负载、高并发和高性能场景表现。
同时,CPU 和内存应检查以下内容:
禁用 CPU 节能模式
在 X86 架构上,部分系统会模式使用 CPU 节能模式。为发挥最佳性能,需要配置为高性能模式来始终保持 CPU 在最高频率上工作。
检查系统 CPU 模式
cpupower frequency-info --policy
如果输出为The governor "powersave"则说明当前是节能模式,需要调整为性能模式 performance。
sudo nano /etc/systemd/system/cpupower.service
添加以下内容
[Unit]
Description=Set CPU performance governor
After=network.target[Service]
Type=oneshot
ExecStart=/usr/bin/cpupower frequency-set --governor performance
ExecStartPost=/bin/sleep 1
ExecStartPost=/usr/bin/cpupower frequency-set --governor performance
RemainAfterExit=yes[Install]
WantedBy=multi-user.target
启用服务
sudo systemctl daemon-reload
sudo systemctl enable cpupower.service
sudo systemctl start cpupower.service
使用 64K PAGE_SIZE 内核
在 ARM 架构上,因为其 TLB 较小,在高性能计算和数据库场景中,应当使用 page size 为 64K 的 Linux 内核,从而获得更好的性能。
getconf PAGE_SIZE
如果您的系统使用小于64K的内核,应进行内核切换,可以参考>>
Choosing between the arm64 and arm64+largemem installer options | Ubuntu
绑定 CPU
在部分国产 CPU 上,往往 Non-Uniform Memory Access (NUMA) 之间带宽是 CPU 的主要瓶颈,需要主动绑定 CPU 来发挥全部性能。
除此之外,如果 KWDB 和应用部署在同一个服务器上,为避免发生 CPU 争抢引发性能衰退,也需要进行绑定 CPU 来优化性能。
建议使用 numactl 来查看 NUMA 信息和绑定 CPU。numactl 是一个用于管理 NUMA 系统的工具。它可以用于查看 NUMA 配置,并将进程绑定到特定的 NUMA 节点或 CPU 上,从而优化性能。
- 查看 NUMA 节点的信息:
使用 numactl --hardware 或 lscpu 命令查看系统中的 NUMA 节点及其关联的 CPU 和内存信息:
numactl --hardware
或者:
lscpu
这将输出类似以下的信息:
available: 2 nodes (0-1) node 0 cpus: 0 1 2 3 4 5 6 7 node 0 size: 16384 MB node 0 free: 12000 MB node 1 cpus: 8 9 10 11 12 13 14 15 node 1 size: 16384 MB node 1 free: 12000 MB
这里显示了可用的 NUMA 节点,以及每个节点包含的 CPU 核心和内存信息。
- 绑定进程到特定的 NUMA 节点:
如果想将 KWDB 进程绑定到 NUMA 节点 0,可以使用以下命令:
numactl --cpunodebind=0 --membind=0 kwbase <args>
- 绑定进程到特定的 CPU:
如果想将 KWDB 进程绑定到特定的 CPU 核心(例如 CPU 0 和 CPU 1),可以使用以下命令:
numactl --physcpubind=0,1 kwbase <args>
存储
建议使用 Ext4 文件系统。同时,存储应检查以下内容:
检测并关闭系统 swap
关闭 swap 可以提升 KWDB 的性能,但可能会损失部分稳定性。
swapon --show
如果没有输出,表示没有启用的 swap。如果存在 swap,可以通过以下方式永久禁用:
编辑 /etc/fstab 文件,注释掉包含 swap 的行:
/swapfile none swap sw 0 0
重启系统永久生效。
调整I/O调度器为 noop
内核的 I/O 调度会导致性能损失,调整调度器为 noop 后,可以将 I/O 直接下发给硬件,从而获得更好的性能。
cat /sys/block/sdX/queue/scheduler
将 sdX 修改为您的磁盘(如 sda、sdb 等),如果为 deadline,则需要调整。
- 创建一个新的 udev 规则文件,例如 /etc/udev/rules.d/60-io-scheduler.rules:
sudo nano /etc/udev/rules.d/60-io-scheduler.rules
- 添加规则:
ACTION=="add|change", KERNEL=="sd[a-z]", ATTR{queue/scheduler}="noop"
这里,sd[a-z] 表示所有以 sd 开头的磁盘设备(如 sda、sdb 等)。您可以根据需要调整设备匹配模式。
3. 重新加载 udev 规则:
sudo udevadm control --reload-rules
- 应用新规则:
sudo udevadm trigger
磁盘容量
KWDB 推荐使用 SSD 或者 NVME 设备,尽量避免使用共享存储,确保至少 500 IOPS 和 30MB/s 处理效率。 KWDB 系统本身占用磁盘较小(<1GB),实际需求取决于业务量和开启的功能。
磁盘需求量可通过以下公式预估:
1、 压缩前空间:总存储空间=设备数量单台设备每天写入行数分区天数总分区数(行宽/1024/1024+15/64/分片可存储的最大数据行数/500/1000)/1024,单位为GB。
2、压缩后空间:总存储空间=设备数量单台设备每天写入行数分区天数总分区数(行宽/1024/1024/压缩比+15/64/分片可存储的最大数据行数/500/1000)/1024,单位为GB。
其中,分区天数取决于时序表的分区时间范围(PARTITION INTERVAL )设置。KWDB 默认每10天进行一次分区,分区天数的值即为10,如果建表时将分区时间范围设置为1mon, 则对应的分区天数为30。
总分区数取决于表的生命周期参数 RETENTIONS <keep_duration> 和分区时间范围(PARTITION INTERVAL )设置,例如,如果将表的生命周期设置为10天,分区天数使用默认值10天,则总分区数为1。如果没有设置生命周期参数和分区时间,则总分区数取决于业务周期。例如,如果需要存储一年的数据,总分区数将为37。
行宽为每行数据所有列占用空间的字节总数,各数据列所占用字节数如下:
数据类型 | 占用字节数 |
---|---|
第一列时间戳 | 16字节 |
BOOL | 1字节 |
INT2 | 2字节 |
INT4、FLOAT4 | 4字节 |
DOUBLE、TIMESTAMP、INT8 | 8字节 |
CHAR、BYTES | DDL中定义宽度 + 1 |
NCHAR | DDL中定义宽度*2 + 1 |
VARCHAR、VARBYTES | 8字节偏移宽度+平均内容宽度 |
分片可存储的最大数据行数为实时参数ts.blocks_per_shard.max_limit和ts.rows_per_block.max_limit的乘积,默认值为1000000。
压缩比通常大于等于10,实际压缩比取决于用户数据重复度,重复度越高,压缩比越高,重复度越低,压缩比越低。
假设某项目有1000台设备,每台设备每天写入行数为1000行,分区天数采用默认值10,表的生命周期设置为30天,每行数据占用的总字节数为913,分片可存储的最大数据行数为5000,压缩比为58,则压缩前的空间预计为10001000103(913/1024/1024+15/64/1000/10)/1024≈26 GB,压缩后占用的空间预计为10001000103(913/1024/1024/58+15/64/1000/10)/1024≈1.1 GB。
以下假设列出了不同规模数据库推荐配置的参数值和预计占用的压缩分区空间和活跃未压缩分区空间的合计大小:
- 表内有20个数据列;
- 每行数据的总宽度为500字节;
- 保存数据时间3年;
- 部署方式为单节点部署,如果是集群部署,预估空间时应乘以集群副本数;
- 压缩比为10:1。
√ 小型规模
设备数 | 数据写入速率 | 数据量 | 推荐配置 | 预估空间合计 |
---|---|---|---|---|
100 | 1条/分钟 | 14.4万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 100 ts.blocks_per_shard.max_limit: 1500 ts.rows_per_block.max_limit: 1000 时序表设置: PARTITION INTERVAL:10d ACTIVETIME:200d | 20 GB |
100 | 1条/10秒 | 86.4万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 100 ts.blocks_per_shard.max_limit: 5000 ts.rows_per_block.max_limit: 1000 时序表设置: PARTITION INTERVAL:5d ACTIVETIME:30d | 64 GB |
100 | 1条/秒 | 864万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 100 ts.blocks_per_shard.max_limit: 10000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:1000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:10d | 552 GB |
500 | 1条/分钟 | 72万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 8000 ts.rows_per_block.max_limit: 1000 - ts.mount.max_limit:1000 时序表设置: PARTITION INTERVAL:10d ACTIVETIME:60d | 61 GB |
500 | 1条/10秒 | 432万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 25000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:1000 时序表设置: PARTITION INTERVAL:5d ACTIVETIME:20d | 297 GB |
500 | 1条/秒 | 4320万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 50000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:1000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:5d | 2.6 TB |
1000 | 1条/分钟 | 144万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 8000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:1000 时序表设置: PARTITION INTERVAL:10d ACTIVETIME:30d | 102 GB |
1000 | 1条/10秒 | 864万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 25000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:2000 时序表设置: PARTITION INTERVAL:5d ACTIVETIME:10d | 551 GB |
1000 | 1条/秒 | 8640万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 50000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:2000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:3d | 5.2 TB |
√ 中型规模
设备数 | 数据写入速率 | 数据量 | 推荐配置 | 预估空间合计 |
---|---|---|---|---|
1万 | 1条/分钟 | 1440万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 886 GB |
1万 | 1条/10秒 | 8640万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 5.3 TB |
1万 | 1条/秒 | 86400万/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 52 TB |
10万 | 1条/分钟 | 1.44亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 8.5 TB |
10万 | 1条/10秒 | 8.64亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 50.6 TB |
10万 | 1条/秒 | 86.4亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 502 TB |
√ 大型规模
设备数 | 数据写入速率 | 数据量 | 推荐配置 | 预估空间合计 |
---|---|---|---|---|
50万 | 1条/分钟 | 7.2亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 75.3 TB |
50万 | 1条/10秒 | 43.2亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 251 TB |
50万 | 1条/秒 | 432亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 2510 TB |
100万 | 1条/分钟 | 14.4亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 150 TB |
100万 | 1条/10秒 | 86.4亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 502 TB |
100万 | 1条/秒 | 864亿/天 | 集群实时参数: ts.entities_per_subgroup.max_limit: 500 ts.blocks_per_shard.max_limit: 230000 ts.rows_per_block.max_limit: 1000 ts.mount.max_limit:5000 时序表设置: PARTITION INTERVAL:1d ACTIVETIME:2d | 5020 TB |
网络与时钟
网络会影响 KWDB 的业务通信和时钟的表现。因此应检查以下内容:
网络带宽
KWDB 需要足够的网络带宽来满足节点间数据通信需求。当因带宽不足引发策略性丢包、通信过长时,会影响节点心跳、业务重试等问题,从而降低集群稳定性和性能。
建议集群内使用万兆网卡保证足够的网络带宽。
网络抖动
KWDB 在集群模式下依赖时钟保证数据一致性,在节点时钟波动超过500ms时会产生异常。因此必须安装对时服务,并通过低网络抖动(jitter)来降低时钟波动。
例如 ,如果使用 NTP 网络对时,为保证 NTP 在当前集群网络下的时钟波动不超过500ms,在保证本地网络抖动较低的基础上,还可以通过如下方式保证时钟准确性:
- 选择更合适的稳定的时钟源
- 根据各节点的网络状态和性能,调整 NTP 服务器的权重
- 选择较稳定或精度较高的的对时协议(如 NTP4 或 PTP)
- 提高时间同步频率,使用 iburst 和调整 imnpoll maxpoll 选项
网络时延
KWDB 在集群模式下如果多节点间延迟达到100ms以上会处于不可用状态,建议保证各节点延迟在20ms以下
TCP 参数
KWDB 在集群模式下需要全对称高速网络来保证数据迁移和数据广播。当前版本下,KWDB 会使用基于 tcp 的 grpc 协议进行数据传递。因此,必要情况下,集群内对系统 tcp 参数进行优化,都可以提高 KWDB 的性能与稳定性。例如,修改以下 Linux 内核 TCP 参数:
# TCP 缓冲区大小
net.core.rmem_max = 16777216
net.core.wmem_max = 16777216
net.ipv4.tcp_rmem = 4096 87380 16777216
net.ipv4.tcp_wmem = 4096 65536 16777216# TCP 窗口自动调谐
net.ipv4.tcp_window_scaling = 1# TCP 内存设置
net.ipv4.tcp_mem = 50576 64768 98152# TCP 高效传输
net.ipv4.tcp_moderate_rcvbuf = 1
net.core.netdev_max_backlog = 250000# TCP 快速打开
net.ipv4.tcp_fastopen = 3
在使用4.9及以上版本的 Linux 内核时,应打开 BBR 来提高网络性能.
#网络队列调度
net.core.default_qdisc = fq#TCP拥塞算法
net.ipv4.tcp_congestion_control = bbr
或者选用6.8及以上版本的 Linux 内核,通过内核默认集成的 TCP 并发连接优化,获得更好的 TCP 性能, 点击参阅
安全性
非安全模式的集群存在严重的安全风险:
- 集群对所有客户端都是开放的,允许访问集群中任意节点的 IP 地址。
- 所有用户都可以在无需密码的情况下访问集群。
- 任何用户都可以以 root 用户身份访问集群,并对所有数据进行读写操作。
- 缺乏网络加密和认证机制,使得数据传输容易受到威胁。
因此,KWDB 强烈建议在部署时采用安全模式,通过TLS加密技术验证节点和客户端的身份,并对节点与客户端之间的数据传输进行加密,以有效防范未经授权的访问和数据篡改。