На этой странице представлен обзор соглашений REST API, а также указатель распространенных задач Google Health API и примеры их выполнения.
Соглашения REST API
API Google Health соответствует стандартам Google API Improvement Proposals (AIP) , в частности AIP-127 (транскодирование HTTP и gRPC) и AIP-131–AIP-135 (стандартные методы). Эти стандарты определяют, как данные сопоставляются из протосообщения с HTTP-запросом.
Параметры запроса
Параметры запроса используются, когда данные являются частью URL-адреса. Это в основном относится к запросам GET (получение ресурса) или запросам LIST (фильтрация/пагинация), но также используется для операций DELETE .
- Размещение : Добавляется к URL-адресу после знака вопроса (
?. - Синтаксис : Пары ключ-значение, разделенные символом
&. - Сопоставление : Каждое поле в сообщении запроса, не являющееся частью шаблона пути URL, сопоставляется с параметром запроса.
- Лучше всего подходит для : простых типов данных (строки, целые числа, перечисления) и повторяющихся полей.
Пример синтаксиса:
GET https://health.googleapis.com/v4/users/me/dataTypes/data-type/dataPoints?page_size=10&filter=data_type.interval.start_time >= "2025-10-01T00:00:00Z"
Текст запроса
Тело запроса используется, когда данные изменяют состояние ресурса или слишком велики для URL-адреса. Обычно тело представляет собой JSON-представление самого ресурса. Как правило, используется для операций POST , PATCH и PUT .
- Размещение : Внутри HTTP-запроса (не виден в URL).
- Синтаксис : Отформатировано как JSON-объект.
- Сопоставление : определено в аннотации
google.api.http.-
body: "*"означает, что всё сообщение является его содержанием. -
body: "resource_name"означает, что только определенное поле в протоколе является телом.
-
- Наилучшее применение : сложные объекты, вложенные сообщения и конфиденциальные данные.
Пример синтаксиса:
POST https://health.googleapis.com/v4/users/me/dataTypes/data-type/dataPoints:rollUp
Content-Type: application/json
{
"range": {
"startTime": "2025-11-05T00:00:00Z",
"endTime": "2025-11-13T00:00:00Z"
},
"windowSize": "3600s"
}Гибридный случай
В методе Update соответствующем стандарту AIP-134, или в операции PATCH используются оба подхода. URL-адрес содержит имя ресурса, тело запроса содержит обновленные данные ресурса, а параметр запроса (обычно update_mask ) указывает, какие поля следует изменить.
PATCH https://health.googleapis.com/v4/projects/project-id/subscribers/subscriber-id
Content-Type: application/json
{
"endpointUri": "https://myapp.com/new-webhooks/health"
}
Основные отличия с первого взгляда
| Особенность | Параметры запроса | Текст запроса |
|---|---|---|
| Руководство AIP | Используется для поиска, фильтрации и операций чтения. | Используется для операций записи. |
| Видимость | Видно в истории браузера и журналах сервера. | Скрыто в URL-адресе. |
| Сложность | Ограничено плоскими или повторяющимися структурами. | Поддерживает глубоко вложенные JSON-объекты. |
| Кодирование | Необходимо закодировать в формате URL (например, пробелы становятся %20 ). | Стандартное кодирование JSON. |
Даты
Все даты в API Google Health отображаются в формате YYYY-MM-DD . API Nutrition поддерживает стандарт ISO-8601 для значений дат при соблюдении следующих условий:
- Четырехзначный год
YYYY - Годовые значения находятся в диапазоне 0000-9999
- Не применяется ограничение дат начала, предусмотренное стандартом ISO-8601 или другими эпохами.
Заголовки
Для выполнения запросов к API Google Health необходимо использовать соответствующие заголовки и токен доступа. Для запросов GET и POST рекомендуется использовать следующий заголовок:
Authorization: Bearer access-token Accept: application/json
индекс задач API
В этом разделе представлен указатель распространенных задач API Google Health и примеры выполнения каждой из них.
Получите идентификатор пользователя Fitbit или Google.
После того, как пользователь дает согласие через Google OAuth 2.0, ответ с токеном не содержит идентификатор пользователя Fitbit или Google. Чтобы получить идентификатор пользователя, вызовите конечную точку getIdentity . getIdentity возвращает как устаревший идентификатор пользователя Fitbit, так и идентификатор пользователя Google.
Мы рекомендуем, чтобы сразу после получения согласия нового пользователя через OAuth, вы вызывали конечную точку getIdentity и сохраняли оба идентификатора пользователя. Это обеспечит обратную и прямую совместимость вашей интеграции.
Например:
Запрос
GET https://health.googleapis.com/v4/users/me/identity Authorization: Bearer access-token Accept: application/json
Ответ
{
"name": "users/me/identity",
"legacyUserId": "A1B2C3",
"healthUserId": "111111256096816351"
}Получайте внутридневные или подробные данные, собранные в течение дня.
Используйте конечную точку list для определенного типа данных, чтобы получить внутридневные или подробные данные, собранные в течение дня с поддерживаемыми интервалами для этого типа данных.
Например:
Запрос
GET https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints Authorization: Bearer access-token Accept: application/json
Ответ
{
"dataPoints": [
{
"dataSource": {
"recordingMethod": "PASSIVELY_MEASURED",
"device": {
"manufacturer": "",
"displayName": "Charge 6"
},
"platform": "FITBIT"
},
"steps": {
"interval": {
"startTime": "2026-03-04T07:05:00Z",
"startUtcOffset": "0s",
"endTime": "2026-03-04T07:06:00Z",
"endUtcOffset": "0s",
"civilStartTime": {
"date": {
"year": 2026,
"month": 3,
"day": 4
},
"time": {
"hours": 7,
"minutes": 5
}
},
"civilEndTime": {
"date": {
"year": 2026,
"month": 3,
"day": 4
},
"time": {
"hours": 7,
"minutes": 6
}
}
},
"count": "40"
}
},
...
],
"nextPageToken": "Xm5h-6L0viZxIlRuWjx5bmvy98zj85uG34tuMn16mu2pntsnZI32iqhq"
}Фильтрация данных по интервалу времени начала гражданских работ.
Используйте конечную точку list с параметром filter для фильтрации данных по гражданскому времени или интервалу.
Например:
Запрос
GET https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints?filter=steps.interval.civil_start_time >= "2026-03-04T00:00:00" Authorization: Bearer access-token Accept: application/json
Ответ
{
"dataPoints": [
{
"dataSource": {
"recordingMethod": "PASSIVELY_MEASURED",
"device": {
"manufacturer": "",
"displayName": "Charge 6"
},
"platform": "FITBIT"
},
"steps": {
"interval": {
"startTime": "2026-03-04T07:05:00Z",
"startUtcOffset": "0s",
"endTime": "2026-03-04T07:06:00Z",
"endUtcOffset": "0s",
"civilStartTime": {
"date": {
"year": 2026,
"month": 3,
"day": 4
},
"time": {
"hours": 7,
"minutes": 5
}
},
"civilEndTime": {
"date": {
"year": 2026,
"month": 3,
"day": 4
},
"time": {
"hours": 7,
"minutes": 6
}
}
},
"count": "40"
}
...
],
"nextPageToken": "Xm5h-6L0viZxIlRuQjp5bml1bZ4ve2dhNmZvMnt4Yn7qIGQhbHN3YQ"
}Фильтрация данных по времени наблюдения выборки
Используйте конечную точку list с параметром filter для фильтрации данных по времени наблюдения образца.
Например:
Запрос
GET https://health.googleapis.com/v4/users/me/dataTypes/body-fat/dataPoints?filter=body_fat.sample_time.physical_time >= "2026-03-01T00:00:00Z" Authorization: Bearer access-token Accept: application/json
Ответ
{
"dataPoints": [
{
"name": "users/2515055256096816351/dataTypes/body-fat/dataPoints/1234567890",
"dataSource": {
"recordingMethod": "UNKNOWN",
"application": {
"packageName": "",
"webClientId": "",
"googleWebClientId": "google-web-client-id"
},
"platform": "GOOGLE_WEB_API"
},
"-->bodyFat<--": {
"sampleTime": {
"physicalTime": "2026-03-10T10:00:00Z",
"utcOffset": "0s",
"civilTime": {
"date": {
"year": 2026,
"month": 3,
"day": 10
},
"time": {
"hours": 10
}
}
},
"percentage": 20
}
}
"nextPageToken": ""
}Фильтрация данных по источникам данных, таким как носимые устройства.
Используйте конечную точку reconcile для получения данных для определенного "семейства источников данных". Для этого укажите параметр dataSourceFamily в качестве параметра запроса.
В таблице ниже описаны поддерживаемые параметры dataSourceFamily :
| Вариант | Описание |
|---|---|
users/me/dataSourceFamilies/all-sources | Значение по умолчанию. Включает данные из всех доступных источников. |
users/me/dataSourceFamilies/google-wearables | Включает данные с устройств отслеживания местоположения Google и Fitbit (таких как трекеры Fitbit и часы Pixel Watch). Исключает данные, введенные вручную. |
users/me/dataSourceFamilies/google-sources | Включает собственные данные Google, такие как данные с устройств слежения и данные, внесенные вручную. |
Вот пример фильтрации только данных о сне, записанных трекером за сутки после 03.03.2026:
Запрос
GET https://health.googleapis.com/v4/users/me/dataTypes/sleep/dataPoints:reconcile?dataSourceFamily=users/me/dataSourceFamilies/google-wearables&filter=sleep.interval.civil_end_time >= "2026-03-03" Authorization: Bearer access-token Accept: application/json
Ответ
{
"dataPoints": [
{
"name": "users/2515055256096816351/dataTypes/sleep/dataPoints/2724123844716220216",
"dataSource": {
"recordingMethod": "DERIVED",
"device": {
"displayName": "Charge 6"
},
"platform": "FITBIT"
},
"sleep": {
"interval": {
"startTime": "2026-03-03T20:57:30Z",
"startUtcOffset": "0s",
"endTime": "2026-03-04T04:41:30Z",
"endUtcOffset": "0s"
},
"type": "STAGES",
"stages": [
{
"startTime": "2026-03-03T20:57:30Z",
"startUtcOffset": "0s",
"endTime": "2026-03-03T20:59:30Z",
"endUtcOffset": "0s",
"type": "AWAKE",
"createTime": "2026-03-04T04:43:40.937183Z",
"updateTime": "2026-03-04T04:43:40.937183Z"
},
…
{
"startTime": "2026-03-04T04:07:30Z",
"startUtcOffset": "0s",
"endTime": "2026-03-04T04:41:30Z",
"endUtcOffset": "0s",
"type": "AWAKE",
"createTime": "2026-03-04T04:43:40.937183Z",
"updateTime": "2026-03-04T04:43:40.937183Z"
}
],
"metadata": {
"stagesStatus": "SUCCEEDED",
"processed": true,
"main": true
},
"summary": {
"minutesInSleepPeriod": "464",
"minutesAfterWakeUp": "0",
"minutesToFallAsleep": "0",
"minutesAsleep": "407",
"minutesAwake": "57",
"stagesSummary": [
{
"type": "AWAKE",
"minutes": "56",
"count": "12"
},
{
"type": "LIGHT",
"minutes": "198",
"count": "19"
},
{
"type": "DEEP",
"minutes": "114",
"count": "10"
},
{
"type": "REM",
"minutes": "94",
"count": "4"
}
]
},
"createTime": "2026-03-04T04:43:40.337983Z",
"updateTime": "2026-03-04T04:43:40.937183Z"
}
}
],
"nextPageToken": ""
}Сводные данные за определенный период времени.
Используйте конечную точку rollUp для возврата агрегированных данных за временной интервал в секундах, в диапазоне datetime , соответствующем физическому времени пользователя (в формате UTC).
При вызове конечной точки rollUp необходимо указать в теле запроса требуемый диапазон дат в гражданском времени пользователя. Например:
Запрос
POST https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints:rollUp
Authorization: Bearer access-token
Accept: application/json
{
"range": {
"startTime": "2026-02-17T17:00:00Z",
"endTime": "2026-02-17T17:59:59Z"
},
"windowSize": "30s"
}Ответ
{
"rollupDataPoints": [
{
"startTime": "2026-02-17T17:55:00Z",
"endTime": "2026-02-17T17:55:30Z",
"steps": {
"countSum": "41"
}
},
{
"startTime": "2026-02-17T17:54:00Z",
"endTime": "2026-02-17T17:54:30Z",
"steps": {
"countSum": "31"
}
},
...
]
}Агрегировать данные за один или несколько дней.
Конечная точка dailyRollUp используется, когда необходимо агрегировать данные за один или несколько дней ( windowSize ). В теле запроса укажите диапазон закрытого и открытого гражданского времени для требуемого интервала. В зависимости от типа данных вы получите либо сумму, либо среднее значение за интервал.
Например:
Запрос
POST https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints:dailyRollUp
Authorization: Bearer access-token
Accept: application/json
{
"range": {
"start": {
"date": {
"year": 2026,
"month": 2,
"day": 26
},
"time": {
"hours": 0,
"minutes": 0,
"seconds": 0,
"nanos": 0
}
},
"end": {
"date": {
"year": 2026,
"month": 2,
"day": 26
},
"time": {
"hours": 23,
"minutes": 59,
"seconds": 59,
"nanos": 0
}
}
},
"windowSizeDays": 1
}Ответ
{
"rollupDataPoints": [
{
"civilStartTime": {
"date": {
"year": 2026,
"month": 2,
"day": 26
},
"time": {}
},
"civilEndTime": {
"date": {
"year": 2026,
"month": 2,
"day": 26
},
"time": {
"hours": 23,
"minutes": 59,
"seconds": 59
}
},
"steps": {
"countSum": "3822"
}
}
]
}Вставить или обновить данные о здоровье пользователя
Используйте конечную точку patch для добавления или обновления данных пользователя в приложении Fitbit.
Вот пример, когда пользователь зафиксировал процент жира в организме на весах "HumanScale" от компании "Scales R Us". Новое показание процента жира в организме пользователя составляет 20% на 10 марта 2026 года.
Запрос
PATCH https://health.googleapis.com/v4/users/me/dataTypes/body-fat/dataPoints/1234567890
Authorization: Bearer access-token
content-length: 329
{
"name": "bodyFatName",
"dataSource": {
"recordingMethod": "ACTIVELY_MEASURED",
"device": {
"formFactor": "SCALE",
"manufacturer": "Scales R Us",
"displayName": "HumanScale"
}
},
"bodyFat": {
"sampleTime": {
"physicalTime": "2026-03-10T10:00:00Z"
},
"percentage": 20
}
}Ответ
{
"done": true,
"response": {
"@type": "type.googleapis.com/google.devicesandservices.health.v4main.DataPoint",
"name": "users/2515055256096816351/dataTypes/body-fat/dataPoints/1234567890",
"dataSource": {
"recordingMethod": "ACTIVELY_MEASURED",
"device": {
"formFactor": "SCALE",
"manufacturer": "Scales R Us",
"displayName": "HumanScale"
},
"application": {
"googleWebClientId": "618308034039.apps.googleusercontent.com"
},
"platform": "GOOGLE_WEB_API"
},
"bodyFat": {
"sampleTime": {
"physicalTime": "2026-03-10T10:00:00Z"
},
"percentage": 20
}
}
}Зарегистрируйте продукт питания
Для регистрации информации о продукте питания отправьте POST запрос на конечную точку данных nutrition-log . Тело запроса содержит объект DataPoint с объектом nutritionLog . Для получения дополнительной информации см. руководство по питанию .
Например:
Запрос
POST https://health.googleapis.com/v4/users/me/dataTypes/nutrition-log/dataPoints
Authorization: Bearer access-token
Content-Type: application/json
{
"nutritionLog": {
"interval": {
"startTime": "2026-06-16T12:00:00Z",
"endTime": "2026-06-16T12:30:00Z"
},
"foodDisplayName": "Banana",
"mealType": "LUNCH",
"energy": {
"kcal": 105
},
"totalCarbohydrate": {
"grams": 27
},
"totalFat": {
"grams": 0.3
}
}
}Ответ
{
"done": true,
"response": {
"@type": "type.googleapis.com/google.devicesandservices.health.v4.DataPoint",
"name": "users/2515055256096816351/dataTypes/nutrition-log/dataPoints/567890",
"dataSource": {
"recordingMethod": "ACTIVELY_MEASURED",
"platform": "GOOGLE_WEB_API"
},
"nutritionLog": {
"interval": {
"startTime": "2026-06-16T12:00:00Z",
"startUtcOffset": "0s",
"endTime": "2026-06-16T12:30:00Z",
"endUtcOffset": "0s"
},
"energy": {
"kcal": 105
},
"totalCarbohydrate": {
"grams": 27
},
"totalFat": {
"grams": 0.3
},
"mealType": "LUNCH",
"foodDisplayName": "Banana"
}
}
}Удаление данных о состоянии здоровья пользователя
Используйте конечную точку batchDelete для удаления массива данных пользователя из приложения Fitbit.
Вот пример, когда пользователь ранее зафиксировал процент жира в организме на весах, но хочет удалить эту запись. Используя user-id и data-point-id из исходного действия вставки:
Запрос
POST https://health.googleapis.com/v4/users/me/dataTypes/body-fat/dataPoints:batchDelete
Authorization: Bearer access-token
Accept: application/json
content-length: 93
{
"names": [
"users/2515055256096816351/dataTypes/body-fat/dataPoints/1234567890"
]
}Ответ
{
"done": true,
"response": {
"@type": "type.googleapis.com/google.devicesandservices.health.v4main.BatchDeleteDataPointsResponse"
}
}Найти информацию об устройстве
Используйте конечную точку list для получения списка устройств, сопряженных с учетной записью пользователя. В список входят информация о модели устройства ( deviceVersion ) и время последней синхронизации с мобильным приложением Google Health ( lastSyncTime ).
Информация о конфигурации и синхронизации списка полезна для устранения неполадок с синхронизацией или для получения исторических данных с момента последней синхронизации.
Например:
Запрос
GET https://health.googleapis.com/v4/users/me/pairedDevices Authorization: Bearer access-token Accept: application/json
Ответ
{
"pairedDevices": [
{
"name": "users/me/pairedDevices/123456",
"deviceType": "TRACKER",
"batteryStatus": "High",
"batteryLevel": 88,
"lastSyncTime": "2026-03-04T07:05:00Z",
"deviceVersion": "Charge 6",
"macAddress": "00:11:22:33:44:55",
"features": [
"STEPS",
"HEART_RATE"
]
}
]
}Запрос исторических данных
Одно из главных преимуществ API Google Health — возможность отслеживать производительность пользователя и контролировать показатели его здоровья в течение длительных периодов времени. Вы можете запрашивать данные пользователя за весь период, с момента их записи; API не накладывает никаких ограничений на объем исторических данных, которые может обрабатывать ваше приложение.
Однако запросы к историческим данным по-прежнему регулируются стандартными ограничениями скорости . Для обеспечения стабильности системы и предотвращения чрезмерной нагрузки API Google Health использует автоматическую пагинацию с размерами страниц, специфичными для каждой конечной точки. Обратите внимание на следующие ограничения и поведение:
- Автоматическая пагинация: если вы запрашиваете большой объем данных, API вернет только первую страницу результатов, не превышающую лимит размера страницы для данной конечной точки, вместе с токеном
nextPageToken. Для запроса последующих страниц необходимо использоватьnextPageToken. - Размер страниц может варьироваться: ограничения зависят от конечной точки и типа данных. Для большинства типов данных размер страниц ограничен максимум 10 000. Однако для некоторых типов данных, таких как
exerciseиsleep, размер страницы по умолчанию ограничен 25. Например, если клиент запрашивает все данные о сне за последние 10 лет, API все равно вернет только 25 сеансов сна на первой странице. - Ограничения по диапазону дат для сводных данных: Для конечных точек сводных и агрегированных данных (таких как
rollUpиdailyRollUp) диапазоны дат запросов ограничены в зависимости от типа данных:- Максимальный диапазон в 14 дней для
calories-in-heart-rate-zone,heart-rate,active-minutesиtotal-calories. - Для всех остальных типов сводных данных максимальный диапазон составляет 90 дней.
- Максимальный диапазон в 14 дней для
В зависимости от объема исторических данных, необходимых вашему приложению, для получения всего набора данных потребуется постраничная навигация. Учитывайте это при проектировании процесса синхронизации данных в вашем приложении.
Для обеспечения оптимальной производительности и во избежание ошибок API следуйте этим рекомендациям при запросе исторических данных:
Поэтапная синхронизация данных (горячая и холодная загрузка)
- Первоначальная «горячая» загрузка: во время основной последовательности загрузки загружаются и отображаются только данные за последние 7–14 дней. Это гарантирует, что пользователи увидят данные немедленно, без ожидания завершения длительных запросов.
- Фоновая «холодная» загрузка: после отрисовки основного пользовательского интерфейса перенаправьте получение более старых исторических данных в асинхронную очередь с более низким приоритетом или фоновый процесс.
Разбиение запросов на фрагменты для агрегирования
- Поскольку конечные точки для агрегирования и ежедневного агрегирования устанавливают ограничение на максимальный диапазон дат (14 или 90 дней в зависимости от типа данных), необходимо разбивать большие запросы на агрегирование исторических данных на более мелкие последовательные интервалы в пределах этих ограничений.
- Безопасно объединяйте или упорядочивайте эти подзапросы, чтобы соблюдать ограничения на параллельное выполнение и поддерживать стабильные индикаторы выполнения пользовательского интерфейса.
Используйте предварительно агрегированные сводные данные.
Реструктурируйте обзорные панели мониторинга и графики трендов, используя предварительно агрегированные сводные данные (например, DailyRollUpDataPoints ). Это значительно снизит вычислительную нагрузку на бэкэнд и время передачи данных по сети клиенту.
Устойчивая обработка ошибок (интеллектуальные повторные попытки)
- Внедрите строгую экспоненциальную обработку при столкновении с ограничениями скорости (
429 Too Many Requests) и таймаутами шлюза сервера (504 Gateway Timeout). Никогда не повторяйте сразу большие, неудачно завершившиеся запросы. Мгновенные повторные попытки увеличивают перегрузку бэкэнда и усугубляют деградацию системы.