3. 数据库选型与配置优化(Cassandra)

在 ThingsBoard 高并发场景下,Cassandra 作为后端时序数据库与元数据存储,其数据模型设计、一致性级别选择、压缩策略及读写参数调优直接决定了平台吞吐量与延迟。本章从底层原理出发,给出可落地的配置方案。

3.1 Cassandra 数据模型设计

ThingsBoard 使用 Cassandra 存储设备遥测数据、属性与关系。核心设计原则是:按查询建表,避免跨分区扫描。

核心表结构示例:
-- 遥测数据表(按设备ID + 时间戳分区)
CREATE TABLE ts_kv_cf (
    entity_id uuid,
    key int,
    ts bigint,
    bool_v boolean,
    str_v text,
    long_v bigint,
    dbl_v double,
    PRIMARY KEY ((entity_id, key), ts)
) WITH CLUSTERING ORDER BY (ts DESC);

-- 最新遥测表(仅保留每个key的最新值)
CREATE TABLE ts_kv_latest_cf (
    entity_id uuid,
    key int,
    ts bigint,
    bool_v boolean,
    str_v text,
    long_v bigint,
    dbl_v double,
    PRIMARY KEY ((entity_id, key))
);
设计要点:
  • 分区键:使用 (entity_id, key) 组合,确保同一设备同一指标落在同一分区,避免跨节点查询。
  • 排序列:ts DESC 使最新数据排在分区头部,提升最近数据读取性能。
  • 避免大分区:单个分区建议不超过 100MB,可通过时间桶(如按天/小时拆分)控制分区大小。
Cassandra 数据模型分区与排序结构 Cassandra 数据模型:分区键 + 排序列 分区键 (entity_id, key) 排序列 ts DESC 数据行 bool_v / str_v / long_v / dbl_v 设计原则说明: • 分区键决定数据分布:同一设备同一指标的所有数据落在同一节点 • 排序列决定分区内顺序:ts DESC 使最新数据在分区头部,读取快 • 避免大分区:单分区 < 100MB,可通过时间桶拆分(如 ts_bucket) • 最新值表使用相同分区键,无排序列,直接覆盖写入

3.2 一致性级别选择

Cassandra 的一致性级别决定了读写操作的副本确认数量。ThingsBoard 默认使用 LOCAL_QUORUM,但在高并发场景下可针对性调整。

一致性级别 适用场景 延迟 数据一致性
LOCAL_QUORUM 默认读写,平衡一致性与性能 中等 强(多数副本确认)
LOCAL_ONE 高吞吐写入,可容忍少量丢失 低 弱(单副本确认)
EACH_QUORUM 多数据中心强一致 高 最强(每个DC多数确认)
ANY 极端写入性能,不保证持久化 极低 无(写入hinted handoff即可)
生产建议:
  • 写入:使用 LOCAL_QUORUM 或 LOCAL_ONE。LOCAL_ONE 可提升 30%-50% 写入吞吐,但需接受极端故障下的数据丢失风险。
  • 读取:使用 LOCAL_QUORUM 保证最新数据;对非关键查询可使用 LOCAL_ONE 降低延迟。
  • 避免:QUORUM(跨DC)和 ALL,它们会大幅增加延迟,不适合 IoT 高并发场景。

3.3 压缩策略

Cassandra 通过压缩减少磁盘占用与 I/O。ThingsBoard 的时序数据适合 TimeWindowCompactionStrategy (TWCS)。

压缩策略 适用场景 优势 劣势
SizeTieredCompactionStrategy (STCS) 通用负载 实现简单 空间放大,读放大
LeveledCompactionStrategy (LCS) 读密集型 读性能好,空间放大低 写放大高
TimeWindowCompactionStrategy (TWCS) 时序数据(推荐) 写放大低,自动过期 需合理设置窗口大小
TWCS 配置示例:
-- 创建表时指定 TWCS
CREATE TABLE ts_kv_cf (
    entity_id uuid,
    key int,
    ts bigint,
    bool_v boolean,
    str_v text,
    long_v bigint,
    dbl_v double,
    PRIMARY KEY ((entity_id, key), ts)
) WITH CLUSTERING ORDER BY (ts DESC)
  AND compaction = {
    'class': 'TimeWindowCompactionStrategy',
    'compaction_window_size': 1,
    'compaction_window_unit': 'HOURS',
    'min_threshold': 4,
    'max_threshold': 32
  }
  AND default_time_to_live = 2592000;  -- 30天自动过期
