Check-ins

Read an Objective's check-in history and record a new value and its progress.

A check-in records an Objective's latest value. GPS stores the value, works out the new progress, and keeps the change in the Objective's history. The history also holds check-ins made in GPS and updates from connected integrations.

Method Path Scope Webhook
GET /objectives/{objectiveId}/progress progress:read
POST /objectives/{objectiveId}/progress progress:write None (see below)

The JavaScript examples assume a headers object holding your key:

JavaScript
const headers = {
  'X-API-Key': process.env.GPS_API_KEY_ID,
  'X-API-Secret': process.env.GPS_API_SECRET,
};

The check-in object#

Field Type Notes
id string Check-in ID.
objectiveId string
notes string or null
updatedBy string or null Member ID of who recorded it. null for some integration updates.
value number or null The value sent with the check-in.
previousProgress number or null Progress percentage before.
newProgress number or null Progress percentage after.
progressChange number or null newProgress minus previousProgress.
previousValue number or null The Objective's currentValue before.
newValue number or null The Objective's currentValue after.
createdAt string ISO 8601 timestamp.

List check-ins#

GET /objectives/{objectiveId}/progress

Returns the Objective's check-in history, newest first.

Scope: progress:read

Parameter In Notes
objectiveId path Objective ID.
limit, offset query See Pagination.
curl https://plan.empiraa.app/api/v1/objectives/c7e9a1b3-4d5f-4a6b-9c8d-1e2f3a4b5c6d/progress \
  -H "X-API-Key: $GPS_API_KEY_ID" \
  -H "X-API-Secret: $GPS_API_SECRET"

Response 200

JSON
{
  "data": [
    {
      "id": "4b6d8f0b-2c3e-4f5a-b6c7-8d9e0f1a2b3c",
      "objectiveId": "c7e9a1b3-4d5f-4a6b-9c8d-1e2f3a4b5c6d",
      "notes": "Two new annual contracts signed",
      "updatedBy": "5d7f9b1d-3e5a-4c7e-9f1a-2b3c4d5e6f70",
      "value": 60000,
      "previousProgress": 45,
      "newProgress": 50,
      "progressChange": 5,
      "previousValue": 54000,
      "newValue": 60000,
      "createdAt": "2026-11-12T03:15:42.118Z"
    }
  ],
  "meta": { "total": 1, "limit": 50, "offset": 0 }
}

Errors: 404 NOT_FOUND if the Objective doesn't exist or is in another organization; 422 VALIDATION_ERROR for a bad limit or offset.

Record a check-in#

POST /objectives/{objectiveId}/progress

Sets the Objective's currentValue to value, recalculates its progress, and adds an entry to its history.

How progress is worked out:

  • The Objective has a targetValue: progress is value ÷ targetValue × 100. With a target of 120,000, a value of 60,000 gives 50%.
  • No targetValue: value is taken as the progress percentage itself.
  • Status Objectives (measurement type Status (On Track / Off Track / Complete)) are done or not done: a value of 1 or more records done, anything less records not done.

Progress can go past 100%, since beating a target is a real result, but it must stay between 0% and 1000% (0% and 100% for status Objectives). A check-in that would land outside that range is refused.

A check-in doesn't change the Objective's status.

Scope: progress:write

Webhook: none. A check-in through the API doesn't fire objective.updated, even though the Objective's progress changes. If you rely on webhooks, re-read the Objective after the check-in.

Path parameter Notes
objectiveId Objective ID.

Request body

Field Type Required Allowed values Notes
value number Yes The Objective's new value.
notes string or null No Up to 2,000 characters
onBehalfOf string No Active member ID Who recorded it (updatedBy). Default: the key's creator. See Attribution.
curl -X POST https://plan.empiraa.app/api/v1/objectives/c7e9a1b3-4d5f-4a6b-9c8d-1e2f3a4b5c6d/progress \
  -H "X-API-Key: $GPS_API_KEY_ID" \
  -H "X-API-Secret: $GPS_API_SECRET" \
  -H "Content-Type: application/json" \
  -d '{ "value": 60000, "notes": "Two new annual contracts signed" }'

Response 201

JSON
{
  "data": {
    "id": "4b6d8f0b-2c3e-4f5a-b6c7-8d9e0f1a2b3c",
    "objectiveId": "c7e9a1b3-4d5f-4a6b-9c8d-1e2f3a4b5c6d",
    "notes": "Two new annual contracts signed",
    "updatedBy": "5d7f9b1d-3e5a-4c7e-9f1a-2b3c4d5e6f70",
    "value": 60000,
    "previousProgress": 45,
    "newProgress": 50,
    "progressChange": 5,
    "previousValue": 54000,
    "newValue": 60000,
    "createdAt": "2026-11-12T03:15:42.118Z"
  }
}

Errors

Status code When
404 NOT_FOUND The Objective doesn't exist or is in another organization.
422 VALIDATION_ERROR value is missing or not a number, notes is too long, or the resulting progress is out of range. The error text explains the range for that Objective.
422 INVALID_USERS onBehalfOf isn't an active member.
422 NO_KEY_OWNER No onBehalfOf, and the key's creator is no longer a member.

Example of an out-of-range check-in:

JSON
{
  "error": "Progress can go past 100% — that's what beating a target looks like — but it has to be between 0% and 1000%.",
  "code": "VALIDATION_ERROR",
  "docs": "https://empiraa.com/docs/api"
}