TapTo API: Difference between revisions

From TapTo Wiki

Created page with "{{Warn|This page refers to the future version 2.0.0 of TapTo which is in active development. Please don't use any information on this page until it's been finalised and released.}} The TapTo API is an API available on and published by every device running the core TapTo software. This API allows management of all TapTo features which would not present a security risk. The [https://tapto.life/ TapTo Life] app uses this API for all c..."
 
No edit summary
Line 23: Line 23:


==== Requests ====
==== Requests ====
A request object informs the peer to run a pre-defined method, and report back when it's completed with a response object.
A request object asks the connected peer to run a pre-defined method, and report back when it's completed with a response object.
 
An example request:<syntaxhighlight lang="json">
{
    "tapto": 1,
    "id": "9ab7679f-6de9-11ef-9a9b-020304050607",
    "timestamp": 1725803556229,
    "method": "media.search",
    "params": {
        "query": "240p"
    }
}
</syntaxhighlight>This request would query TapTo's media database for a file containing the word "240p" and return a response with the search results.
 
Request keys:
{| class="wikitable"
|+
!Key
!Type
!Required
!Description
|-
|tapto
|number
|Yes
|Specifies the protocol version and is used to validate a payload. It must be contained in every request or else the request will be rejected. Currently this must be the integer <code>1</code>.
|-
|id
|string
|Yes*
|A UUID v1 generated by the requesting client, used to match requests back to responses. A request missing this key is valid but would be treated as a notification and not receive any response (or an error).
|-
|timestamp
|number
|Yes
|An integer timestamp of the current UNIX epoch in milliseconds when the request was generated. This value is used by the encryption layer to validate the request.
|-
|method
|string
|Yes
|A string corresponding to a method to be run by the receiving peer.
|-
|params
|any
|No
|Arguments supplied for the method. The value of this key depends on the method used and is omitted for some methods.
|}
All available request methods and their parameters are documented below.
 
===== Notifications =====
Notifications are requests which do not contain an ID. Otherwise, they are identical to a standard request object. Notifications can be sent by either peer and do not receive a response.
 
Like standard requests, notifications may or may not have parameters and its value will depend on the method. Types of notifications are documented below.
 
==== Responses ====
Every request sent must have a matching response. An example response to the media.search request shown above:<syntaxhighlight lang="json">
{
    "tapto": 1,
    "id": "9ab7679f-6de9-11ef-9a9b-020304050607",
    "timestamp": 1725803557,
    "result": {
        "results": [{
            "system": {
                "id": "Gameboy",
                "name": "Gameboy"
            },
            "name": "240p Test Suite (PD) v0.03 tepples",
            "path": "Gameboy/240p Test Suite (PD) v0.03 tepples.gb"
        }],
        "total": 1
    }
}
</syntaxhighlight>Response keys:
{| class="wikitable"
!Key
!Type
!Required
!Description
|-
|tapto
|number
|Yes
|Same as a request.
|-
|id
|string
|Yes
|Same as a request. The same ID sent by the original request.
|-
|timestamp
|number
|Yes
|Same as a request, with an updated time.
|-
|result
|any
|No*
|Return value of the method. May be null depending on the method. See methods for possible values.
|-
|error
|Error
|No*
|If a method failed, this key will be populated with the error details and the result key will be empty. See below for details about errors.
|}
 
===== Response Errors =====
If a method fails, it will populate the error key in the response object with details about the failure. An example of a failed request:<syntaxhighlight lang="json">
{
    "tapto": 1,
    "id": "9ab7679f-6de9-11ef-9a9b-020304050607",
    "timestamp": 1725805903,
    "error": {
        "code": 1,
        "message": "query or system is required"
    }
}
</syntaxhighlight>Error keys:
{| class="wikitable"
!Key
!Type
!Required
!Description
|-
|code
|number
|Yes
|An integer specifying the general error category.
|-
|message
|string
|Yes
|Short human readable message explaining the error cause if possible.
|}
{{Warn|Error codes are not finalised yet.}}
 
==== Protocol Errors ====
If a low-level error occurs before a request context can be established, a protocol error will be sent back. This can happen, for example, if a JSON payload is malformed or a payload could not be decrypted. They're identical to an error response except they will have no ID.
 
Protocol errors may be sent unencrypted if a secure context couldn't be established.

Revision as of 14:42, 8 September 2024

This page refers to the future version 2.0.0 of TapTo which is in active development. Please don't use any information on this page until it's been finalised and released.

