データをフィルタする

Google Health API は、標準の取得メソッドを呼び出すときに、フィルタ式を使用して返されるデータポイントを制限します。具体的には、フィルタは次のものとともに使用されます。

このガイドでは、フィルタリングの実装方法、構文と規則について説明し、各レコードタイプの例を示します。

フィルタの規則

Google Health API は、Google API 改善提案(AIP-160)標準に沿ってフィルタを実装します。

クエリ パラメータ

フィルタは、filter パラメータの URL クエリ文字列を使用して渡されます。フィルタには特殊文字(<、>=、引用符など)が含まれているため、HTTP リクエストで送信する際は URL エンコードする必要があります。

たとえば、フィルタ steps.interval.civil_start_time >= "2026-03-04T00:00:00" を含むリクエストは次のようにエンコードする必要があります。

GET https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints
  ?filter=steps.interval.civil_start_time%20%3E%3D%20%222026-03-04T00%3A00%3A00%22

命名形式

データ型が複数の単語で構成されている場合、識別子の形式はリソースパスとフィルタで異なります。

  • エンドポイント パス: ハイフンを使用します(例: /dataTypes/body-fat)。
  • フィルタ文字列: アンダー スコアを使用します(例: body_fat)。

フィルタ ID にハイフンを使用すると、API はエラー理由 INVALID_DATA_POINT_FILTER で 400 Bad Request を返します。

フィルタのタイプとフィールド

フィルタで使用するフィールドは、クエリを実行するデータ型のレコード タイプによって異なります。次の表に、各レコード タイプでサポートされているフィールドを示します。

レコードタイプ 説明 サポートされているフィルタ フィールド
間隔 一定期間にわたって記録されたデータポイント(steps、distance、calories など)。 {dataType}.interval.start_time
{dataType}.interval.civil_start_time

例:
steps.interval.civil_start_time
サンプル 瞬時の観測値または短い測定値(weight、body-fat、blood-glucose など)。 {dataType}.sample_time.physical_time
{dataType}.sample_time.civil_time

例:
body_fat.sample_time.physical_time
毎日 1 日の指標と概要(daily-heart-rate-variability など)。 {dataType}.date

例:
daily_heart_rate_variability.date
セッション 特別なタイミング ルールで延長されたユーザー セッション。 運動: {dataType}.interval.civil_start_time
睡眠: sleep.interval.end_time、sleep.interval.civil_end_time
心電図: electrocardiogram.interval.start_time

例:
sleep.interval.civil_end_time

サポートされている演算子と形式ルール

フィルタ式は、次の形式ルールに準拠する必要があります。

比較演算子

サポートされている比較演算子は次の 2 つのみです。

演算子 説明
>= 下限(この値を含む)。
< 上限(この値を含まない)。

他の比較演算子(>、<=、= など)を使用すると、INVALID_DATA_POINT_FILTER_RESTRICTION_COMPARATOR を含む 400 Bad Request が返されます。

論理演算子

演算子 サポート
AND デフォルトでサポートされている唯一の演算子。開始境界と終了境界を組み合わせるために使用されます。
OR サポートされていません。OR を使用すると、400 Bad Request エラー理由 INVALID_DATA_POINT_FILTER_EXPRESSION_STRUCTURE(「フィルタは制限の論理積またはシーケンスである必要があります。検出: DISJUNCTION」)。

時間リテラル

フィルタ式の時間リテラルには、次の形式を使用する必要があります。

時刻型 要件 例
物理時間 RFC 3339 形式。末尾は Z または UTC オフセット。現実世界のイベントを UTC で表します。 正: "2026-03-01T00:00:00Z"、"2026-03-01T00:00:00-08:00"
誤: "2026-03-01"
民事訴訟 ISO 8601 形式: YYYY-MM-DD[THH:mm:ss]。ユーザーの時計の時刻を表します。位置情報やタイムゾーンのオフセットとは無関係です。 正しい例: "2026-03-01"、"2026-03-01T08:30:00"

フィルタの検証ルール

フィルタには、次のルールが適用されます。

