> For the complete documentation index, see [llms.txt](https://docs.pulsoid.net/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.pulsoid.net/heart-rate-and-sensor-data/write-heart-rate-via-http.md).

# Write Data via HTTP

Submit a heart rate reading and the battery level of the measuring device for the authenticated user.

**Request**

<table><thead><tr><th width="197">name</th><th>value</th></tr></thead><tbody><tr><td>url</td><td><code>https://dev.pulsoid.net/api/v1/data</code></td></tr><tr><td>method</td><td><code>POST</code></td></tr><tr><td>content-type</td><td><code>application/json</code></td></tr><tr><td>scope</td><td><code>data:heart_rate:write</code> for <code>heart_rate</code>, <code>data:battery_level:write</code> for <code>battery_level</code></td></tr></tbody></table>

**Authentication**

Provide your OAuth2 Bearer token using one of the following methods:

| Method          | Example                            |
| --------------- | ---------------------------------- |
| Query parameter | `?access_token=YOUR_TOKEN`         |
| Header          | `Authorization: Bearer YOUR_TOKEN` |

**Request Body**

```json
{
  "measured_at": 1709312400000,
  "data": {
    "heart_rate": 75,
    "battery_level": {
      "percent": 67
    }
  }
}
```

| Field                       | Type    | Required | Description                                                                        |
| --------------------------- | ------- | -------- | ---------------------------------------------------------------------------------- |
| measured\_at                | number  | Yes      | Unix timestamp in milliseconds when the data was measured                          |
| data.heart\_rate            | integer | No       | Heart rate in beats per minute. Must be greater than 0                             |
| data.battery\_level.percent | integer | No       | Battery level of the measuring device (heart rate monitor or watch), from 0 to 100 |

`data` must contain at least one of `heart_rate` or `battery_level`. The token needs the scope of every field present in `data`.

{% hint style="info" %}
Heart rate values of 0 or below and battery levels outside of 0 to 100 are silently ignored and will not be stored. Other valid values from the same request are still stored.
{% endhint %}

**HTTP Status Codes**

| Status | Description                                                                                      |
| ------ | ------------------------------------------------------------------------------------------------ |
| `200`  | Data accepted                                                                                    |
| `400`  | Malformed request body, or `data` has neither `heart_rate` nor `battery_level` (error code 6007) |
| `400`  | Token does not have the scope required by a field in `data` (error code 6003)                    |
| `401`  | Missing or invalid token                                                                         |
| `500`  | Unexpected server error (error code 6001)                                                        |

**cURL Request Example**

```bash
curl -X POST https://dev.pulsoid.net/api/v1/data \
  -H "Authorization: Bearer 8c4da3ce-7ed7-4a19-a1f1-058498661e45" \
  -H "Content-Type: application/json" \
  -d '{"measured_at": 1709312400000, "data": {"heart_rate": 75}}'
```

**cURL Request Example with battery level**

```bash
curl -X POST https://dev.pulsoid.net/api/v1/data \
  -H "Authorization: Bearer 8c4da3ce-7ed7-4a19-a1f1-058498661e45" \
  -H "Content-Type: application/json" \
  -d '{"measured_at": 1709312400000, "data": {"heart_rate": 75, "battery_level": {"percent": 67}}}'
```
