icloud-photos-sync local server API 1.0
This document describes the API of icloud-photo-sync's web server. Parameters are passed as query strings.
Requests to an unknown endpoint, or with an unsupported method, are rejected with 400 and the message Method (<method>) not supported on endpoint <url>. Unexpected errors while handling a request are answered with 500 (see InternalError).
Servers
| Description | URL |
|---|---|
| The URL and port depend on your local setup - by default the webserver is exposed at port 80, below the configured web base path | http://localhost:80 |
Endpoints
GET /api/state
Provides the current operational state of the application
Responses
{
"state": "ready",
"timestamp": 0,
"nextSync": 0,
"prevError": {
"message": "string",
"code": "string"
},
"prevTrigger": "sync",
"progressMsg": "string",
"progress": 10.12,
"trustedPhoneNumbers": [
{
"id": 0,
"maskedNumber": "+49 •••• •••••12"
}
]
}
Schema of the response body
{
"type": "object",
"required": [
"state",
"timestamp"
],
"properties": {
"state": {
"type": "string",
"enum": [
"ready",
"running",
"blocked"
],
"description": "`blocked` means the application is waiting for an MFA code"
},
"timestamp": {
"type": "integer",
"description": "Time of the last state change, in milliseconds since epoch"
},
"nextSync": {
"type": "integer",
"description": "Time of the next scheduled sync, in milliseconds since epoch (daemon mode only)"
},
"prevError": {
"type": "object",
"description": "The error of the last run, cleared when the next run starts",
"properties": {
"message": {
"type": "string"
},
"code": {
"type": "string"
}
}
},
"prevTrigger": {
"type": "string",
"enum": [
"sync",
"auth"
]
},
"progressMsg": {
"type": "string"
},
"progress": {
"type": "number",
"description": "Progress of the current run in percent"
},
"trustedPhoneNumbers": {
"type": "array",
"description": "The trusted phone numbers of the account, available once an MFA code was required - the `id` is used as `phoneNumberId` for `/api/resend_mfa`",
"items": {
"type": "object",
"required": [
"id",
"maskedNumber"
],
"properties": {
"id": {
"type": "integer"
},
"maskedNumber": {
"type": "string",
"example": "+49 •••• •••••12"
}
}
}
}
}
}
Refer to the common response description: InternalError.
GET /api/log
Provides all stored log entries since the last trigger
Input parameters
| Parameter | In | Type | Default | Nullable | Description |
|---|---|---|---|---|---|
loglevel |
query | string | none | No | The minimum log level of the returned entries, defaults to 'none' (returning no entries) |
Responses
[
{
"level": "debug",
"time": 0,
"source": "string",
"message": "string"
}
]
Schema of the response body
{
"type": "array",
"items": {
"type": "object",
"required": [
"level",
"time",
"source",
"message"
],
"properties": {
"level": {
"type": "string",
"enum": [
"debug",
"info",
"warn",
"error"
]
},
"time": {
"type": "integer",
"description": "Time of the log entry, in milliseconds since epoch"
},
"source": {
"type": "string"
},
"message": {
"type": "string"
}
}
}
}
Refer to the common response description: InternalError.
POST /api/reauthenticate
Requests the application to re-authenticate
Responses
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "Reauthentication requested"
}
}
}
Refer to the common response description: SyncInProgress.
Refer to the common response description: InternalError.
POST /api/sync
Requests the application to execute an ad-hoc sync
Description
The sync is only executed, if the application runs in daemon mode
Responses
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "Sync requested"
}
}
}
Refer to the common response description: SyncInProgress.
Refer to the common response description: InternalError.
POST /api/resend_mfa
Requests the tool to resend the MFA code utilizing the provided method
Input parameters
| Parameter | In | Type | Default | Nullable | Description |
|---|---|---|---|---|---|
method |
query | string | No | The selected resend method | |
phoneNumberId |
query | integer | 1 | No | The id of the trusted phone number (see `trustedPhoneNumbers` of `/api/state`), in case multiple trusted phone numbers are registered with the account. Ignored for the `device` method. |
Responses
{
"message": "Requesting MFA resend with method 'Device'"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"examples": [
"Requesting MFA resend with method 'Device'",
"Requesting MFA resend with method 'SMS' (Number ID: 1)",
"Requesting MFA resend with method 'Voice' (Number ID: 2)"
]
}
}
}
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "Resend method does not match expected format"
}
}
}
Refer to the common response description: MFANotExpected.
Refer to the common response description: InternalError.
POST /api/mfa
Enters the MFA code for authentication
Input parameters
| Parameter | In | Type | Default | Nullable | Description |
|---|---|---|---|---|---|
code |
query | string | No | The MFA code provided by the trusted source |
Responses
{
"message": "Read MFA code: 123456"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"example": "Read MFA code: 123456"
}
}
}
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "Unexpected MFA code format! Expecting 6 digits"
}
}
}
Refer to the common response description: MFANotExpected.
Refer to the common response description: InternalError.
POST /api/subscribe
Creates a notification subscription
Request body
{
"endpoint": "string",
"expirationTime": 10.12,
"keys": {
"p256dh": "string",
"auth": "string"
}
}
Schema of the request body
{
"type": "object",
"required": [
"endpoint",
"keys"
],
"properties": {
"endpoint": {
"type": "string",
"minLength": 1
},
"expirationTime": {
"type": "number"
},
"keys": {
"type": "object",
"required": [
"p256dh",
"auth"
],
"properties": {
"p256dh": {
"type": "string",
"minLength": 1
},
"auth": {
"type": "string",
"minLength": 1
}
}
}
}
}
Responses
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "Push subscription added successfully"
}
}
}
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "Unable to add push subscription"
}
}
}
Refer to the common response description: InternalError.
GET /api/vapid-public-key
Gets the VAPID public key, required for push notification support
Responses
{
"publicKey": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"publicKey": {
"type": "string"
}
}
}
Refer to the common response description: InternalError.
GET /metrics
Provides sync metrics in the Prometheus/OpenMetrics exposition format
Description
Only available if the Prometheus metrics export is enabled (--export-prometheus-metrics), otherwise the endpoint does not exist and the request is rejected with 400.
The exposition format is negotiated through the Accept header, following the Prometheus content negotiation: OpenMetrics 1.0.0 and the Prometheus text formats 1.0.0 and 0.0.4 are supported, the Prometheus text format 0.0.4 is used as fallback.
See the sync metrics documentation for the exposed metrics.
Input parameters
| Parameter | In | Type | Default | Nullable | Description |
|---|---|---|---|---|---|
Accept |
header | string | No | The accepted exposition formats, e.g. as sent by Prometheus |
Responses
"string"
Schema of the response body
{
"type": "string"
}
"string"
Schema of the response body
{
"type": "string"
}
"string"
Schema of the response body
{
"type": "string"
}
Refer to the common response description: InternalError.
Common responses
This section describes common responses that are reused across operations.
SyncInProgress
The action cannot be performed, because a sync or authentication is currently in progress (the state is not ready)
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "Cannot perform action while sync is in progress"
}
}
}
MFANotExpected
No MFA code is expected at this time (the state is not blocked)
{
"message": "string"
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"const": "MFA code not expected at this time."
}
}
}
InternalError
An unexpected error occurred while handling the request
{
"message": "WEB_SERVER_UNKNOWN_ERR: ..."
}
Schema of the response body
{
"type": "object",
"properties": {
"message": {
"type": "string",
"description": "The description of the error",
"example": "WEB_SERVER_UNKNOWN_ERR: ..."
}
}
}