TWCS 调优要点:
  • 窗口大小:根据数据写入频率设置,通常 1 小时或 1 天。窗口内 SSTable 合并,窗口外不再合并。
  • TTL 配合:时序数据设置 default_time_to_live,TWCS 会自动删除过期 SSTable,无需手动清理。
  • min_threshold / max_threshold:控制窗口内触发压缩的 SSTable 数量,默认 4/32 适合大多数场景。

3.4 读写性能调优参数

Cassandra 的 JVM 堆、磁盘 I/O、并发读写等参数直接影响 ThingsBoard 吞吐。以下为生产环境推荐配置。

参数 默认值 推荐值 说明
concurrent_reads 32 64-128 增加读并发,适合高查询场景
concurrent_writes 32 64-128 增加写并发,适合高写入场景
memtable_allocation_type heap_buffers offheap_buffers 减少GC压力,提升写入吞吐
memtable_heap_space_in_mb 1/4 heap 512-1024 根据写入量调整,避免OOM
commitlog_sync periodic periodic 保持periodic,降低写延迟
commitlog_sync_period_in_ms 10000 2000-5000 缩短同步周期,减少数据丢失窗口
file_cache_size_in_mb 512 1024-2048 增加文件缓存,提升读性能
JVM 堆配置:
  • 堆大小建议为系统内存的 1/4,不超过 8GB(避免GC停顿)。
  • 使用 G1GC 垃圾回收器:-XX:+UseG1GC,并设置 -XX:MaxGCPauseMillis=200。
  • 启用 off-heap 内存:memtable_allocation_type: offheap_buffers 减少堆压力。
Cassandra 读写性能调优参数关系 Cassandra 读写性能调优参数关系 Cassandra 引擎 读写路径核心 concurrent_writes 64-128 memtable_allocation offheap_buffers commitlog_sync_period 2000-5000ms concurrent_reads 64-128 file_cache_size 1024-2048 MB JVM 堆 + G1GC ≤8GB, MaxGCPause=200ms 写入路径优化 • 提高写并发 • 使用 off-heap 减少 GC • 缩短 commitlog 同步周期 读取路径优化 • 提高读并发 • 增加文件缓存 • 优化 JVM 堆与 GC

3.5 生产环境配置清单

以下为 ThingsBoard 生产环境 Cassandra 配置清单,可直接用于 cassandra.yaml 调整。

cassandra.yaml 关键配置:
# 并发设置
concurrent_reads: 64
concurrent_writes: 64
concurrent_counter_writes: 32

# 内存与缓存
memtable_allocation_type: offheap_buffers
memtable_heap_space_in_mb: 512
memtable_offheap_space_in_mb: 512
file_cache_size_in_mb: 1024

# 提交日志
commitlog_sync: periodic
commitlog_sync_period_in_ms: 2000
commitlog_segment_size_in_mb: 32

# 压缩与GC
compaction_throughput_mb_per_sec: 64
concurrent_compactors: 4

# 超时设置
read_request_timeout_in_ms: 5000
write_request_timeout_in_ms: 5000
request_timeout_in_ms: 10000
验证与监控:
  • 使用 nodetool cfstats 查看各表读写延迟与分区大小。
  • 使用 nodetool tpstats 监控线程池积压情况。
  • 关注 Pending Tasks 指标,若持续增长需增加并发或优化查询。

通过以上数据模型设计、一致性级别选择、TWCS 压缩策略及读写参数调优,ThingsBoard 可在单集群支撑百万级设备接入与每秒数十万次数据写入,同时保持亚秒级查询延迟。