The TapTo API is an API available on and published by every device running the core TapTo software. This API allows management of all TapTo features which would not present a security risk. The TapTo Life app uses this API for all communication with TapTo devices.

This page documents the protocol used to communicate with the API and each method available to interact with a TapTo device. It is the source of truth when developing applications that interact with TapTo.

Communication Protocol

The API uses a standard WebSocket connection to exchange JSON payloads using a custom variant of the JSON-RPC 2.0 protocol. It is not compatible with standard JSON-RPC libraries.

All remote unsecured WebSocket connections must encrypt every payload using the encryption layer detailed below, or else the payload will be immediately rejected. Local unencrypted connections are allowed, depending on the platform and privilege context of the running service.

Connection

Connections to the API can be established with any standard WebSocket client, using the root endpoint (/) of the HTTP server published by the TapTo service. By default, the HTTP server is accessible on port 7497. Keep in mind this port is configurable by the user.

An example address for connecting to the API: ws://10.0.0.123:7497/

The connection requires no special configuration or authentication to begin.

JSON Payloads

Peers communicate back and forth using JSON payloads and a request-response based on the JSON-RPC 2.0 protocol. The TapTo protocol is incompatible with existing JSON-RPC libraries.

Because a WebSocket connection is asynchronous, request payloads are tagged with a unique ID. The client peer must keep track of IDs sent to another client and wait for a matching response object.

Requests

A request object asks the connected peer to run a pre-defined method, and report back when it's completed with a response object.

An example request:

{
    "tapto": 1,
    "id": "9ab7679f-6de9-11ef-9a9b-020304050607",
    "timestamp": 1725803556229,
    "method": "media.search",
    "params": {
        "query": "240p"
    }
}

This request would query TapTo's media database for a file containing the word "240p" and return a response with the search results.

Request keys:

Key Type Required Description
tapto number Yes Specifies the protocol version and is used to validate a payload. It must be contained in every request or else the request will be rejected. Currently this must be the integer 1.
id string Yes* A UUID v1 generated by the requesting client, used to match requests back to responses. A request missing this key is valid but would be treated as a notification and not receive any response (or an error).
timestamp number Yes An integer timestamp of the current UNIX epoch in milliseconds when the request was generated. This value is used by the encryption layer to validate the request.
method string Yes A string corresponding to a method to be run by the receiving peer.
params any No Arguments supplied for the method. The value of this key depends on the method used and is omitted for some methods.

All available request methods and their parameters are documented below.

Notifications

Notifications are requests which do not contain an ID. Otherwise, they are identical to a standard request object. Notifications can be sent by either peer and do not receive a response.

Like standard requests, notifications may or may not have parameters and its value will depend on the method. Types of notifications are documented below.

Responses

Every request sent must have a matching response. An example response to the media.search request shown above:

{
    "tapto": 1,
    "id": "9ab7679f-6de9-11ef-9a9b-020304050607",
    "timestamp": 1725803557,
    "result": {
        "results": [{
            "system": {
                "id": "Gameboy",
                "name": "Gameboy"
            },
            "name": "240p Test Suite (PD) v0.03 tepples",
            "path": "Gameboy/240p Test Suite (PD) v0.03 tepples.gb"
        }],
        "total": 1
    }
}

Response keys:

Key Type Required Description
tapto number Yes Same as a request.
id string Yes Same as a request. The same ID sent by the original request.
timestamp number Yes Same as a request, with an updated time.
result any No* Return value of the method. May be null depending on the method. See methods for possible values.
error Error No* If a method failed, this key will be populated with the error details and the result key will be empty. See below for details about errors.
Response Errors

If a method fails, it will populate the error key in the response object with details about the failure. An example of a failed request:

{
    "tapto": 1,
    "id": "9ab7679f-6de9-11ef-9a9b-020304050607",
    "timestamp": 1725805903,
    "error": {
        "code": 1,
        "message": "query or system is required"
    }
}

Error keys:

Key Type Required Description
code number Yes An integer specifying the general error category.
message string Yes Short human readable message explaining the error cause if possible.
Error codes are not finalised yet.

Protocol Errors

If a low-level error occurs before a request context can be established, a protocol error will be sent back. This can happen, for example, if a JSON payload is malformed or a payload could not be decrypted. They're identical to an error response except they will have no ID.

Protocol errors may be sent unencrypted if a secure context couldn't be established.