ルール 説明 例
混合時間タイプなし 物理的な時間境界と民事上の時間境界を混在させないでください。 無効: steps.interval.start_time >= "2026-03-01T00:00:00Z" AND steps.interval.civil_start_time < "2026-03-02"
エラー: INVALID_DATA_POINT_FILTER_MIXED_TIME_RESTRICTIONS(「フィルタに物理時間範囲と民事時間範囲の両方を含めることはできません」)
データ型が混在していない リクエスト パスでデータ型に属するフィールドを使用します。 無効: フィルタ distance.interval.start_time >= "..." を含むパス /users/.../dataTypes/steps/...
エラー: INVALID_DATA_POINT_FILTER_COLLECTION_MISMATCH(「フィルタのデータ型が親のデータ型コレクションと一致しません」)
時間順序ロジック 上限は下限より大きくする必要があります。 無効: steps.interval.start_time >= "2026-03-02T00:00:00Z" AND steps.interval.start_time < "2026-03-01T00:00:00Z"
エラー: INVALID_TIME_RANGE(「クエリの終了時刻は開始時刻より厳密に大きくする必要があります」)
ケースの形式 データ型の名前に一致するスネークケースを使用します。 無効: body-fat.sample_time.physical_time >= "..."
エラー: INVALID_DATA_POINT_FILTER(「無効なフィルタ」)

API は、無効なフィルタに対して HTTP 400 Bad Request を返します。error.details[].metadata.detailedReasons でエラー理由コードを確認します。

必要な OAuth スコープ

フィルタを使用してデータポイントをクエリするには、承認済みユーザーがそのデータ型の関連する OAuth スコープを付与する必要があります。必要なスコープがない場合、API は MISSING_OAUTH_SCOPE で 403 Forbidden ステータスを返します。

