Google Health API 中的数据管理

在 Google Health API 中处理数据,从根本上来说就是在云端 Google Health API 数据存储区与您自己的应用或后端数据存储区之间同步数据的循环过程。不过,此周期可能会因多种因素而呈现不同的形式:

  • 您是否正在将数据写入 Google Health API?仅读取?还是两者兼而有之?
  • 您的数据存储区是位于应用或设备本地吗?还是在您自己的云中?
  • 您是否需要在用户应用和穿戴式设备之间同步 Google Health API 数据?您多久同步一次设备?
  • 您要处理的是什么类型的数据?基本统计信息?度量单位? 采样率不同的时间序列?
  • 您是否计划在应用处于后台时读取数据?
  • 您是否计划使用应用获得用户权限之前记录的历史数据?

如需了解这些内容如何整合在一起,请查看 Google Health API 同步生命周期。此生命周期有两个版本:标准版(读写)和只读版。

标准同步生命周期

Google Health API 中的标准同步生命周期
图 1:Google Health API 中的标准同步生命周期

与 Google Health API 集成意味着将数据复制到应用或后端数据存储区。为便于在本文档中使用,我们将此数据存储区称为开发者数据存储区

这里的“复制”可以指任何离散活动,例如从 Google Health API 读取数据(复制到开发者数据存储区)或向 Google Health API 写入数据(复制到 Google Health API)。以特定顺序重复执行这些操作就是同步生命周期。

图 1 展示了涉及读取和写入操作的标准同步生命周期,而未考虑之前提及的任何因素。

写入

  1. 准备要写入的新数据 - 从外部设备或应用转移数据,并将数据点格式化为与 Google 健康数据 API 数据类型兼容的 JSON 表示形式。请注意,健康数据 API 目前不支持为写入操作指定自定义的客户端分配 ID。此类 ID 可能会在 POST 中提供,但会被忽略。
  2. 更新插入记录 - 使用 REST 端点向 Google Health API 提交数据点。使用 POST 创建记录,使用 PATCH 插入和更新现有记录。PATCH 操作所需的 ID 将来自之前的 POST 操作(之前周期中的下一步)。
  3. 处理返回的资源 ID - 使用服务器生成的 ID 时,请提取并持久保存服务器返回的资源 name 或 ID,以便日后进行更新 (PATCH) 或删除 (DELETE)。如需详细了解这两种类型,请参阅标识策略

读取

  1. 读取记录 - 使用 REST 端点(GET,带有 filter 查询参数和 pageToken 分页,或 rollUpdailyRollUp 等聚合端点)从 Google Health API 中提取新数据和现有数据的更改,或使用 Webhook 订阅 (projects.subscribers) 接收实时通知。通知仅指示有新数据可用,而不指示实际数据是什么。
  2. 协调开发者数据存储区 - 将新数据和更新后的数据与开发者数据存储区进行协调。在同步期间,关联的设备可能会生成重叠的时间间隔。如需了解 Google Health API 如何解决这些问题,请参阅时间间隔时间戳和已连接的设备同步

然后,此循环会根据外部设备或应用的具体需求以适当的间隔重复进行。我们通常建议按以下顺序在您自己的数据存储区和 Google Health API 之间同步数据。

识别策略

如果您打算将数据写入 Google Health API,那么在构建与 Google Health API 的集成之前,您必须在创建数据点(数据的基本单位)时选择资源标识策略。

健康数据 API 目前不支持为写入操作分配客户端 ID。 此类 ID 可能会在 POST 中提供,但会被忽略。此处提供了有关此选项的详细信息,仅供参考。

  1. 服务器生成的 ID(默认选项):客户端提交不含 ID 的数据,Google Health API 后端会生成并返回唯一的系统标识符。
  2. 客户端分配的自定义 ID(根据 AIP-133,尚未支持):客户端应用生成一个唯一标识符(例如 UUID 或本地数据库主键),并在创建时将其提供在资源路径中。

下表比较了这两种识别策略,可帮助您为集成选择合适的方法:

功能 服务器生成的 ID 客户分配的自定义 ID
ID 生成 服务器在 POST 执行期间生成随机系统 ID。 客户端在写入之前在本地生成稳定 ID(UUID v4 / 内部主键)。
资源路径 .../dataPoints/{server_id}(在响应中返回) .../dataPoints/{custom_id}
写入后本地步骤 必需。必须将返回的 server_id 存储在本地数据库中,以便日后进行更新/删除。 否。应用已拥有相应 ID。
ID 映射表 必需。客户端必须维护双向映射(local_idserver_id)。 不需要。客户端直接使用自己的主密钥。
重试行为(网络较弱) 存在重复风险。重试超时的 POST 会创建具有新服务器 ID 的重复记录。 安全且幂等。使用相同的 custom_id 重试 POST 可防止重复创建(返回 409 ALREADY_EXISTS)。
离线同步支持 受限。必须等待服务器响应以获取正式资源 ID,然后才能引用这些 ID。 完整版。您可以使用稳定的 ID 离线创建和更改实体,然后在重新连接到网络时无缝同步。
格式限制 完全由服务器处理。 必须遵循 ^[a-z0-9-]{4,63}$(4-63 个小写字母、数字和连字符)。
适用场景

在以下情况下,请选择服务器生成的 ID:

  • 您的应用是只写 / 追加模式(例如发送遥测数据或步数,这些数据之后不会更新或删除)。
  • 您的应用不会维护包含各个数据点的本地永久性数据库。
  • 您希望简单易用,无需管理字符串验证限制条件(例如 4-63 个字符)。

