时间戳谁来打:设备时钟漂移与对时方案
时间错了,所有按时间聚合的结果都会错,而且很难发现。本文说明时钟漂移有多大、对时该怎么做、以及设备没有电池供电的实时时钟时怎么办。
- 时间错了不会报错,数据照常入库,往往几个月后才被发现。
- 普通晶振每天可能偏差数秒,温差会放大偏差,同批设备会在时间轴上逐渐散开。
- 开机对一次之后不再对时是常见错误,漂移是持续发生的。
- 没有实时时钟的设备在对时成功前不应上报,更不能用默认时间填充。
- 平台应对时间戳做合理性检查并留下记录,而不是静默接受。
时间问题的麻烦之处在于它不会报错。设备时钟慢了两小时,数据照常入库、曲线照常绘制,只是峰值出现在错误的位置、告警在错误的时刻触发、按小时的统计把两个小时的数据合并到了一起。等到有人发现对不上,往往已经积累了几个月的脏数据。
漂移有多大
普通晶振的频率偏差通常以百万分之几十计,换算下来每天可能偏差数秒;温度变化会放大这个偏差,而户外设备正好经历大幅温差。几秒听起来不多,但一年累积下来就是可观的量,而且不同设备偏的方向还不一样 —— 同一批设备的数据在时间轴上会逐渐散开。
对时的几种做法
- 网络对时协议:设备直接向时间服务器同步,精度足够,前提是网络允许对应端口通过,部分企业网络会屏蔽;
- 随业务报文对时:平台在下行响应里带上服务端时间,设备据此校准。不需要额外端口,实现简单,精度受往返时延影响但对多数场景够用;
- 网关代授时:终端设备不联公网,由网关统一对时后再下发给终端,适合现场总线结构。
对时时机比对时方式更容易出错。常见做法是开机对一次,然后再也不管 —— 而漂移是持续的。合理的做法是开机对一次,之后按固定周期重对,周期根据晶振精度和业务容忍度确定,通常以小时或天计。
没有实时时钟芯片的设备
成本敏感的设备可能没有带电池的实时时钟,断电后时间归零。这类设备重新上电时,在对时成功之前采集的数据带着错误时间。处理办法有两种:缓存但不上报,等对时成功后统一补上正确时间;或者上报时明确标记「时间未同步」,由平台决定如何处理。
不可接受的做法是用一个默认时间(比如 1970 年或固件编译时间)上报。这类数据混进时序库之后,查询的时间范围会被拉到很远,部分存储引擎的分区策略也会因此产生大量空分区。
平台侧的兜底
平台应当对收到的时间戳做合理性检查:明显早于设备投产日期的、超出当前时间一定范围的,都应当标记出来而不是静默接受。标记之后的处理方式取决于业务 —— 可以拒收、可以入库但打标、可以用接收时间替代并记录替代事实。关键是这件事要有记录,否则后续没人能解释那段数据为什么不对。
这一项和断网补传是配套的:补传依赖设备自己打的时间戳,而时间戳的可信度依赖对时。只做补传不做对时,补回来的数据时间仍然是错的。现场总线结构下由网关统一授时更常见,这类部署形态在制造业项目里占多数。
常见问题
物联网设备多久对一次时?
取决于晶振精度与业务容忍度。日常做法是开机对一次,之后以小时或天为周期重对。如果业务要求跨设备的数据能在秒级对齐,周期要相应缩短,并在验收时实测多台设备的时间偏差。
设备没有 RTC 怎么保证时间正确?
断电后时间归零的设备,应当在对时成功之前只缓存不上报,或者上报时明确标记时间未同步。绝不要用编译时间或 1970 年这类默认值填充,这会污染时序库并可能导致大量空分区。
用服务端接收时间代替设备时间行不行?
正常在线时偏差有限,但设备断网补传时会把一整段历史数据挤到恢复的那一刻,曲线和统计全部失真。可以作为对时失败时的兜底,但必须记录下来这条数据用的是替代时间。
参考资料
- 物联网平台产品文档 · 阿里云
- 物联网通信 IoT Hub 产品文档 · 腾讯云