Users API
Base URL: https://YOUR-SERVER/api. Send your API key in x-api-key where authentication is required. A key also needs the listed permission; your account's access rules still apply.
API guide · All endpoints · OpenAPI JSON
GET /users— Get all usersGET /users/me/backup-devices— List own backup devicesPOST /users/me/backup-devices— Register or report an own backup deviceDELETE /users/me/backup-devices/{id}— Remove an own backup device without deleting assetsGET /users/me/backup-devices/{id}/reconciliations— List own device reconciliation historyPOST /users/me/backup-devices/{id}/reconciliations— Start own device inventory reconciliationPOST /users/me/backup-devices/{id}/reconciliations/{runId}/buckets— Reconcile one complete differing bucketGET /users/me/calendar-heatmap— Retrieve calendar heatmap activityDELETE /users/me/onboarding— Delete user onboardingGET /users/me/onboarding— Retrieve user onboardingPUT /users/me/onboarding— Update user onboardingGET /users/me/pins— Get my pinned collectionsPUT /users/me/pins— Replace my pinned collectionsGET /users/me/preferences— Get my preferencesPUT /users/me/preferences— Update my preferencesGET /users/me/preferences/history— Get my preference historyDELETE /users/profile-image— Delete user profile imagePOST /users/profile-image— Create user profile imageGET /users/{id}— Retrieve a userGET /users/{id}/profile-image— Retrieve user profile image
Get all users
GET /api/users
Retrieve a list of all users on the server.
Authentication: API key. Permission: user.read.
Responses
Field definitions: UserResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"items": {
"$ref": "#/components/schemas/UserResponseDto"
},
"type": "array"
}
}
},
"description": ""
}
}List own backup devices
GET /api/users/me/backup-devices
Authentication: API key. Permission: user.read.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
limit | query | No | integer |
offset | query | No | integer |
Parameter types, defaults and constraints
[
{
"name": "limit",
"required": false,
"in": "query",
"schema": {
"minimum": 1,
"maximum": 200,
"default": 100,
"type": "integer"
}
},
{
"name": "offset",
"required": false,
"in": "query",
"schema": {
"minimum": 0,
"maximum": 1000000,
"default": 0,
"type": "integer"
}
}
]Responses
Field definitions: BackupDeviceListDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/BackupDeviceListDto"
}
}
},
"description": ""
}
}Register or report an own backup device
POST /api/users/me/backup-devices
Stable deviceKey scoped to the owner. Success time and pending count are device-reported, never checksum verification. Removing a device preserves assets and reconciliation history.
Authentication: API key. Permission: user.update.
Request body
Required.
Field definitions: BackupDeviceWriteDto
{
"application/json": {
"schema": {
"$ref": "#/components/schemas/BackupDeviceWriteDto"
}
}
}Responses
Field definitions: BackupDeviceDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/BackupDeviceDto"
}
}
},
"description": ""
}
}Remove an own backup device without deleting assets
DELETE /api/users/me/backup-devices/{id}
Authentication: API key. Permission: user.update.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
id | path | Yes | string |
Parameter types, defaults and constraints
[
{
"name": "id",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-4[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12})$",
"type": "string"
}
}
]Responses
{
"204": {
"description": ""
}
}List own device reconciliation history
GET /api/users/me/backup-devices/{id}/reconciliations
Requires elevated unfiltered session; checkedAt identifies actual inventory snapshot. Includes incomplete runs explicitly; admin metadata access never grants foreign hash access.
Authentication: API key. Permission: asset.read.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
id | path | Yes | string |
limit | query | No | integer |
offset | query | No | integer |
Parameter types, defaults and constraints
[
{
"name": "id",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-4[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12})$",
"type": "string"
}
},
{
"name": "limit",
"required": false,
"in": "query",
"schema": {
"minimum": 1,
"maximum": 200,
"default": 100,
"type": "integer"
}
},
{
"name": "offset",
"required": false,
"in": "query",
"schema": {
"minimum": 0,
"maximum": 1000000,
"default": 0,
"type": "integer"
}
}
]Responses
Field definitions: ReconciliationHistoryDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ReconciliationHistoryDto"
}
}
},
"description": ""
}
}Start own device inventory reconciliation
POST /api/users/me/backup-devices/{id}/reconciliations
Requires a current elevated session and no active hidden-content filter.256 indexed bucket digests of sorted unique raw SHA256 bytes, maximum2000 hashes per bucket. Differing buckets require complete hash lists. Snapshot database inventory excludes offline/last-checked-missing originals; not a fresh filesystem check.
Authentication: API key. Permission: asset.read.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
id | path | Yes | string |
Parameter types, defaults and constraints
[
{
"name": "id",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-4[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12})$",
"type": "string"
}
}
]Request body
Required.
Field definitions: ReconciliationStartDto
{
"application/json": {
"schema": {
"$ref": "#/components/schemas/ReconciliationStartDto"
}
}
}Responses
Field definitions: ReconciliationResultDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ReconciliationResultDto"
}
}
},
"description": ""
}
}Reconcile one complete differing bucket
POST /api/users/me/backup-devices/{id}/reconciliations/{runId}/buckets
Up to2000 distinct SHA256 hashes matching original count/digest and first-byte bucket. Server extras never count as device missing. Changed server inventory refuses continuation; start a new run. Repeated validated bucket requests do not double-count; a concurrent snapshot conflict returns409 and may be retried. No completed audit until every differing bucket is validated.
Authentication: API key. Permission: asset.read.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
id | path | Yes | string |
runId | path | Yes | string |
Parameter types, defaults and constraints
[
{
"name": "id",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$",
"type": "string"
}
},
{
"name": "runId",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$",
"type": "string"
}
}
]Request body
Required.
Field definitions: ReconciliationBucketDto
{
"application/json": {
"schema": {
"$ref": "#/components/schemas/ReconciliationBucketDto"
}
}
}Responses
Field definitions: ReconciliationResultDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/ReconciliationResultDto"
}
}
},
"description": ""
}
}Retrieve calendar heatmap activity
GET /api/users/me/calendar-heatmap
Retrieve activity counts for a specified period, in a calendar heatmap format.
Authentication: API key. Permission: user.read.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
from | query | No | Start date in UTC |
to | query | No | End date in UTC |
type | query | No |
Parameter types, defaults and constraints
Field definitions: CalendarHeatmapType
[
{
"name": "from",
"required": false,
"in": "query",
"description": "Start date in UTC",
"schema": {
"format": "date",
"pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))$",
"example": "2024-01-01",
"type": "string"
}
},
{
"name": "to",
"required": false,
"in": "query",
"description": "End date in UTC",
"schema": {
"format": "date",
"pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))$",
"example": "2024-01-01",
"type": "string"
}
},
{
"name": "type",
"required": false,
"in": "query",
"schema": {
"default": "Upload",
"$ref": "#/components/schemas/CalendarHeatmapType"
}
}
]Responses
Field definitions: CalendarHeatmapResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/CalendarHeatmapResponseDto"
}
}
},
"description": ""
}
}Delete user onboarding
DELETE /api/users/me/onboarding
Delete the onboarding status of the current user.
Authentication: API key. Permission: userOnboarding.delete.
Responses
{
"204": {
"description": ""
}
}Retrieve user onboarding
GET /api/users/me/onboarding
Retrieve the onboarding status of the current user.
Authentication: API key. Permission: userOnboarding.read.
Responses
Field definitions: OnboardingResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/OnboardingResponseDto"
}
}
},
"description": ""
}
}Update user onboarding
PUT /api/users/me/onboarding
Update the onboarding status of the current user.
Authentication: API key. Permission: userOnboarding.update.
Request body
Required.
Field definitions: OnboardingDto
{
"application/json": {
"schema": {
"$ref": "#/components/schemas/OnboardingDto"
}
}
}Responses
Field definitions: OnboardingResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/OnboardingResponseDto"
}
}
},
"description": ""
}
}Get my pinned collections
GET /api/users/me/pins
Complete ordered snapshot of current access-filtered titles, counts and covers. Unavailable pins disclose only their opaque pin ID and kind. Requires a user session.
Authentication: API key. Permission: userPreference.read.
Responses
Field definitions: PinnedCollectionsResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/PinnedCollectionsResponseDto"
}
}
},
"description": ""
}
}Replace my pinned collections
PUT /api/users/me/pins
Add, remove or reorder by replacing the complete ordered list against expectedRevision. Stale writes return 409. Retain unavailable pins using their opaque ID, kind and null targetId. Requires a user session.
Authentication: API key. Permission: userPreference.update.
Request body
Required.
Field definitions: PinnedCollectionsUpdateDto
{
"application/json": {
"schema": {
"$ref": "#/components/schemas/PinnedCollectionsUpdateDto"
}
}
}Responses
Field definitions: PinnedCollectionsResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/PinnedCollectionsResponseDto"
}
}
},
"description": ""
}
}Get my preferences
GET /api/users/me/preferences
Retrieve the preferences for the current user.
Authentication: API key. Permission: userPreference.read.
Responses
Field definitions: UserPreferencesResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/UserPreferencesResponseDto"
}
}
},
"description": ""
}
}Update my preferences
PUT /api/users/me/preferences
Update the preferences of the current user.
Deprecated. Avoid this operation in new integrations; use the replacement supported by your server release.
Authentication: API key. Permission: userPreference.update.
Request body
Required.
Field definitions: UserPreferencesUpdateDto
{
"application/json": {
"schema": {
"$ref": "#/components/schemas/UserPreferencesUpdateDto"
}
}
}Responses
Field definitions: UserPreferencesResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/UserPreferencesResponseDto"
}
}
},
"description": ""
}
}Get my preference history
GET /api/users/me/preferences/history
The newest changes to the current user’s own preferences, with the device that saved each. Locked-content rules appear only as changed.
Authentication: API key. Permission: userPreference.read.
Responses
Field definitions: UserPreferenceHistoryResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/UserPreferenceHistoryResponseDto"
}
}
},
"description": ""
}
}Delete user profile image
DELETE /api/users/profile-image
Delete the profile image of the current user.
Authentication: API key. Permission: userProfileImage.delete.
Responses
{
"204": {
"description": ""
}
}Create user profile image
POST /api/users/profile-image
Upload and set a new profile image for the current user.
Authentication: API key. Permission: userProfileImage.update.
Request body
Required. A new avatar for the user
Field definitions: CreateProfileImageDto
{
"multipart/form-data": {
"schema": {
"$ref": "#/components/schemas/CreateProfileImageDto"
}
}
}Responses
Field definitions: CreateProfileImageResponseDto
{
"201": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/CreateProfileImageResponseDto"
}
}
},
"description": ""
}
}Retrieve a user
GET /api/users/{id}
Retrieve a specific user by their ID.
Authentication: API key. Permission: user.read.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
id | path | Yes | string |
Parameter types, defaults and constraints
[
{
"name": "id",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-4[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12})$",
"type": "string"
}
}
]Responses
Field definitions: UserResponseDto
{
"200": {
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/UserResponseDto"
}
}
},
"description": ""
}
}Retrieve user profile image
GET /api/users/{id}/profile-image
Retrieve the profile image file for a user.
Authentication: API key. Permission: userProfileImage.read.
Parameters
| Name | Where | Required | Description |
|---|---|---|---|
id | path | Yes | string |
Parameter types, defaults and constraints
[
{
"name": "id",
"required": true,
"in": "path",
"schema": {
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-4[0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12})$",
"type": "string"
}
}
]Responses
{
"200": {
"content": {
"application/octet-stream": {
"schema": {
"format": "binary",
"type": "string"
}
}
},
"description": ""
}
}© 2026 Frameleaf Inc. All rights reserved.
Frameleaf and the Frameleaf logo are Trademarks of Frameleaf Inc.