如果符合以下条件,请选择自定义 ID:

  • 您运营的是一款双向同步应用,该应用可在设备之间读取、写入和更新健康记录。
  • 您的应用具有一个本地数据库(例如 Room 或 SQLite),用于存储具有本地主键的记录。
  • 用户在离线状态下或通过间歇性移动连接记录数据,此时需要进行安全重试。
  • 您希望消除后端数据库与 API 之间的 ID 映射表。

只读同步生命周期

Google Health API 中的只读同步生命周期
图 2:Google Health API 中的只读同步生命周期

如果应用仅打算从 Google Health API 读取数据,则必须将数据复制到其开发者数据存储区,并处理生命周期的协调部分。

阅读部分中介绍的任务也适用于此处。

图 2 展示了只读生命周期。

间隔时间戳和已连接的设备同步

间隔数据表示在一段时间内收集的测量数据,例如步数、心率或锻炼时段。相比之下,时间点测量包括手动输入的数据,例如饮食记录或体重秤读数。间隔数据通常源自同步的已连接设备,例如智能手表和运动手环。

处理区间数据时,区间时间戳(startTimeendTime)会带来独特的行为。本部分将说明重叠区间出现的原因,并比较 listreconcile 端点。

来自关联设备的重叠时间段

Fitbit 手环和 Google Pixel Watch 等关联设备在佩戴时会持续收集高频生物识别数据。设备将数据点同步到 Google Health 后,不会追溯性地更改这些现有记录。 其存储的间隔时间戳保持不变。

不过,在后续同步周期之前,设备端算法通常会重新解读原始传感器遥测数据。设备会重新划分在之前数小时内收集的读数。当设备再次同步时,它会上传新的数据点。它们的开始和结束边界可以与之前存储的间隔重叠。

例如,假设某用户佩戴智能手表,其活动数据以两个连续批次同步:

  1. 在首次同步期间,设备会上传一个涵盖 10:00:00Z10:14:59Z 的数据点。
  2. 在设备上重新计算后,第二次同步会上传另一个涵盖 10:14:00Z10:28:59Z 的数据点。

这两条记录会分别存储在 Google Health 后端中。因此,这两个数据点都涵盖了从 10:14:00Z10:14:59Z 的时间间隔。在查询原始记录时,这会产生 59 秒的重叠。

比较列表并协调端点

您可以使用 listreconcile 端点处理这些重叠的时间段。选择符合应用要求的端点:

功能 list 个端点 reconcile 个端点
HTTP 方法 GET https://health.googleapis.com/v4/users/me/dataTypes/<var>dataType</var>/dataPoints GET https://health.googleapis.com/v4/users/me/dataTypes/<var>dataType</var>/dataPoints:reconcile
重叠行为 返回所有存储的记录,并将其标记为已上传,但不进行重复数据删除。如果时间区间重叠,则返回两条记录。 解决冲突,并对设备和同步会话中的重叠记录进行去重处理,然后将这些记录合并为单个连续的数据流。
优点 提供每部设备和每个同步批次上传的每条记录的完整、未修改的审核跟踪记录。 通过自动处理重叠的时间区间和多设备冲突,简化时间轴渲染和时长计算。
缺点 您的应用负责检测和解决重叠的时间段、多设备冲突和摘下手环的时间段。 响应中会省略重叠的下级记录,因此无法单独审核各个设备的同步批次。

reconcile 端点旨在用于绘制用户界面、呈现活动时间轴和计算不重叠的总时长。它会解决重新分桶的同步会话中的冲突间隔。它还会协调在多部设备(例如手表和手机)上同时记录的活动。

对账通过选择权威记录(而非合成人工时间并集)来解决冲突的会话。例如,它不会将 11:00:00Z11:30:00Z11:20:00Z11:50:00Z 合并为 11:00:00Z11:50:00Z。协调后的响应会返回获胜的数据点及其原始记录间隔。这样可以保持相应会话的已衡量遥测数据和指标的完整性。

图 3 说明了 reconcile 端点如何处理重叠的会话。它会选择权威记录,而不是创建人为的时间并集。

解决重叠区间:协调端点去重与人工时间并集合并
图 3:冲突会话调解与人工时间并集合并

Endpoints 指南提供了完整的请求和响应示例。如需比较原始 list 记录与 reconcile 输出,请参阅获取协调一致的间隔数据视图

list 端点专为设备诊断和数据审核而设计。当工作流需要检查每部设备上传的未修改记录时,请使用此方法。使用 list 进行查询时,客户端逻辑必须处理原始数据中的任何时间段重叠。

时间戳可变性和所有者更新

在正常同步周期内,已连接的设备不会追溯修改存储的时间戳。不过,区间时间戳(startTimeendTime)并非在所有数据源中都保持不变。只有记录的原始创建者或所有者才能修改其字段。其他应用无法修改其未创建的数据点。

所有者应用可以使用 patch 端点来更新其现有记录。这包括修改开始或结束时间戳。 如需查看使用 PATCH 更新时间戳的示例,请参阅 Endpoints 指南中的更新现有数据的时间段时间戳

同样,从外部平台(例如“健康数据共享”或合作伙伴应用)同步的数据点会继承来自原始来源的更新。当原始应用修改现有记录时,这些更新会传播到 Google 健康。