次の表に、OAuth スコープと、そのスコープで読み取りアクセス権が付与されるデータ型のマッピングを示します。テーブルには、相対形式でスコープが表示されます(たとえば、.activity_and_fitness.readonly は https://www.googleapis.com/auth/googlehealth.activity_and_fitness.readonly を表します)。

必要な OAuth スコープ データ型
.activity_and_fitness.readonly active-energy-burned、active-minutes、active-zone-minutes、activity-level、altitude、calories-in-heart-rate-zone、daily-vo2-max、distance、exercise、floors、run-vo2-max、sedentary-period、steps、swim-lengths-data、time-in-heart-rate-zone、total-calories、vo2-max
.ecg.readonly 心電図
.health_metrics_and_measurements.readonly blood-glucose、body-fat、core-body-temperature、daily-heart-rate-variability、daily-heart-rate-zones、daily-oxygen-saturation、daily-respiratory-rate、daily-resting-heart-rate、daily-sleep-temperature-derivations、heart-rate、heart-rate-variability、height、oxygen-saturation、respiratory-rate-sleep-summary、skin-temperature-sensors、weight
.irn.readonly irregular-rhythm-notification
.nutrition.readonly food、food-measurement-unit、hydration-log、nutrition-log
.sleep.readonly sleep

リクエストされたデータ型に対してクライアントに書き込みスコープ(.activity_and_fitness.writeonly など)のみが付与されている場合でも、独自のクライアントが書き込んだデータポイントをクエリできます。この場合、リクエストは暗黙的に self-sources データソース ファミリーに制限されます。詳細とデータ型の制限については、データソース ファミリーでフィルタするをご覧ください。

ユースケースと例

次の例は、一般的なシナリオのフィルタを作成する方法を示しています。

物理的な時間範囲で歩数をクエリする

2026-03-01T00:00:00Z(含む)~ 2026-03-02T00:00:00Z(含まない)の間に記録されたクエリステップ:

GET https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints
  ?filter=steps.interval.start_time >= "2026-03-01T00:00:00Z"
  AND steps.interval.start_time < "2026-03-02T00:00:00Z"

民事時間範囲でクエリを実行する

2026 年 3 月 4 日の 1 日の歩数をユーザーのローカル時計を基準にクエリします。

GET https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints
  ?filter=steps.interval.civil_start_time >= "2026-03-04"
  AND steps.interval.civil_start_time < "2026-03-05"

身体サンプル時間で体脂肪をクエリする

2026 年 3 月以降に記録された体脂肪率の測定値をクエリします(UTC)。

GET https://health.googleapis.com/v4/users/me/dataTypes/body-fat/dataPoints
  ?filter=body_fat.sample_time.physical_time >= "2026-03-01T00:00:00Z"

民事訴訟のサンプル時間によるクエリの重み付け

特定のローカル時刻以降に記録された体重ログをクエリします。

GET https://health.googleapis.com/v4/users/me/dataTypes/weight/dataPoints
  ?filter=weight.sample_time.civil_time >= "2026-03-01T08:00:00"

心拍変動の 1 日の概要をクエリする

特定の日付より前に記録された心拍変動(HRV)の 1 日の概要をクエリします。

GET https://health.googleapis.com/v4/users/me/dataTypes/daily-heart-rate-variability/dataPoints
  ?filter=daily_heart_rate_variability.date < "2026-08-15"

民事開始時刻でエクササイズ セッションをクエリする

ユーザーのローカル タイムゾーンの特定の週に発生したエクササイズ セッションをクエリします。

GET https://health.googleapis.com/v4/users/me/dataTypes/exercise/dataPoints
  ?filter=exercise.interval.civil_start_time >= "2026-03-01"
  AND exercise.interval.civil_start_time < "2026-03-08"

民事上の終了時刻で睡眠セッションをクエリする

セッションの終了時刻で睡眠記録をクエリします。

GET https://health.googleapis.com/v4/users/me/dataTypes/sleep/dataPoints
  ?filter=sleep.interval.civil_end_time >= "2026-03-04T05:00:00"
  AND sleep.interval.civil_end_time < "2026-03-04T12:00:00"

開始時刻で心電図をクエリする

物理的な UTC 時点から始まる心電図の記録をクエリします。ECG クエリは、start_time の >= 比較のみをサポートします。

GET https://health.googleapis.com/v4/users/me/dataTypes/electrocardiogram/dataPoints
  ?filter=electrocardiogram.interval.start_time >= "2026-03-10T12:00:00Z"

データソース ファミリーでフィルタする

データソース ファミリーは、データソース(スマートウォッチ、モバイルアプリ、手動入力など)の論理グループです。特定のタイプのソース(身体活動量計、手動入力、独自のクライアントによって書き込まれたデータなど)からデータを分離または集計できます。

list、reconcile、rollUp、dailyRollUp の各エンドポイントはすべて dataSourceFamily パラメータをサポートしています。渡すメカニズムはエンドポイントによって異なります。

エンドポイント(HTTP メソッド) メカニズム
list(GET) dataSourceFamily を URL クエリ パラメータとして渡します。
reconcile(GET) dataSourceFamily を URL クエリ パラメータとして渡します。
rollUp(POST) dataSourceFamily を JSON リクエスト本文のフィールドとして渡します。
dailyRollUp(POST) dataSourceFamily を JSON リクエスト本文のフィールドとして渡します。

サポートされているデータソース ファミリー

次の表に、サポートされている dataSourceFamily 値を示します。

オプション 説明
users/me/dataSourceFamilies/all-sources デフォルト値(読み取りスコープが付与されている場合)。利用可能なすべてのファーストパーティ(1P)データソースとサードパーティ(3P)データソースのデータポイントが含まれます。このオプションでは、サードパーティ製アプリのデータ(スマートウォッチの歩数 + サードパーティ製アプリの歩数 + 携帯電話の歩数 + 手動入力の歩数など)が返されます。
users/me/dataSourceFamilies/google-wearables Google と Fitbit トラッカー デバイス(Fitbit ウェアラブル トラッカーや Google Pixel Watch など)で記録されたデータが含まれます。手動で記録されたデータとスマートフォンで推定されたデータは除外されます。統合でウェアラブル ハードウェアによって直接記録されたセンサーの生テレメトリーが必要な場合は、このオプションを使用します。
users/me/dataSourceFamilies/google-sources Google と Fitbit のファーストパーティ ソースが含まれます。これには、トラッカー デバイスの記録、ヘルスコネクトのデータ、ファーストパーティ製アプリ(Fitbit アプリや Google Fit など)を通じて記録された手動入力が含まれます。
users/me/dataSourceFamilies/self-sources 呼び出し元のクライアントが Google Health API を介して書き込んだデータのみが含まれます(データソースが API を介して登録され、呼び出し元と同じ OAuth クライアント ID を持つデータポイント)。

リクエストされたデータソース ファミリーに一致するデータポイントがない場合、レスポンスはエラーではなく空のリストになります。

書き込み専用スコープとセルフソース

リクエストされたデータ型に対して書き込みスコープ(.activity_and_fitness.writeonly など)のみが付与された呼び出し元は、自身が書き込んだデータのみを読み取ることができます。

  • dataSourceFamily パラメータが明示的に指定されていないリクエスト、または dataSourceFamily が users/me/dataSourceFamilies/self-sources に設定されているリクエストは、暗黙的に self-sources に制限されます。
  • 書き込みスコープのみで他のデータソース ファミリー(all-sources、google-wearables、google-sources など)をリクエストすると、403 Forbidden(PERMISSION_DENIED)エラーが発生します。

リスト エンドポイントのデータ型の制限

list エンドポイント(users.dataTypes.dataPoints.list)では、sleep、food、food-measurement-unit のデータ型で dataSourceFamily によるフィルタリングはサポートされていません。

  • sleep、food、food-measurement-unit の list で dataSourceFamily を明示的に設定すると、400 Bad Request(INVALID_ARGUMENT)エラーが発生します。
  • 書き込みスコープのみが付与されている場合(呼び出し元のスコープによって self-sources への制限が暗黙的に示されている場合)、これらのデータ型に対して list を呼び出すと、403 Forbidden(PERMISSION_DENIED)エラーで失敗します。
  • dataSourceFamily で sleep データポイントをフィルタするには、代わりに reconcile エンドポイントを使用します。

データソース ファミリーの例

独自のクライアントがユーザーのために書き込んだ未加工のデータポイントを一覧表示するには、dataSourceFamily クエリ パラメータを users/me/dataSourceFamilies/self-sources に設定して list エンドポイントを呼び出します。

たとえば、次の GET リクエストは、2026 年 3 月 1 日以降に呼び出し元クライアントによって書き込まれた未加工の body-fat 測定値を一覧表示します。

リクエスト

GET https://health.googleapis.com/v4/users/me/dataTypes/body-fat/dataPoints
  ?dataSourceFamily=users/me/dataSourceFamilies/self-sources
  &filter=body_fat.sample_time.physical_time >= "2026-03-01T00:00:00Z"
Authorization: Bearer access-token
Accept: application/json

レスポンス

{
  "dataPoints": [
    {
      "name": "users/123456789/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": ""
}

特定のデータソース ファミリーから調整済みのデータ ストリームを取得するには、dataSourceFamily クエリ パラメータを使用して reconcile エンドポイントを呼び出します。

たとえば、次の GET リクエストは、2026 年 3 月 3 日以降の日のトラッカーで記録された睡眠を取得します。

リクエスト

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 エンドポイントを呼び出し、JSON リクエスト本文で dataSourceFamily フィールドを渡します。

次の POST リクエストは、ウェアラブル デバイスからのみ集計された、1 時間間隔(3600s)での歩数の 1 日の推移をクエリします。

リクエスト

POST https://health.googleapis.com/v4/users/me/dataTypes/steps/dataPoints:rollUp
Authorization: Bearer access-token
Accept: application/json

{
  "range": {
    "startTime": "2026-07-29T00:00:00Z",
    "endTime": "2026-07-29T23:59:59Z"
  },
  "windowSize": "3600s",
  "dataSourceFamily": "users/me/dataSourceFamilies/google-wearables"
}

レスポンス

{
  "rollupDataPoints": [
    {
      "startTime": "2026-07-29T08:00:00Z",
      "endTime": "2026-07-29T09:00:00Z",
      "steps": {
        "countSum": "1200"
      }
    },
    {
      "startTime": "2026-07-29T09:00:00Z",
      "endTime": "2026-07-29T10:00:00Z",
      "steps": {
        "countSum": "3450"
      }
    }
  ]
}

特定のソース ファミリーの 1 日のデータポイントを集計するには、dailyRollUp エンドポイントを呼び出し、リクエスト本文で dataSourceFamily フィールドを渡します。

たとえば、次のリクエストは、すべてのファーストパーティの Google と Fitbit のソース(ウェアラブル + 手動入力)を含む、ユーザーの歩数の 1 日あたりのロールアップを計算します。

リクエスト

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": 7,
        "day": 28
      },
      "time": {
        "hours": 0,
        "minutes": 0,
        "seconds": 0,
        "nanos": 0
      }
    },
    "end": {
      "date": {
        "year": 2026,
        "month": 7,
        "day": 30
      },
      "time": {
        "hours": 0,
        "minutes": 0,
        "seconds": 0,
        "nanos": 0
      }
    }
  },
  "windowSizeDays": 1,
  "dataSourceFamily": "users/me/dataSourceFamilies/google-sources"
}

レスポンス

{
  "rollupDataPoints": [
    {
      "civilStartTime": {
        "date": {
          "year": 2026,
          "month": 7,
          "day": 28
        },
        "time": {}
      },
      "civilEndTime": {
        "date": {
          "year": 2026,
          "month": 7,
          "day": 28
        },
        "time": {
          "hours": 23,
          "minutes": 59,
          "seconds": 59
        }
      },
      "steps": {
        "countSum": "8430"
      }
    },
    {
      "civilStartTime": {
        "date": {
          "year": 2026,
          "month": 7,
          "day": 29
        },
        "time": {}
      },
      "civilEndTime": {
        "date": {
          "year": 2026,
          "month": 7,
          "day": 29
        },
        "time": {
          "hours": 23,
          "minutes": 59,
          "seconds": 59
        }
      },
      "steps": {
        "countSum": "11245"
      }
    }
  ]
}