Managing the node over the HTTP API

Everything the web interface does, the node can do on a request from outside: the HTTP API reads and changes the configuration of the running service and reports its state. Together with the web interface these are the only interfaces that apply a change immediately and report the result.

This page gives the general picture: where the API is, how it is arranged, how errors arrive and how it differs from editing the settings file. The reference for the individual requests and keys is in separate documents (Reference documents); it is not repeated here.

Access

The API answers on the same web server as the administration interface. In the configuration as delivered that is port 8808; if no port is set in the settings at all, the service uses the built-in value 43971. The TLS port is 43981, but immediately after installation TLS is off and that port is not listened on (Initial settings). The API has no address or prefix of its own such as /api.

  • HTTP and HTTPS are equal. The redirect from the open port to TLS affects only the pages of the interface; API requests keep working over both protocols.

  • Authentication is HTTP Digest, with the same accounts as the web interface and the same roles: Admin — full access, Restricted admin — read everything and pause a stream, its input or its output, Viewer — read only. A write performed outside one’s role is refused. Instead of a password the session can be presented with an auto-login key — a cookie, the X-Auth-Token header or the ?auth-token= parameter.

  • Requests from the node itself are not authenticated. A call that arrived on the loopback interface (127.0.0.1, ::1) passes without Digest and gets the Admin role. This cannot be turned off; there is no setting for it. The concession does have bounds: it cannot be claimed from outside the node — giving yourself a loopback address with a header will not work — and it is withdrawn for a cross-origin request, since otherwise a web page open on the node would command the whole API through 127.0.0.1 with no credentials at all.

    There is one consequence to act on: any process on the node commands the configuration without a password. If a reverse proxy is put in front of the API, point it at a non-loopback address of the same node — then authentication works as usual. A proxy that reaches 127.0.0.1 hands full access to everyone whose requests it forwards.

  • There are only two methodsGET and POST. Any other method gets the answer “method not supported”; the exception is the browser’s preflight OPTIONS request, which the server answers with a permission if the origin of the request is allowed.

Warning

The role restricts writing only. The role check is performed for POST requests; reading is not restricted at all, and the values come back as they are, unmasked. An account with the Viewer role sees every password, the Meshwork secrets, the transport passphrases and the content-protection keys — and exporting a backup copy of the settings is a read as well, which is the whole configuration in one request. The Viewer role limits the ability to change the node, not access to its secrets: create one on that understanding.

The delivery of streams and of the electronic program guide runs on ports of its own and does not manage settings (Initial settings).

What the API is made of

Family

Purpose

/config/…

Reading and changing the configuration. The tree of requests mostly repeats the structure of the settings file: a section of the file is a node of the tree (The structure of the document). There are divergences: the array of archive storages is addressed as /config/dvr-storage and the program-guide channel sets as /config/epg-channel-set, although in the file they sit inside dvr-storage-list and epg-server.

/data/…

The state of the running service, mostly for reading: the streams and their pipelines, the hardware, the program guide, the system monitor, the log, the license information. A few requests change state — resetting statistics, starting a scan, clearing an alert; only one of them edits the configuration — removing a Meshwork peer from the domain overview. Ready-made request examples are in Single-day schedule in JSON and Complaint assistant.

/schema/…

Reference lists in JSON format, read-only: the input and output types supported by this build, the languages, the receiver cards and transcoder devices that were found, the severity scale and the alert codes. They have nothing to do with the settings schema file (Checking against the JSON Schema).

Individual addresses

A few service requests outside these trees: restarting the service, exporting and restoring a backup copy of the settings, the list of network interfaces, ending the session.

How errors arrive

An application-level error is returned by the API with HTTP code 200 and a non-zero result field in the body of the response: a value out of range, a failed check, an attempt to write an immutable key, a refusal to write a key this role may not touch.

A script that checks only the HTTP code will therefore count every such refusal as a success, one after another. Parse the body of the response.

Codes other than 200 do occur, but they mean something else: 401 — authentication did not pass, 403 — the role is not admitted to the request itself, 404 — there is no such request, 405 — the method is not supported. A refusal by role therefore arrives in two different ways: the whole request is rejected with code 403, while an individual inadmissible key comes back in an ordinary response with a non-zero result.

A value outside the permitted range the API refuses. That is how it differs from reading the settings file, where such a value is clamped to the edge of the range (Accepted, but not as the person editing intended).

An unknown key the API does not refuse: it is skipped exactly as when the file is read, the response arrives with result 0, and the only trace is in the node’s log. A typo in a key name is therefore invisible here as well — key names are checked in advance against the schema (Checking against the JSON Schema).

Changes that need a restart

Two changes take effect only after a restart of the service: license activation and the restoration of the settings from a backup. Neither of them leaves the restart to the operator’s discretion: having accepted the file, the service restarts itself about four seconds later — that cannot be postponed, and the node is unavailable while it restarts. The responses to these two requests carry no reboot field; in the JSON responses of the configuration API it means that the node is already going down for a restart, and not that a restart is waiting for a command. A node whose license has expired restarts in the same way, on its own. Restarting the service at one’s own will is possible with a separate request, from the web interface or with the command sudo systemctl restart pss.

Changing the listening ports and turning TLS on do not need a restart of the service: it closes the listening socket and opens it again, and there will be no reboot field in the response. The connections open on that port are broken in the process, and from then on you have to connect on the new port.

The API or the settings file

HTTP API

The pss.json file

When it takes effect

Immediately

From the next start of the service

State of the service

Running

Stopped

Result

Returned in the response

Visible only in the log after the start

A value out of range

Refused

Clamped to the edge

An unknown key

Ignored silently, result 0

Ignored silently, unless you read the log

What it is good for

Pinpoint changes, automation, observation

Bulk edits, carrying settings between nodes and versions

Editing the file of a running service is useless and dangerous: the service overwrites pss.json from what it holds in memory, and it does so on a schedule of its own — the edit will disappear without a single message. Stop the service and check the file against the schema before starting it; the procedure is Editing, checking and carrying the settings.

Reference documents

Document

Contents

http_config_api.txt

The reference for the configuration API: the protocol, the operations, the /config tree and an entry-by-entry description of every key — type, constraints, default value.

http_data_api.txt

The reference for the state and statistics API: the /data tree, the response formats, the requests to the log and to the databases.

pss_config_file.txt

The reference for the format of the settings file. Its account for the operator is The pss.json settings file.

pss_config_editing.txt

The procedures for editing, checking and carrying the settings. Their account is Editing, checking and carrying the settings.

pss.schema.json, pss.compat.schema.json

A machine-readable description of the settings file in JSON Schema format (Checking against the JSON Schema).

The documents are written in English. They are not part of the package: they are not on the node and there is no point looking for them there.

All of it is published on the documentation site, one directory per product version:

https://doc2.pstreamer.tv/reference/      four reference documents
https://doc2.pstreamer.tv/schema/         two schemas

Take the directory for the version you have installed: a reference from another release does not describe your node.

Warning

Backward compatibility is not guaranteed. An update may change the HTTP API, the schema and the format of the settings file alike: the set and the names of the keys, the ranges of values, the shape of requests and responses. Check the scripts that work with the API again after every update, and take the reference documents and the schema of the same version as the installed build.

Three rules follow from this for anyone writing their own integration:

  • Pin the version the script was written for, and check it at startup.

  • Read a write back after writing it. A key that no longer exists in the new build is not refused but ignored, and the response reports success: the one request that would have caught such a disappearance is the one that will not catch it.

  • An attribute missing from the response means “this version does not report it”, not zero. Otherwise a metric removed or renamed at an update turns into a plausible measurement of something that does not exist.