Files
shopdb-flask/docs/openapi.json
cproudlock 762d1b7210 Make the API usable by an agent, and stop the contract going stale
Someone writing a script against ShopDB had two options: read a 705 KB spec, or
guess. The spec is the reference, not an index, and handing an agent the whole
thing means either truncating it or spending a context window on 479 operations
nobody asked about.

Three additions, each feeding the next.

/api/docs/operations.txt is the index: every operation on one line with its
method, path, tag, auth and summary, at around 70 KB for all 486. A caller can
hold the entire API at once, find the four operations it needs, and only then
fetch their schemas.

/api/docs/openapi.json?tag=... narrows the spec to one of the 41 tag groups.
Components are kept intact deliberately: pruning the schema graph to match would
leave references resolving to nothing, and a generator that fails confusingly is
worse than a file that is larger than strictly necessary.

tools/mcp/ is an MCP server built on both. Five tools rather than 483, because a
tool per operation is unusable - clients degrade past a few dozen and models
start picking the wrong one. It reads everything from the live instance at call
time, so enabling a plugin adds operations it can already reach with no change
here. The token is the security boundary and the README says so plainly: every
operation the credential permits is reachable, so exploratory work wants a
read-scoped token.

The rest of this is about the contract not drifting, which is what makes any of
the above trustworthy.

Two CI jobs:

- api-contract runs the parity gates and then regenerates the spec and fails if
  anything changed. Those gates already existed and already worked - they caught
  both routes added here, unprompted - but nothing ran them except by hand, and
  the committed spec had silently drifted by three operations, including two
  setup endpoints added the day before.
- migrations-mysql is the job the header comment has been claiming for some
  time while not existing. It described "the REAL multi-site deploy path" and
  "what catches an Alembic regression on MySQL before it ships", and there was
  no such job. That is worse than no comment: it is the false confidence that
  let a migration ship which could not build a schema on a fresh MySQL database.
  The suite runs on SQLite, and SQLite accepts a foreign key onto a table that
  does not exist.

CONTRIBUTING.md now says to run gen_openapi.py --refresh after changing a route,
and that a route the sweep cannot classify belongs in PUBLIC_ENDPOINTS with a
reason rather than hand-edited into the inventory, which the next refresh would
overwrite. The new index route is declared there alongside the spec it indexes.
2026-09-20 12:59:49 -04:00

34405 lines
927 KiB
JSON

{
"openapi": "3.1.0",
"info": {
"title": "ShopDB Flask API",
"version": "0.12.0",
"description": "Asset-management API (core + plugins). Responses use a `success_response` envelope: `{status, data, meta}`. Auth: Bearer JWT (login or a managed PAT) for `jwt`/`admin`/`permission:*`; `X-API-Key` for collector/managed-token endpoints; public endpoints need neither. A permission-gated route is published as bearer-required, which is what a default install does - a site that grants the permission to the `guest` role makes that same route answer a caller with no token."
},
"servers": [
{
"url": "/",
"description": "relative to the deployed mount"
}
],
"components": {
"schemas": {
"SuccessEnvelope": {
"type": "object",
"properties": {
"status": {
"type": "string",
"enum": [
"success"
]
},
"data": {
"description": "The payload. Shape is per endpoint."
},
"meta": {
"type": "object",
"properties": {
"timestamp": {
"type": "string",
"format": "date-time"
},
"requestid": {
"type": "string"
},
"pagination": {
"type": "object",
"properties": {
"page": {
"type": "integer"
},
"perpage": {
"type": "integer"
},
"total": {
"type": "integer"
},
"pages": {
"type": "integer"
}
}
}
}
}
},
"required": [
"status"
]
},
"ErrorEnvelope": {
"type": "object",
"properties": {
"status": {
"type": "string",
"enum": [
"error"
]
},
"data": {
"type": "object",
"properties": {
"error": {
"type": "object",
"properties": {
"code": {
"type": "string"
},
"message": {
"type": "string"
},
"details": {
"type": "object"
}
},
"required": [
"code",
"message"
]
}
},
"required": [
"error"
]
},
"meta": {
"type": "object"
}
},
"required": [
"status",
"data"
]
}
},
"securitySchemes": {
"bearerAuth": {
"type": "http",
"scheme": "bearer",
"bearerFormat": "JWT",
"description": "Login token or a managed Personal Access Token (scoped)."
},
"apiKeyAuth": {
"type": "apiKey",
"in": "header",
"name": "X-API-Key",
"description": "A managed service or device token in a header. X-API-Key for collector and managed tokens (collector.ingest, and any service permission a plugin declares); X-Endpoint-Bootstrap-Token for agent bootstrap; X-Kiosk-Token for a kiosk screen. The operation description names the header and, where the gate is token-OR-network, the allowlist that is the other half."
},
"setupCodeAuth": {
"type": "apiKey",
"in": "query",
"name": "code",
"description": "A single-use provisioning code, redeemed in the query string because the caller is a browser being pointed at a URL. Spent on any attempt, right or wrong, and short-lived."
}
}
},
"tags": [
{
"name": "core-apitokens"
},
{
"name": "core-applications"
},
{
"name": "core-assets"
},
{
"name": "core-auditlogs"
},
{
"name": "core-auth"
},
{
"name": "core-businessunits"
},
{
"name": "core-collector"
},
{
"name": "core-customfields"
},
{
"name": "core-dashboard"
},
{
"name": "core-dashboarddefaults"
},
{
"name": "core-docs"
},
{
"name": "core-employees"
},
{
"name": "core-locations"
},
{
"name": "core-maplevels"
},
{
"name": "core-mappositions"
},
{
"name": "core-models"
},
{
"name": "core-modeltypes"
},
{
"name": "core-operatingsystems"
},
{
"name": "core-plugins"
},
{
"name": "core-pluginui"
},
{
"name": "core-reports"
},
{
"name": "core-scripts"
},
{
"name": "core-search"
},
{
"name": "core-settings"
},
{
"name": "core-setup"
},
{
"name": "core-shopdbbackups"
},
{
"name": "core-supportteams"
},
{
"name": "core-users"
},
{
"name": "core-vendors"
},
{
"name": "plugin-backups"
},
{
"name": "plugin-computers"
},
{
"name": "plugin-endpoints"
},
{
"name": "plugin-guides"
},
{
"name": "plugin-knowledgebase"
},
{
"name": "plugin-machines"
},
{
"name": "plugin-network"
},
{
"name": "plugin-notifications"
},
{
"name": "plugin-printers"
},
{
"name": "plugin-slides"
},
{
"name": "plugin-tools"
},
{
"name": "plugin-warranty"
}
],
"paths": {
"/api/apitokens": {
"get": {
"tags": [
"core-apitokens"
],
"summary": "List the caller's own tokens. Admins may pass ?all=true for everyone's.",
"description": "List the caller's own tokens. Admins may pass ?all=true for everyone's.\n\n**Auth:** jwt\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/apitokens -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"createddate": "2026-01-01T00:00:00.000000Z",
"displayprefix": "<redacted:secret>",
"expiresat": null,
"isactive": true,
"isexpired": false,
"lastusedat": null,
"name": "member token",
"resourcescopes": null,
"scopes": null,
"tokenid": 2,
"tokenprefix": "<redacted:secret>",
"userid": 2,
"username": "<redacted:person>"
},
{
"createddate": "2026-01-01T00:00:00.000000Z",
"displayprefix": "<redacted:secret>",
"expiresat": null,
"isactive": true,
"isexpired": false,
"lastusedat": null,
"name": "admin token",
"resourcescopes": null,
"scopes": null,
"tokenid": 1,
"tokenprefix": "<redacted:secret>",
"userid": 1,
"username": "<redacted:person>"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "all",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "false"
}
}
]
},
"post": {
"tags": [
"core-apitokens"
],
"summary": "Create a token for the caller. Returns the full secret ONCE.",
"description": "Create a token for the caller. Returns the full secret ONCE.\n\n**Auth:** permission:apitokens.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/apitokens -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"displayprefix": "<redacted:secret>",
"expiresat": null,
"isactive": true,
"isexpired": false,
"lastusedat": null,
"name": "direct token",
"resourcescopes": null,
"scopes": [
"applications.create"
],
"secret": "<redacted:secret>",
"tokenid": 1,
"tokenprefix": "<redacted:secret>",
"userid": 1,
"warning": "Save this token now. It will not be shown again. Store it somewhere safe."
},
"message": "Token created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"name": "direct token",
"scopes": [
"applications.create"
]
}
}
}
}
}
},
"/api/apitokens/{tokenid}": {
"delete": {
"tags": [
"core-apitokens"
],
"summary": "Revoke (deactivate) a token. Own token, or any if admin.",
"description": "Revoke (deactivate) a token. Own token, or any if admin.\n\n**Auth:** permission:apitokens.create\n\n**Params:** path: tokenid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/apitokens/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "Token revoked",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "tokenid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-apitokens"
],
"summary": "Rename, rescope, or deactivate a token. Own token, or any if admin.",
"description": "Rename, rescope, or deactivate a token. Own token, or any if admin.\n\n**Auth:** permission:apitokens.create\n\n**Params:** path: tokenid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/apitokens/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"displayprefix": "<redacted:secret>",
"expiresat": null,
"isactive": true,
"isexpired": false,
"lastusedat": null,
"name": "test token",
"resourcescopes": null,
"scopes": [
"applications.edit"
],
"tokenid": 1,
"tokenprefix": "<redacted:secret>",
"userid": 1
},
"message": "Token updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "tokenid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: tokenid (int); body: JSON (fields not yet documented)"
},
"example": {
"scopes": [
"applications.edit"
]
}
}
}
}
}
},
"/api/applications": {
"get": {
"tags": [
"core-applications"
],
"summary": "List all applications.",
"description": "List all applications.\n\n**Auth:** permission:applications.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/applications -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "appname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "installable",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "showhidden",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "false"
}
}
]
},
"post": {
"tags": [
"core-applications"
],
"summary": "Create a new application.",
"description": "Create a new application.\n\n**Auth:** permission:applications.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/applications -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appdescription": null,
"appid": 1,
"applicationlink": null,
"applicationnotes": null,
"appname": "Before Revoke",
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"documentationpath": null,
"image": null,
"installersha256": null,
"installpath": null,
"isactive": true,
"ishidden": false,
"isinstallable": false,
"islicenced": false,
"ismonitorable": false,
"isprinter": false,
"isrequired": false,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"monitorlaunchpath": null,
"monitorprocessname": null,
"supportteamid": null,
"supportteamname": null,
"teamurl": null
},
"message": "Application created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"appname": "No Backdate",
"createddate": "2026-01-01 00:00:00"
}
}
}
}
}
},
"/api/applications/{app_id}": {
"delete": {
"tags": [
"core-applications"
],
"summary": "Permanently delete an application, its versions, and its uploads.",
"description": "Permanently delete an application, its versions, and its uploads.\n\n**Auth:** permission:applications.delete\n\n**Params:** path: app_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/applications/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"deactivatedpolicies": [
"Required app: Doomed",
"Hand made push"
],
"policyresult": "kept"
},
"message": "Application deleted; deactivated 2 policy(ies) that referenced it: Required app: Doomed, Hand made push",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": false,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "This route reads a JSON body. The example is a request that worked."
},
"example": {
"confirm": "OK"
}
}
}
}
},
"get": {
"tags": [
"core-applications"
],
"summary": "Get a single application with details.",
"description": "Get a single application with details.\n\n**Auth:** permission:applications.view\n\n**Params:** path: app_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/applications/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appdescription": null,
"appid": 1,
"applicationlink": null,
"applicationnotes": null,
"appname": "TeamApp",
"contacts": [
{
"name": "Alice",
"sso": "a01"
}
],
"createddate": "2026-01-01T00:00:00.000000Z",
"documentationpath": null,
"image": null,
"installedcount": 0,
"installersha256": null,
"installpath": null,
"isactive": true,
"ishidden": false,
"isinstallable": false,
"islicenced": false,
"ismonitorable": false,
"isprinter": false,
"isrequired": false,
"knowledgebase": [],
"modifieddate": "2026-01-01T00:00:00.000000Z",
"monitorlaunchpath": null,
"monitorprocessname": null,
"supportteamid": 1,
"supportteamname": "Controls",
"teamurl": "https://sn.example/controls",
"versions": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-applications"
],
"summary": "Update an application.",
"description": "Update an application.\n\n**Auth:** permission:applications.edit\n\n**Params:** path: app_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/applications/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appdescription": null,
"appid": 1,
"applicationlink": null,
"applicationnotes": null,
"appname": "Test App",
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"documentationpath": null,
"image": null,
"installersha256": null,
"installpath": null,
"isactive": true,
"ishidden": false,
"isinstallable": false,
"islicenced": false,
"ismonitorable": false,
"isprinter": false,
"isrequired": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"monitorlaunchpath": null,
"monitorprocessname": null,
"policynote": "A configuration policy was created for this application, but it is not attached to any business policy and installs nothing until an admin adds it to one.",
"policyresult": "created",
"supportteamid": null,
"supportteamname": null,
"teamurl": null
},
"message": "Application updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: app_id (int); body: JSON (fields not yet documented)"
},
"example": {
"ismonitorable": false,
"monitorlaunchpath": "",
"monitorprocessname": ""
}
}
}
}
}
},
"/api/applications/{app_id}/image": {
"delete": {
"tags": [
"core-applications"
],
"summary": "Remove an application's image and clear the field.",
"description": "Remove an application's image and clear the field.\n\n**Auth:** permission:applications.edit\n\n**Params:** path: app_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/applications/1/image -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-applications"
],
"summary": "Upload (or replace) an application's image.",
"description": "Upload (or replace) an application's image.\n\n**Auth:** permission:applications.edit\n\n**Params:** path: app_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/applications/1/image -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appdescription": null,
"appid": 1,
"applicationlink": null,
"applicationnotes": null,
"appname": "Test App",
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"documentationpath": null,
"image": "/api/applications/image/application-1.png",
"installersha256": null,
"installpath": null,
"isactive": true,
"ishidden": false,
"isinstallable": false,
"islicenced": false,
"ismonitorable": false,
"isprinter": false,
"isrequired": false,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"monitorlaunchpath": null,
"monitorprocessname": null,
"supportteamid": null,
"supportteamname": null,
"teamurl": null
},
"message": "Application image uploaded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: app_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/applications/{app_id}/installed": {
"get": {
"tags": [
"core-applications"
],
"summary": "List all computers that have this application installed.",
"description": "List all computers that have this application installed.\n\n**Auth:** permission:applications.view\n\n**Params:** path: app_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/applications/1/installed -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/applications/{app_id}/package": {
"delete": {
"tags": [
"core-applications"
],
"summary": "Remove an uploaded installer and clear the path it set.",
"description": "Remove an uploaded installer and clear the path it set.\n\n**Auth:** permission:applications.edit\n\n**Params:** path: app_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/applications/1/package -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appdescription": null,
"appid": 1,
"applicationlink": null,
"applicationnotes": null,
"appname": "Test App",
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"documentationpath": null,
"image": null,
"installersha256": null,
"installpath": "<redacted:sharepath>",
"isactive": true,
"ishidden": false,
"isinstallable": false,
"islicenced": false,
"ismonitorable": false,
"isprinter": false,
"isrequired": false,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"monitorlaunchpath": null,
"monitorprocessname": null,
"supportteamid": null,
"supportteamname": null,
"teamurl": null
},
"message": "Installer removed",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-applications"
],
"summary": "Upload (or replace) the installer for an application.",
"description": "Upload (or replace) the installer for an application.\n\n**Auth:** permission:applications.edit\n\n**Params:** path: app_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/applications/1/package -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appdescription": null,
"appid": 1,
"applicationlink": null,
"applicationnotes": null,
"appname": "Test App",
"appversionid": null,
"bytes": 130,
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"detectedversion": "<redacted:address>",
"documentationpath": null,
"image": null,
"installersha256": "<redacted:digest>",
"installpath": "/api/applications/package/1/setup.exe",
"isactive": true,
"ishidden": false,
"isinstallable": false,
"islicenced": false,
"ismonitorable": false,
"isprinter": false,
"isrequired": false,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"monitorlaunchpath": null,
"monitorprocessname": null,
"sha256": "<redacted:digest>",
"supportteamid": null,
"supportteamname": null,
"teamurl": null,
"uploadedfilename": "setup.exe"
},
"message": "Installer uploaded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: app_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/applications/{app_id}/revert": {
"post": {
"tags": [
"core-applications"
],
"summary": "Strip an application back to a catalogue record.",
"description": "Strip an application back to a catalogue record.\n\n**Auth:** permission:applications.edit\n\n**Params:** path: app_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/applications/1/revert -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appdescription": null,
"appid": 1,
"applicationlink": null,
"applicationnotes": null,
"appname": "Test App",
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"documentationpath": null,
"image": "/api/applications/image/application-1.png",
"installersha256": null,
"installpath": null,
"isactive": true,
"ishidden": false,
"isinstallable": false,
"islicenced": false,
"ismonitorable": false,
"isprinter": false,
"isrequired": false,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"monitorlaunchpath": null,
"monitorprocessname": null,
"supportteamid": null,
"supportteamname": null,
"teamurl": null
},
"message": "Application reverted to record",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: app_id (int); body: JSON (fields not yet documented)"
},
"example": {
"confirm": "OK"
}
}
}
}
}
},
"/api/applications/{app_id}/versions": {
"get": {
"tags": [
"core-applications"
],
"summary": "List all versions for an application.",
"description": "List all versions for an application.\n\n**Auth:** permission:applications.view\n\n**Params:** path: app_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/applications/1/versions -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-applications"
],
"summary": "Create a new version for an application.",
"description": "Create a new version for an application.\n\n**Auth:** permission:applications.create\n\n**Params:** path: app_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/applications/1/versions -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appid": 1,
"appversionid": 1,
"dateadded": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"notes": null,
"releasedate": null,
"sha256": "<redacted:digest>",
"silentargs": "/S /v/qn",
"version": "1.2.3"
},
"message": "Version created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: app_id (int); body: JSON (fields not yet documented)"
},
"example": {
"sha256": "<redacted:digest>",
"silentargs": "/S /v/qn",
"version": "1.2.3"
}
}
}
}
}
},
"/api/applications/image/{filename}": {
"get": {
"tags": [
"core-applications"
],
"summary": "Serve an uploaded application image.",
"description": "Serve an uploaded application image.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** path: filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/applications/image/example.png\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/applications/machines/{machine_id}": {
"get": {
"tags": [
"core-applications"
],
"summary": "List all applications installed on a computer.",
"description": "List all applications installed on a computer.\n\n**Auth:** permission:applications.view\n\n**Params:** path: machine_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/applications/machines/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"appdescription": null,
"appid": 1,
"appname": "Test App",
"appversionid": null,
"computerid": 1,
"id": 1,
"installeddate": "2026-01-01T00:00:00.000000Z",
"installedversion": "1.2.3",
"isactive": true
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "machine_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-applications"
],
"summary": "Install an application on a computer.",
"description": "Install an application on a computer.\n\n**Auth:** permission:applications.create\n\n**Params:** path: machine_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/applications/machines/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "machine_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: machine_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/applications/machines/{machine_id}/{app_id}": {
"delete": {
"tags": [
"core-applications"
],
"summary": "Uninstall an application from a computer.",
"description": "Uninstall an application from a computer.\n\n**Auth:** permission:applications.delete\n\n**Params:** path: machine_id (int), app_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/applications/machines/1/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "machine_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-applications"
],
"summary": "Update installed application (e.g., change version).",
"description": "Update installed application (e.g., change version).\n\n**Auth:** permission:applications.edit\n\n**Params:** path: machine_id (int), app_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/applications/machines/1/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "machine_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: machine_id (int), app_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/applications/package/{filename}": {
"get": {
"tags": [
"core-applications"
],
"summary": "Download an uploaded installer.",
"description": "Download an uploaded installer.\n\n**Auth:** permission:applications.download\n\n**Params:** path: filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/applications/package/example.png -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/assets": {
"get": {
"tags": [
"core-assets"
],
"summary": "List all assets with filtering and pagination.",
"description": "List all assets with filtering and pagination.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assetid": 1,
"assetnumber": "A-1",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "machine",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "mill",
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"serialnumber": "<redacted:host>",
"statusid": 1
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "businessunit_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "dir",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "asc"
}
},
{
"name": "include_type_data",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "false"
}
},
{
"name": "location_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "sort",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "assetnumber"
}
},
{
"name": "status_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "statusid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "type",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "type_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "typeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-assets"
],
"summary": "Create a new asset.",
"description": "Create a new asset.\n\n**Auth:** permission:assets.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/assets -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/assets/{asset_id}": {
"delete": {
"tags": [
"core-assets"
],
"summary": "Delete (soft delete) an asset.",
"description": "Delete (soft delete) an asset.\n\n**Auth:** permission:assets.delete\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/assets/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-assets"
],
"summary": "Get a single asset with full details.",
"description": "Get a single asset with full details.\n\n**Auth:** permission:assets.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "include_type_data",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
}
]
},
"put": {
"tags": [
"core-assets"
],
"summary": "Update an asset.",
"description": "Update an asset.\n\n**Auth:** permission:assets.edit\n\n**Params:** path: asset_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/assets/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: asset_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/assets/{asset_id}/communications": {
"get": {
"tags": [
"core-assets"
],
"summary": "Get all communications for an asset.",
"description": "Get all communications for an asset.\n\n**Auth:** permission:assets.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/1/communications -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/assets/{asset_id}/relationships": {
"get": {
"tags": [
"core-assets"
],
"summary": "Get all relationships for an asset.",
"description": "Get all relationships for an asset.\n\n**Auth:** permission:assets.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/1/relationships -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"incoming": [
{
"createddate": "2026-01-01T00:00:00.000000Z",
"inheritsposition": true,
"isactive": true,
"isdirectional": true,
"label": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"relationshipid": 1,
"relationshiptypeid": 1,
"relationshiptypename": "controls",
"sourceasset": {
"assetid": 1,
"assetnumber": "PC-1",
"assettypecolor": null,
"assettypeid": 2,
"assettypename": "computer",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"serialnumber": "<redacted:host>",
"statusid": 1
},
"sourceassetid": 1,
"targetassetid": 2
}
],
"outgoing": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/assets/lookup/{assetnumber}": {
"get": {
"tags": [
"core-assets"
],
"summary": "Look up an asset by its asset number.",
"description": "Look up an asset by its asset number.\n\n**Auth:** permission:assets.view\n\n**Params:** path: assetnumber (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/lookup/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetnumber",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/assets/map": {
"get": {
"tags": [
"core-assets"
],
"summary": "Get all assets with map positions for unified floor map display.",
"description": "Get all assets with map positions for unified floor map display.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/map -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assets": [
{
"assetid": 1,
"assetnumber": "2007",
"assettype": "machine",
"assettypeid": 1,
"businessunit": null,
"businessunitid": null,
"displayname": "<redacted:person>",
"dualpathpartner": null,
"levelid": null,
"location": null,
"locationid": null,
"mapx": 100,
"mapy": 100,
"name": null,
"primaryip": null,
"serialnumber": "<redacted:host>",
"status": null,
"statuscolor": null,
"statusid": 1,
"typedata": {
"assetid": 1,
"controllermodelid": null,
"controllervendorid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"islocationonly": false,
"lastmaintenancedate": null,
"machineid": 1,
"machinetypeid": null,
"maintenanceintervaldays": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"nextmaintenancedate": null,
"requiresmanualconfig": false,
"vendorid": null
}
},
{
"assetid": 2,
"assetnumber": "2008",
"assettype": "machine",
"assettypeid": 1,
"businessunit": null,
"businessunitid": null,
"displayname": "<redacted:person>",
"dualpathpartner": null,
"levelid": null,
"location": null,
"locationid": null,
"mapx": 110,
"mapy": 110,
"name": null,
"primaryip": null,
"serialnumber": "<redacted:host>",
"status": null,
"statuscolor": null,
"statusid": 1,
"typedata": {
"assetid": 2,
"controllermodelid": null,
"controllervendorid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"islocationonly": false,
"lastmaintenancedate": null,
"machineid": 2,
"machinetypeid": null,
"maintenanceintervaldays": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"nextmaintenancedate": null,
"requiresmanualconfig": false,
"vendorid": null
}
}
],
"filters": {
"assettypes": [
{
"assettype": "machine",
"assettypeid": 1,
"color": null,
"icon": null
}
],
"businessunits": [],
"locations": [],
"statuses": [],
"subtypes": {
"Computer": [],
"Machine": [],
"Network Device": [],
"Printer": []
}
},
"total": 2
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "assettype",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "statusid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "subtype",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/assets/relationships": {
"post": {
"tags": [
"core-assets"
],
"summary": "Create a relationship between two assets.",
"description": "Create a relationship between two assets.\n\n**Auth:** permission:assets.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/assets/relationships -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"inheritsposition": true,
"isactive": true,
"label": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"propagated": [
{
"createddate": "2026-01-01T00:00:00.000000Z",
"inheritsposition": true,
"isactive": true,
"label": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"relationshipid": 3,
"relationshiptypeid": 1,
"sourceassetid": 1,
"targetassetid": 3
}
],
"propagatedcount": 1,
"relationshipid": 2,
"relationshiptypeid": 1,
"sourceassetid": 1,
"targetassetid": 2
},
"message": "Relationship created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"relationshiptypeid": 1,
"sourceassetid": 1,
"targetassetid": 2
}
}
}
}
}
},
"/api/assets/relationships/{rel_id}": {
"delete": {
"tags": [
"core-assets"
],
"summary": "Delete an asset relationship.",
"description": "Delete an asset relationship.\n\n**Auth:** permission:assets.delete\n\n**Params:** path: rel_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/assets/relationships/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "Relationship deleted",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "rel_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/assets/relationshiptypes": {
"get": {
"tags": [
"core-assets"
],
"summary": "List all asset relationship types.",
"description": "List all asset relationship types.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/relationshiptypes -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"color": null,
"description": null,
"isdirectional": false,
"propagatesthrough": [],
"relationshiptype": "WiFi",
"relationshiptypeid": 1
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"core-assets"
],
"summary": "Create a new asset relationship type.",
"description": "Create a new asset relationship type.\n\n**Auth:** permission:assets.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/assets/relationshiptypes -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"color": null,
"description": null,
"isdirectional": true,
"propagatesthrough": [],
"relationshiptype": "Backup For",
"relationshiptypeid": 1
},
"message": "Relationship type created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"isdirectional": false,
"relationshiptype": "Dualpath"
}
}
}
}
}
},
"/api/assets/relationshiptypes/{type_id}": {
"delete": {
"tags": [
"core-assets"
],
"summary": "Delete a relationship type. Refused if any relationship still uses it.",
"description": "Delete a relationship type. Refused if any relationship still uses it.\n\n**Auth:** permission:assets.delete\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/assets/relationshiptypes/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-assets"
],
"summary": "Update a relationship type.",
"description": "Update a relationship type.\n\n**Auth:** permission:assets.edit\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/assets/relationshiptypes/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"color": null,
"description": null,
"isdirectional": false,
"propagatesthrough": [],
"relationshiptype": "USB",
"relationshiptypeid": 1
},
"message": "Relationship type updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
},
"example": {
"isdirectional": false
}
}
}
}
}
},
"/api/assets/statuses": {
"get": {
"tags": [
"core-assets"
],
"summary": "List all asset statuses.",
"description": "List all asset statuses.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/statuses -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-assets"
],
"summary": "Create a new asset status.",
"description": "Create a new asset status.\n\n**Auth:** permission:assets.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/assets/statuses -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/assets/statuses/{status_id}": {
"delete": {
"tags": [
"core-assets"
],
"summary": "Delete an asset status. Refused if any asset still uses it.",
"description": "Delete an asset status. Refused if any asset still uses it.\n\n**Auth:** permission:assets.delete\n\n**Params:** path: status_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/assets/statuses/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "status_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-assets"
],
"summary": "Get a single asset status.",
"description": "Get a single asset status.\n\n**Auth:** permission:assets.view\n\n**Params:** path: status_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/statuses/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "status_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-assets"
],
"summary": "Update an asset status.",
"description": "Update an asset status.\n\n**Auth:** permission:assets.edit\n\n**Params:** path: status_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/assets/statuses/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "status_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: status_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/assets/types": {
"get": {
"tags": [
"core-assets"
],
"summary": "List all asset types.",
"description": "List all asset types.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/types -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-assets"
],
"summary": "Create a new asset type.",
"description": "Create a new asset type.\n\n**Auth:** permission:assets.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/assets/types -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/assets/types/{type_id}": {
"get": {
"tags": [
"core-assets"
],
"summary": "Get a single asset type.",
"description": "Get a single asset type.\n\n**Auth:** permission:assets.view\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/assets/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-assets"
],
"summary": "Update an asset type's display fields (color/icon/description). The name, plugin, and table are structural and not...",
"description": "Update an asset type's display fields (color/icon/description). The name, plugin, and table are structural and not editable here.\n\n**Auth:** permission:assets.edit\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/assets/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/auditlogs": {
"get": {
"tags": [
"core-auditlogs"
],
"summary": "List audit logs with filtering and pagination.",
"description": "List audit logs with filtering and pagination.\n\n**Auth:** permission:audit.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/auditlogs -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 50,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "action",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "entitytype",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "from_date",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 50
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "to_date",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "userid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/auditlogs/entity/{entitytype}/{entityid}": {
"get": {
"tags": [
"core-auditlogs"
],
"summary": "Get audit history for a specific entity.",
"description": "Get audit history for a specific entity.\n\n**Auth:** permission:audit.view\n\n**Params:** path: entitytype (string), entityid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/auditlogs/entity/x/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "entitytype",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
},
{
"name": "entityid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/auditlogs/purge": {
"post": {
"tags": [
"core-auditlogs"
],
"summary": "Delete entries older than the retention window.",
"description": "Delete entries older than the retention window.\n\n**Auth:** permission:audit.purge\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/auditlogs/purge -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/auditlogs/retention": {
"get": {
"tags": [
"core-auditlogs"
],
"summary": "Size of the log and what the configured retention would remove.",
"description": "Size of the log and what the configured retention would remove.\n\n**Auth:** permission:audit.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/auditlogs/retention -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"expired": 0,
"newest": "2026-01-01T00:00:00.000000",
"oldest": "2026-01-01T00:00:00.000000",
"retentiondays": 30,
"total": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/auditlogs/stats": {
"get": {
"tags": [
"core-auditlogs"
],
"summary": "Get audit log statistics.",
"description": "Get audit log statistics.\n\n**Auth:** permission:audit.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/auditlogs/stats -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"actions": {},
"activeUsers": [],
"entities": {},
"recentCount": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/auth/change-password": {
"post": {
"tags": [
"core-auth"
],
"summary": "Change the authenticated user's own password.",
"description": "Change the authenticated user's own password.\n\n**Auth:** jwt\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/auth/change-password -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"mustchangepassword": "<redacted:secret>"
},
"message": "Password changed",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"current_password": "<redacted:secret>",
"new_password": "<redacted:secret>"
}
}
}
}
}
},
"/api/auth/login": {
"post": {
"tags": [
"core-auth"
],
"summary": "Authenticate user and return JWT tokens.",
"description": "Authenticate user and return JWT tokens.\n\n**Auth:** none (the login surface itself; rate limited, 5-strike lockout)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/auth/login -H 'Content-Type: application/json' -d '{}'\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"access_token": "<redacted:secret>",
"expires_in": 3600,
"refresh_token": "<redacted:secret>",
"token_type": "<redacted:secret>",
"user": {
"email": "<redacted:person>",
"firstname": "<redacted:person>",
"lastname": "<redacted:person>",
"mustchangepassword": "<redacted:secret>",
"permissions": [
"assets.view",
"assets.create",
"assets.edit",
"<trimmed for the example: 1 more>"
],
"roles": [
"admin"
],
"userid": 1,
"username": "<redacted:person>"
}
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"password": "<redacted:secret>",
"username": "<redacted:person>"
}
}
}
}
}
},
"/api/auth/logout": {
"post": {
"tags": [
"core-auth"
],
"summary": "Logout user (for frontend token cleanup).",
"description": "Logout user (for frontend token cleanup).\n\n**Auth:** jwt\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/auth/logout -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/auth/me": {
"get": {
"tags": [
"core-auth"
],
"summary": "Get current authenticated user info.",
"description": "Get current authenticated user info.\n\n**Auth:** jwt\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/auth/me -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"email": "<redacted:person>",
"firstname": "<redacted:person>",
"lastname": "<redacted:person>",
"mustchangepassword": "<redacted:secret>",
"permissions": [
"assets.view",
"assets.create",
"assets.edit",
"<trimmed for the example: 1 more>"
],
"roles": [
"admin"
],
"userid": 1,
"username": "<redacted:person>"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/auth/refresh": {
"post": {
"tags": [
"core-auth"
],
"summary": "Refresh access token using refresh token.",
"description": "Refresh access token using refresh token.\n\n**Auth:** jwt (refresh token)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/auth/refresh -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/businessunits": {
"get": {
"tags": [
"core-businessunits"
],
"summary": "List all business units.",
"description": "List all business units.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/businessunits -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "businessunit",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-businessunits"
],
"summary": "Create a new business unit.",
"description": "Create a new business unit.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/businessunits -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/businessunits/{bu_id}": {
"delete": {
"tags": [
"core-businessunits"
],
"summary": "Delete (deactivate) a business unit.",
"description": "Delete (deactivate) a business unit.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: bu_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/businessunits/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "bu_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-businessunits"
],
"summary": "Get a single business unit.",
"description": "Get a single business unit.\n\n**Auth:** permission:assets.view\n\n**Params:** path: bu_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/businessunits/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "bu_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-businessunits"
],
"summary": "Update a business unit.",
"description": "Update a business unit.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: bu_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/businessunits/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "bu_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: bu_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/collector/{pluginname}": {
"post": {
"tags": [
"core-collector"
],
"summary": "Generic collector ingest for any plugin (ADR-006).",
"description": "Generic collector ingest for any plugin (ADR-006).\n\n**Auth:** api-key (per-plugin collector token)\n\n**Params:** path: pluginname (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/collector/x -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"accessprotocols": [],
"action": "updated",
"assetid": 2,
"identityvalue": "LEGACYPC",
"machinelinks": [],
"measuringtoollinkcount": 0,
"measuringtoollinks": [],
"partmarkers": [
{
"assetid": 3,
"assetnumber": "LEGACYPC-PARTMARKER",
"operationassetid": null
}
],
"printerlinkcount": 0,
"printerlinks": [],
"status": "ok",
"warnings": [
"mapped ComputerType not found: Shopfloor PC",
"machine number '0615' is this PC's own asset number; marker not filed under an operation. Rename the PC asset to its hostname, or create the operation asset."
]
},
"message": "computers collector updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "pluginname",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: pluginname (string); body: JSON (fields not yet documented)"
},
"example": {
"hostname": "<redacted:host>",
"queues": [
{
"drivername": "HP Universal Printing PS",
"isdefault": true,
"portaddress": "<redacted:address>",
"portname": "IP_10.20.0.11",
"queuename": "PRINTER-A"
},
{
"drivername": "HP Universal Printing PS",
"isdefault": false,
"portaddress": "<redacted:address>",
"portname": "IP_10.20.0.12",
"queuename": "PRINTER-B"
},
{
"drivername": "HP Universal Printing PS",
"isdefault": false,
"portaddress": "<redacted:address>",
"portname": "IP_10.20.0.99",
"queuename": "Reception Copier"
}
]
}
}
}
}
}
},
"/api/collector/_schemas": {
"get": {
"tags": [
"core-collector"
],
"summary": "List collector schemas for all enabled plugins (JWT-protected).",
"description": "List collector schemas for all enabled plugins (JWT-protected).\n\n**Auth:** jwt\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/collector/_schemas -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/collector/apps": {
"post": {
"tags": [
"core-collector"
],
"summary": "Update installed applications for a PC (matched by hostname).",
"description": "Update installed applications for a PC (matched by hostname).\n\n**Auth:** api-key (collector token, legacy shared key)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/collector/apps -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/collector/bulk": {
"post": {
"tags": [
"core-collector"
],
"summary": "Bulk update multiple PCs at once.",
"description": "Bulk update multiple PCs at once.\n\n**Auth:** api-key (collector token, legacy shared key)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/collector/bulk -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"errors": [],
"notfound": [
"WJLEG01"
],
"timestamp": "2026-01-01T00:00:00.000000",
"updated": 0
},
"message": "0 PC(s) updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"pcs": [
{
"hostname": "<redacted:host>"
}
]
}
}
}
}
}
},
"/api/collector/heartbeat": {
"post": {
"tags": [
"core-collector"
],
"summary": "Record PC online status / heartbeat (single or batch).",
"description": "Record PC online status / heartbeat (single or batch).\n\n**Auth:** api-key (collector token, legacy shared key)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/collector/heartbeat -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"notfound": [
"WJLEG01"
],
"timestamp": "2026-01-01T00:00:00.000000",
"updated": 0
},
"message": "0 PC(s) heartbeat recorded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"hostname": "<redacted:host>"
}
}
}
}
}
},
"/api/collector/pc": {
"post": {
"tags": [
"core-collector"
],
"summary": "Update one PC from the collection script (matched by hostname).",
"description": "Update one PC from the collection script (matched by hostname).\n\n**Auth:** api-key (collector token, legacy shared key)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/collector/pc -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/collector/status": {
"get": {
"tags": [
"core-collector"
],
"summary": "Check collector API status.",
"description": "Check collector API status.\n\n**Auth:** api-key (per-plugin collector token)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/collector/status -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"endpoints": [
"POST /api/collector/<plugin>",
"GET /api/collector/_schemas",
"POST /api/collector/pc",
"<trimmed for the example: 1 more>"
],
"status": "ok",
"timestamp": "2026-01-01T00:00:00.000000"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/customfields": {
"get": {
"tags": [
"core-customfields"
],
"summary": "List custom-field definitions. Filter by ?assettypeid=. ?active=false includes inactive ones.",
"description": "List custom-field definitions. Filter by ?assettypeid=. ?active=false includes inactive ones.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/customfields -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "assettypeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-customfields"
],
"summary": "UNDOCUMENTED: customfields.create_field has no docstring.",
"description": "UNDOCUMENTED: customfields.create_field has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/customfields -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/customfields/{fieldid}": {
"delete": {
"tags": [
"core-customfields"
],
"summary": "UNDOCUMENTED: customfields.delete_field has no docstring.",
"description": "UNDOCUMENTED: customfields.delete_field has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: fieldid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/customfields/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "fieldid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-customfields"
],
"summary": "UNDOCUMENTED: customfields.update_field has no docstring.",
"description": "UNDOCUMENTED: customfields.update_field has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: fieldid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/customfields/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "fieldid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: fieldid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/customfields/asset/{assetid}": {
"get": {
"tags": [
"core-customfields"
],
"summary": "Active custom fields for an asset's type, merged with its values.",
"description": "Active custom fields for an asset's type, merged with its values.\n\n**Auth:** permission:assets.view\n\n**Params:** path: assetid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/customfields/asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-customfields"
],
"summary": "Upsert values for an asset. Body: {values: {fieldid: value, ...}}.",
"description": "Upsert values for an asset. Body: {values: {fieldid: value, ...}}.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: assetid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/customfields/asset/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: assetid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/dashboard": {
"get": {
"tags": [
"core-dashboard"
],
"summary": "Get dashboard summary data (asset-based).",
"description": "Get dashboard summary data (asset-based).\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboard -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"activeassets": 0,
"bystatus": {
"Unknown": 2
},
"counts": {
"machines": 2,
"networkdevices": 0,
"pcs": 0,
"printers": 0,
"total": 2
},
"countsactiveonly": true,
"dualpathcollapsed": false,
"inactiveexcluded": 0,
"inrepair": 0,
"recent": [
{
"assetid": 2,
"assetnumber": "2008",
"assettype": "machine",
"createddate": "2026-01-01T00:00:00.000000Z"
},
{
"assetid": 1,
"assetnumber": "2007",
"assettype": "machine",
"createddate": "2026-01-01T00:00:00.000000Z"
}
],
"statuses": {
"Unknown": 2
},
"totalassets": 2,
"totalmachines": 2,
"totalnetwork": 0,
"totalpc": 0,
"totalprinter": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/dashboard/capabilities": {
"get": {
"tags": [
"core-dashboard"
],
"summary": "What THIS caller can reach, for chrome that would otherwise only 401.",
"description": "What THIS caller can reach, for chrome that would otherwise only 401.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboard/capabilities -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"cansearch": false
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/dashboard/health": {
"get": {
"tags": [
"core-dashboard"
],
"summary": "Health check endpoint (no auth required).",
"description": "Health check endpoint (no auth required).\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboard/health\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"database": "healthy",
"status": "ok"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/dashboard/navigation": {
"get": {
"tags": [
"core-dashboard"
],
"summary": "Get navigation items from all loaded plugins.",
"description": "Get navigation items from all loaded plugins.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboard/navigation -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"icon": "layout-dashboard",
"name": "Dashboard",
"permission": "assets.view",
"position": 0,
"route": "/"
},
{
"icon": "map",
"name": "Map",
"permission": "assets.view",
"position": 4,
"route": "/map"
},
{
"icon": "bell",
"name": "Notifications",
"permission": "notifications.view",
"plugin": "notifications",
"position": 5,
"route": "/notifications"
},
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/dashboard/stats": {
"get": {
"tags": [
"core-dashboard"
],
"summary": "Get detailed statistics by asset type.",
"description": "Get detailed statistics by asset type.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboard/stats -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"bytype": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/dashboard/summary": {
"get": {
"tags": [
"core-dashboard"
],
"summary": "Get dashboard summary data (asset-based).",
"description": "Get dashboard summary data (asset-based).\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboard/summary -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"activeassets": 0,
"bystatus": {},
"counts": {
"machines": 0,
"networkdevices": 0,
"pcs": 0,
"printers": 0,
"total": 0
},
"countsactiveonly": true,
"dualpathcollapsed": true,
"inactiveexcluded": 0,
"inrepair": 0,
"recent": [],
"statuses": {},
"totalassets": 0,
"totalmachines": 0,
"totalnetwork": 0,
"totalpc": 0,
"totalprinter": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/dashboard/widgets": {
"get": {
"tags": [
"core-dashboard"
],
"summary": "Aggregate dashboard widget definitions from all enabled plugins.",
"description": "Aggregate dashboard widget definitions from all enabled plugins.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboard/widgets -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/dashboarddefaults": {
"get": {
"tags": [
"core-dashboarddefaults"
],
"summary": "List all visitor-IP -> business-unit mappings.",
"description": "List all visitor-IP -> business-unit mappings.\n\n**Auth:** permission:settings.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboarddefaults -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"core-dashboarddefaults"
],
"summary": "Create a visitor-IP -> business-unit mapping.",
"description": "Create a visitor-IP -> business-unit mapping.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/dashboarddefaults -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"businessunit": "Materials",
"businessunitid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"dashboarddefaultid": 1,
"description": "Materials lobby kiosk",
"displaypath": "/shopfloor",
"displayrole": "Dashboard",
"fqdn": "<redacted:host>",
"ipaddress": "<redacted:host>",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z"
},
"message": "Mapping created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"businessunitid": 1,
"description": "Materials lobby kiosk",
"ipaddress": "<redacted:host>"
}
}
}
}
}
},
"/api/dashboarddefaults/{default_id}": {
"delete": {
"tags": [
"core-dashboarddefaults"
],
"summary": "Delete (deactivate) a mapping.",
"description": "Delete (deactivate) a mapping.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: default_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/dashboarddefaults/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "Mapping deleted",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "default_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-dashboarddefaults"
],
"summary": "Update a mapping.",
"description": "Update a mapping.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: default_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/dashboarddefaults/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"businessunit": "Materials",
"businessunitid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"dashboarddefaultid": 1,
"description": "moved",
"displaypath": "/shopfloor",
"displayrole": "Dashboard",
"fqdn": "<redacted:host>",
"ipaddress": "<redacted:host>",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z"
},
"message": "Mapping updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "default_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: default_id (int); body: JSON (fields not yet documented)"
},
"example": {
"description": "moved"
}
}
}
}
}
},
"/api/dashboarddefaults/display-role": {
"get": {
"tags": [
"core-dashboarddefaults"
],
"summary": "Resolve what a single 'display' PC should show, from its own IP.",
"description": "Resolve what a single 'display' PC should show, from its own IP.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboarddefaults/display-role\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"businessunit": null,
"businessunitid": null,
"fqdn": "<redacted:host>",
"ipaddress": "<redacted:host>",
"path": "/parts-kiosk",
"role": "3DPrintRoom"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "fqdn",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "ipaddress",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/dashboarddefaults/visitor-location": {
"get": {
"tags": [
"core-dashboarddefaults"
],
"summary": "Resolve the business unit for the calling display by its IP.",
"description": "Resolve the business unit for the calling display by its IP.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/dashboarddefaults/visitor-location\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"businessunit": "Materials",
"businessunitid": 1,
"fqdn": "<redacted:host>",
"ipaddress": "<redacted:host>"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "fqdn",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "ipaddress",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/docs": {
"get": {
"tags": [
"core-docs"
],
"summary": "Redoc page. url_for keeps the asset URLs correct under any mount.",
"description": "Redoc page. url_for keeps the asset URLs correct under any mount.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/docs/\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/docs/llms.txt": {
"get": {
"tags": [
"core-docs"
],
"summary": "Concise LLM-oriented API guide.",
"description": "Concise LLM-oriented API guide.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/docs/llms.txt\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/docs/openapi.json": {
"get": {
"tags": [
"core-docs"
],
"summary": "The generated OpenAPI 3.1 spec (machine + LLM readable).",
"description": "The generated OpenAPI 3.1 spec (machine + LLM readable).\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/docs/openapi.json\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "tag",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/docs/operations.txt": {
"get": {
"tags": [
"core-docs"
],
"summary": "Every operation, one line each: method, path, tag, auth, summary.",
"description": "Every operation, one line each: method, path, tag, auth, summary.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/docs/operations.txt\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/docs/redoc.standalone.js": {
"get": {
"tags": [
"core-docs"
],
"summary": "Vendored Redoc bundle (offline).",
"description": "Vendored Redoc bundle (offline).\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/docs/redoc.standalone.js\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/employees/lookup": {
"get": {
"tags": [
"core-employees"
],
"summary": "Look up multiple employees by SSO list.",
"description": "Look up multiple employees by SSO list.\n\n**Auth:** permission:employees.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/employees/lookup -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "sso",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": ""
}
}
]
}
},
"/api/employees/lookup/{sso}": {
"get": {
"tags": [
"core-employees"
],
"summary": "Look up a single employee by SSO.",
"description": "Look up a single employee by SSO.\n\n**Auth:** permission:employees.view\n\n**Params:** path: sso (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/employees/lookup/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"First_Name": "Test",
"Last_Name": "Person",
"Picture": null,
"Role": null,
"SSO": 210000001,
"Team": null,
"photofilename": "photo-210000001.png",
"photourl": "/api/employees/photo/photo-210000001.png"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "sso",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/employees/search": {
"get": {
"tags": [
"core-employees"
],
"summary": "Search employees by name.",
"description": "Search employees by name.\n\n**Auth:** permission:employees.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/employees/search -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"First_Name": "Dana",
"Last_Name": "Reyes",
"Picture": null,
"Role": null,
"SSO": 990005,
"Team": null,
"photofilename": null,
"photourl": null
},
{
"First_Name": "Sam",
"Last_Name": "Reyes",
"Picture": null,
"Role": null,
"SSO": 990006,
"Team": null,
"photofilename": null,
"photourl": null
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "limit",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 10
}
},
{
"name": "q",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": ""
}
}
]
}
},
"/api/locations": {
"get": {
"tags": [
"core-locations"
],
"summary": "List all locations.",
"description": "List all locations.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/locations -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "locationname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-locations"
],
"summary": "Create a new location.",
"description": "Create a new location.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/locations -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/locations/{location_id}": {
"delete": {
"tags": [
"core-locations"
],
"summary": "Delete (deactivate) a location.",
"description": "Delete (deactivate) a location.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: location_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/locations/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "location_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-locations"
],
"summary": "Get a single location.",
"description": "Get a single location.\n\n**Auth:** permission:assets.view\n\n**Params:** path: location_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/locations/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "location_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-locations"
],
"summary": "Update a location.",
"description": "Update a location.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: location_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/locations/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "location_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: location_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/locations/types": {
"get": {
"tags": [
"core-locations"
],
"summary": "List location types. ?active=false includes inactive ones.",
"description": "List location types. ?active=false includes inactive ones.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/locations/types -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
}
]
},
"post": {
"tags": [
"core-locations"
],
"summary": "UNDOCUMENTED: locations.create_location_type has no docstring.",
"description": "UNDOCUMENTED: locations.create_location_type has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/locations/types -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/locations/types/{type_id}": {
"delete": {
"tags": [
"core-locations"
],
"summary": "UNDOCUMENTED: locations.delete_location_type has no docstring.",
"description": "UNDOCUMENTED: locations.delete_location_type has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/locations/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-locations"
],
"summary": "UNDOCUMENTED: locations.update_location_type has no docstring.",
"description": "UNDOCUMENTED: locations.update_location_type has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/locations/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/maplevels": {
"get": {
"tags": [
"core-maplevels"
],
"summary": "Every active level, grouped by building, in display order.",
"description": "Every active level, grouped by building, in display order.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/maplevels -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"buildings": [
{
"buildingid": 1,
"buildingname": "Public Works",
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"levels": [
{
"assetcount": 0,
"blueprintdark": null,
"blueprintlight": "floorplan.svg",
"buildingid": 1,
"buildingname": "Public Works",
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"isdefault": false,
"levelid": 1,
"levelname": "Ground",
"mapheight": 2550,
"mapwidth": 3300,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"sortorder": 1
}
],
"modifieddate": "2026-01-01T00:00:00.000000Z",
"sortorder": 1
}
],
"defaultlevelid": 1,
"totalplaced": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
},
"post": {
"tags": [
"core-maplevels"
],
"summary": "UNDOCUMENTED: maplevels.create_level has no docstring.",
"description": "UNDOCUMENTED: maplevels.create_level has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/maplevels -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/maplevels/{levelid}": {
"delete": {
"tags": [
"core-maplevels"
],
"summary": "Deactivate a level, refusing while assets are still placed on it.",
"description": "Deactivate a level, refusing while assets are still placed on it.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: levelid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/maplevels/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "levelid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-maplevels"
],
"summary": "UNDOCUMENTED: maplevels.get_level has no docstring.",
"description": "UNDOCUMENTED: maplevels.get_level has no docstring.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** path: levelid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/maplevels/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"blueprintdark": null,
"blueprintlight": "floorplan.svg",
"buildingid": 1,
"buildingname": "Public Works",
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"isdefault": false,
"levelid": 1,
"levelname": "Ground",
"mapheight": 2550,
"mapwidth": 3300,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"sortorder": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "levelid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"patch": {
"tags": [
"core-maplevels"
],
"summary": "UNDOCUMENTED: maplevels.update_level has no docstring.",
"description": "UNDOCUMENTED: maplevels.update_level has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: levelid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/maplevels/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "levelid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": false,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: levelid (int); body: JSON (fields not yet documented)"
}
}
}
}
},
"put": {
"tags": [
"core-maplevels"
],
"summary": "UNDOCUMENTED: maplevels.update_level has no docstring.",
"description": "UNDOCUMENTED: maplevels.update_level has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: levelid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/maplevels/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "levelid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: levelid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/maplevels/{levelid}/blueprint": {
"post": {
"tags": [
"core-maplevels"
],
"summary": "Upload this level's blueprint for one theme.",
"description": "Upload this level's blueprint for one theme.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: levelid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/maplevels/1/blueprint -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "levelid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: levelid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/maplevels/{levelid}/blueprint/{filename}": {
"get": {
"tags": [
"core-maplevels"
],
"summary": "Serve a level's blueprint image. Public, for the same reason as above.",
"description": "Serve a level's blueprint image. Public, for the same reason as above.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** path: levelid (int), filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/maplevels/1/blueprint/example.png -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "levelid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/maplevels/buildings": {
"post": {
"tags": [
"core-maplevels"
],
"summary": "UNDOCUMENTED: maplevels.create_building has no docstring.",
"description": "UNDOCUMENTED: maplevels.create_building has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/maplevels/buildings -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/maplevels/buildings/{buildingid}": {
"patch": {
"tags": [
"core-maplevels"
],
"summary": "Rename or reorder a building. Levels move with it; nothing repositions.",
"description": "Rename or reorder a building. Levels move with it; nothing repositions.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: buildingid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/maplevels/buildings/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "buildingid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": false,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: buildingid (int); body: JSON (fields not yet documented)"
}
}
}
}
},
"put": {
"tags": [
"core-maplevels"
],
"summary": "Rename or reorder a building. Levels move with it; nothing repositions.",
"description": "Rename or reorder a building. Levels move with it; nothing repositions.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: buildingid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/maplevels/buildings/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "buildingid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: buildingid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/mappositions/positions": {
"post": {
"tags": [
"core-mappositions"
],
"summary": "Set positions for many assets at once.",
"description": "Set positions for many assets at once.\n\n**Auth:** permission:assets.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/mappositions/positions -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"snapshotid": 1,
"updated": 1
},
"message": "1 position(s) saved",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"positions": [
{
"assetid": 1,
"levelid": 2,
"mapx": 42,
"mapy": 43
}
]
}
}
}
}
}
},
"/api/mappositions/snapshots": {
"get": {
"tags": [
"core-mappositions"
],
"summary": "Snapshots, newest first. Metadata only - the positions are large.",
"description": "Snapshots, newest first. Metadata only - the positions are large.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/mappositions/snapshots -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/mappositions/snapshots/{snapshotid}/restore": {
"post": {
"tags": [
"core-mappositions"
],
"summary": "Put the positions in this snapshot back.",
"description": "Put the positions in this snapshot back.\n\n**Auth:** permission:assets.edit\n\n**Params:** path: snapshotid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/mappositions/snapshots/1/restore -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"restored": 3,
"skippedassetids": []
},
"message": "3 marker(s) restored",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "snapshotid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: snapshotid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/mappositions/transform": {
"post": {
"tags": [
"core-mappositions"
],
"summary": "Move every placed marker on a level by a transform read off landmarks.",
"description": "Move every placed marker on a level by a transform read off landmarks.\n\n**Auth:** permission:assets.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/mappositions/transform -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetcount": 3,
"dryrun": false,
"levelid": 1,
"moves": [
{
"assetid": 1,
"assetnumber": "M000",
"fromx": 100,
"fromy": 100,
"name": null,
"outofbounds": false,
"tox": 100,
"toy": 1550
},
{
"assetid": 2,
"assetnumber": "M001",
"fromx": 1500,
"fromy": 1200,
"name": null,
"outofbounds": true,
"tox": 1500,
"toy": 2650
},
{
"assetid": 3,
"assetnumber": "M002",
"fromx": 3200,
"fromy": 2500,
"name": null,
"outofbounds": true,
"tox": 3200,
"toy": 3950
}
],
"outofboundscount": 2,
"snapshotid": 1,
"tolevelid": 1,
"transform": {
"offsetx": 0.0,
"offsety": 1450.0,
"scalex": 1.0,
"scaley": 1.0
}
},
"message": "3 marker(s) moved; snapshot 1 can restore them",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"dryrun": false,
"landmarks": [
{
"fromx": 0,
"fromy": 0,
"tox": 0,
"toy": 1450
},
{
"fromx": 1000,
"fromy": 1000,
"tox": 1000,
"toy": 2450
}
],
"levelid": 1
}
}
}
}
}
},
"/api/mappositions/verify": {
"post": {
"tags": [
"core-mappositions"
],
"summary": "Mark markers as reviewed against the current drawing without moving them.",
"description": "Mark markers as reviewed against the current drawing without moving them.\n\n**Auth:** permission:assets.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/mappositions/verify -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"updated": 1
},
"message": "1 marker(s) unverified",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"assetids": [
1
],
"unverify": true
}
}
}
}
}
},
"/api/models": {
"get": {
"tags": [
"core-models"
],
"summary": "List all vendor catalog models.",
"description": "List all vendor catalog models.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/models -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "category",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "modelnumber",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "modeltype",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "vendor",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-models"
],
"summary": "Create a new model.",
"description": "Create a new model.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/models -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/models/{model_id}": {
"delete": {
"tags": [
"core-models"
],
"summary": "Delete (deactivate) a model.",
"description": "Delete (deactivate) a model.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: model_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/models/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "model_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-models"
],
"summary": "Get a single model.",
"description": "Get a single model.\n\n**Auth:** permission:assets.view\n\n**Params:** path: model_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/models/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "model_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-models"
],
"summary": "Update a model.",
"description": "Update a model.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: model_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/models/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "model_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: model_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/models/{model_id}/image": {
"delete": {
"tags": [
"core-models"
],
"summary": "Clear a model image and delete the uploaded file if we own it.",
"description": "Clear a model image and delete the uploaded file if we own it.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: model_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/models/1/image -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"documentationurl": null,
"imageurl": null,
"isactive": true,
"modelnumber": "TESTMODEL-1",
"modelnumberid": 1,
"modeltypeid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"vendorid": null
},
"message": "Model image removed",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "model_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"core-models"
],
"summary": "Upload (or replace) the photo for a model.",
"description": "Upload (or replace) the photo for a model.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: model_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/models/1/image -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"documentationurl": null,
"imageurl": "/api/models/image/model-1.jpg",
"isactive": true,
"modelnumber": "TESTMODEL-1",
"modelnumberid": 1,
"modeltypeid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"vendorid": null
},
"message": "Model image uploaded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "model_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: model_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/models/image/{filename}": {
"get": {
"tags": [
"core-models"
],
"summary": "Serve an uploaded model image (public - asset detail pages read it).",
"description": "Serve an uploaded model image (public - asset detail pages read it).\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** path: filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/models/image/example.png\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/modeltypes": {
"get": {
"tags": [
"core-modeltypes"
],
"summary": "List all model types with optional filtering.",
"description": "List all model types with optional filtering.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/modeltypes -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "category",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "modeltype",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-modeltypes"
],
"summary": "Create a new model type.",
"description": "Create a new model type.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/modeltypes -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/modeltypes/{type_id}": {
"delete": {
"tags": [
"core-modeltypes"
],
"summary": "Delete (deactivate) a model type.",
"description": "Delete (deactivate) a model type.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/modeltypes/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-modeltypes"
],
"summary": "Get a single model type.",
"description": "Get a single model type.\n\n**Auth:** permission:assets.view\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/modeltypes/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-modeltypes"
],
"summary": "Update a model type.",
"description": "Update a model type.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/modeltypes/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/operatingsystems": {
"get": {
"tags": [
"core-operatingsystems"
],
"summary": "List all operating systems.",
"description": "List all operating systems.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/operatingsystems -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "osname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "osversion",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-operatingsystems"
],
"summary": "Create a new operating system.",
"description": "Create a new operating system.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/operatingsystems -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/operatingsystems/{os_id}": {
"delete": {
"tags": [
"core-operatingsystems"
],
"summary": "Delete (deactivate) an operating system.",
"description": "Delete (deactivate) an operating system.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: os_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/operatingsystems/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "os_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-operatingsystems"
],
"summary": "Get a single operating system.",
"description": "Get a single operating system.\n\n**Auth:** permission:assets.view\n\n**Params:** path: os_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/operatingsystems/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "os_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-operatingsystems"
],
"summary": "Update an operating system.",
"description": "Update an operating system.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: os_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/operatingsystems/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "os_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: os_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/plugins": {
"get": {
"tags": [
"core-plugins"
],
"summary": "List all discovered plugins (enabled or not) with their metadata and the framework contract version.",
"description": "List all discovered plugins (enabled or not) with their metadata and the framework contract version.\n\n**Auth:** permission:settings.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/plugins -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/plugins/{name}": {
"put": {
"tags": [
"core-plugins"
],
"summary": "Enable or disable a plugin. Takes effect on the next app restart for route/navigation changes.",
"description": "Enable or disable a plugin. Takes effect on the next app restart for route/navigation changes.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: name (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/plugins/x -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "name",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: name (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/plugins/enabled": {
"get": {
"tags": [
"core-plugins"
],
"summary": "Return just the names of enabled plugins as a flat array.",
"description": "Return just the names of enabled plugins as a flat array.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/plugins/enabled -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
"backups",
"computers",
"employees",
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/plugins/settings-routes": {
"get": {
"tags": [
"core-plugins"
],
"summary": "Return settings routes contributed by all enabled plugins.",
"description": "Return settings routes contributed by all enabled plugins.\n\n**Auth:** permission:settings.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/plugins/settings-routes -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"routes": [
{
"component": "drawn.vue",
"hub": "model-catalog",
"name": "drawn-route",
"path": "drawn",
"tab": "Drawn"
},
{
"component": ".plugins-staged/computers/views/OperatingSystemsList.vue",
"hub": "model-catalog",
"name": "model-catalog-os",
"path": "operatingsystems",
"tab": "Operating Systems"
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/pluginui/asset-panels": {
"get": {
"tags": [
"core-pluginui"
],
"summary": "Return the asset-detail panels matching one asset's type (get_asset_panels).",
"description": "Return the asset-detail panels matching one asset's type (get_asset_panels).\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/pluginui/asset-panels -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assettypes": [
"computer"
],
"empty": "No agent report yet.",
"endpoint": "/api/endpoints/asset/{assetid}/status",
"group": "details",
"id": "endpoints-status",
"plugin": "endpoints",
"position": 10,
"render": "keyvalue",
"title": "Endpoint status"
},
{
"assettypes": [
"computer"
],
"collapsible": true,
"commandendpoint": "/api/endpoints/{assetid}/commands",
"empty": "No monitored services reported.",
"endpoint": "/api/endpoints/asset/{assetid}/services",
"facets": {
"key": "statelabel",
"order": [
"Running",
"Stopped",
"Paused",
"<trimmed for the example: 1 more>"
]
},
"filter": {
"equals": "service",
"key": "kind"
},
"group": "serviceprocess",
"id": "endpoints-tracked-services",
"map": {
"action": "action",
"badge": {
"color": "statecolor",
"label": "statelabel"
},
"title": "name"
},
"permission": "endpoints.command",
"plugin": "endpoints",
"position": 12,
"render": "list",
"status": {
"key": "statecolor",
"levels": {
"green": "ok",
"red": "critical",
"yellow": "warning"
}
},
"title": "Tracked Services"
},
{
"assettypes": [
"computer"
],
"collapsible": true,
"commandendpoint": "/api/endpoints/{assetid}/commands",
"empty": "No monitored processes reported.",
"endpoint": "/api/endpoints/asset/{assetid}/services",
"facets": {
"key": "statelabel",
"order": [
"Running",
"Stopped",
"Paused",
"<trimmed for the example: 1 more>"
]
},
"filter": {
"equals": "process",
"key": "kind"
},
"group": "serviceprocess",
"id": "endpoints-tracked-processes",
"map": {
"action": "action",
"badge": {
"color": "statecolor",
"label": "statelabel"
},
"title": "name"
},
"permission": "endpoints.command",
"plugin": "endpoints",
"position": 13,
"render": "list",
"status": {
"key": "statecolor",
"levels": {
"green": "ok",
"red": "critical",
"yellow": "warning"
}
},
"title": "Tracked Processes"
},
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "assetid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/pluginui/asset-presentation": {
"get": {
"tags": [
"core-pluginui"
],
"summary": "Merge enabled plugins' asset-type presentation entries (hook).",
"description": "Merge enabled plugins' asset-type presentation entries (hook).\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/pluginui/asset-presentation -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assettype": "stubtype",
"plugin": "backups",
"route": "/stubtype/by-asset/{assetid}"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/pluginui/asset-type-descriptors": {
"get": {
"tags": [
"core-pluginui"
],
"summary": "Merge enabled plugins' asset-type subtype descriptors.",
"description": "Merge enabled plugins' asset-type subtype descriptors.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/pluginui/asset-type-descriptors -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assettype": "computer",
"edit_permission": "computers.manage",
"optional_tabs": [],
"plugin": "computers",
"subtype_color_field": "color",
"subtype_description_field": "description",
"subtype_endpoint": "/computers/types",
"subtype_id_field": "computertypeid",
"subtype_label_field": "computertype"
},
{
"assettype": "machine",
"edit_permission": "machines.manage",
"optional_tabs": [],
"plugin": "machines",
"subtype_color_field": "color",
"subtype_description_field": "description",
"subtype_endpoint": "/machines/types",
"subtype_id_field": "machinetypeid",
"subtype_label_field": "machinetype"
},
{
"assettype": "network_device",
"edit_permission": "network.manage",
"optional_tabs": [],
"plugin": "network",
"subtype_color_field": "color",
"subtype_description_field": "description",
"subtype_endpoint": "/network/types",
"subtype_id_field": "networkdevicetypeid",
"subtype_label_field": "networkdevicetype"
},
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/pluginui/core-type-descriptors": {
"get": {
"tags": [
"core-pluginui"
],
"summary": "Return type descriptors for core-owned non-asset types.",
"description": "Return type descriptors for core-owned non-asset types.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/pluginui/core-type-descriptors -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"category": "location",
"edit_permission": "admin",
"group": "other",
"optional_tabs": [],
"subtype_color_field": "color",
"subtype_description_field": "description",
"subtype_endpoint": "/locations/types",
"subtype_id_field": "locationtypeid",
"subtype_label_field": "locationtype",
"type_name": "Location Type",
"type_name_plural": "Location Types"
},
{
"category": "notification",
"custom_component": "NotificationTypesTab",
"edit_permission": "admin",
"group": "other",
"optional_tabs": [],
"subtype_color_field": "typecolor",
"subtype_description_field": "typedescription",
"subtype_endpoint": "/notifications/types",
"subtype_id_field": "notificationtypeid",
"subtype_label_field": "typename",
"type_name": "Notification Type",
"type_name_plural": "Notification Types"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/pluginui/map-overlays": {
"get": {
"tags": [
"core-pluginui"
],
"summary": "Merge enabled plugins' map overlay declarations (get_map_overlays hook).",
"description": "Merge enabled plugins' map overlay declarations (get_map_overlays hook).\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/pluginui/map-overlays -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"endpoint": "/api/whatever",
"id": "due-soon",
"legend": true,
"plugin": "backups",
"title": "Due soon"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/pluginui/settings-cards": {
"get": {
"tags": [
"core-pluginui"
],
"summary": "Merge enabled plugins' settings-catalog cards (get_settings_cards hook).",
"description": "Merge enabled plugins' settings-catalog cards (get_settings_cards hook).\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/pluginui/settings-cards -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"description": "Collection interval, share root for part-marker snapshots, staleness threshold and revision retention",
"group": "Machines",
"icon": "package",
"plugin": "backups",
"position": 21,
"title": "Backups",
"to": "/settings/backups"
},
{
"description": "Download the collector script stamped with this site's URL and ranges",
"group": "Computers",
"icon": "download",
"plugin": "computers",
"position": 26,
"title": "Asset reporter",
"to": "/settings/collector"
},
{
"description": "The shared agent key PCs use until they enroll, the site agent installer builder, and what the agent reports.",
"group": "Endpoints",
"icon": "key",
"plugin": "endpoints",
"position": 27,
"title": "Endpoints",
"to": "/settings/endpoints/agentkey"
},
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/reports": {
"get": {
"tags": [
"core-reports"
],
"summary": "List all available reports.",
"description": "List all available reports.\n\n**Auth:** permission:reports.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/reports -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"reports": [
{
"category": "inventory",
"description": "Machine count grouped by machine type",
"endpoint": "/api/reports/machines-by-type",
"id": "machines-by-type",
"name": "Machines by Type"
},
{
"category": "inventory",
"description": "Asset count grouped by status",
"endpoint": "/api/reports/assets-by-status",
"id": "assets-by-status",
"name": "Assets by Status"
},
{
"category": "usage",
"description": "Most clicked knowledge base articles",
"endpoint": "/api/reports/kb-popularity",
"id": "kb-popularity",
"name": "KB Popularity"
},
"<trimmed for the example: 1 more>"
],
"total": 13
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/reports/asset-inventory": {
"get": {
"tags": [
"core-reports"
],
"summary": "Report: Complete asset inventory summary.",
"description": "Report: Complete asset inventory summary.\n\n**Auth:** permission:reports.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/reports/asset-inventory -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"data": {
"bylocation": [],
"bystatus": [],
"bytype": []
},
"generated": "2026-01-01T00:00:00.000000",
"report": "asset_inventory",
"total": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/reports/assets-by-status": {
"get": {
"tags": [
"core-reports"
],
"summary": "Report: Asset count grouped by status.",
"description": "Report: Asset count grouped by status.\n\n**Auth:** permission:reports.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/reports/assets-by-status -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"data": [],
"generated": "2026-01-01T00:00:00.000000",
"report": "assets_by_status",
"total": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "assettypeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/reports/email": {
"post": {
"tags": [
"core-reports"
],
"summary": "Email a report's data as an HTML table (on-demand delivery).",
"description": "Email a report's data as an HTML table (on-demand delivery).\n\n**Auth:** permission:reports.export\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/reports/email -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"reason": "notconfigured",
"sent": false
},
"message": "Email is not configured (SMTP disabled or host unset).",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"columns": [
{
"key": "vendor",
"label": "Vendor"
}
],
"rows": [
{
"vendor": "Dell"
}
],
"subject": "Warranty Report",
"to": "<redacted:email>"
}
}
}
}
}
},
"/api/reports/kb-popularity": {
"get": {
"tags": [
"core-reports"
],
"summary": "Report: Most clicked knowledge base articles.",
"description": "Report: Most clicked knowledge base articles.\n\n**Auth:** permission:reports.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/reports/kb-popularity -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"data": [],
"generated": "2026-01-01T00:00:00.000000",
"report": "kb_popularity",
"total": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "limit",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 20
}
}
]
}
},
"/api/reports/machines-by-type": {
"get": {
"tags": [
"core-reports"
],
"summary": "Report: Machine count grouped by machine type.",
"description": "Report: Machine count grouped by machine type.\n\n**Auth:** permission:reports.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/reports/machines-by-type -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"data": [],
"generated": "2026-01-01T00:00:00.000000",
"report": "machines_by_type",
"total": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/reports/pc-relationships": {
"get": {
"tags": [
"core-reports"
],
"summary": "Report: PCs with relationships to shop floor machines.",
"description": "Report: PCs with relationships to shop floor machines.\n\n**Auth:** permission:reports.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/reports/pc-relationships -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"data": [
{
"hostname": "<redacted:host>",
"ip": "<redacted:host>",
"machine_number": "4242",
"model": "",
"vendor": ""
}
],
"generated": "2026-01-01T00:00:00.000000",
"report": "pc_relationships",
"total": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/reports/software-compliance": {
"get": {
"tags": [
"core-reports"
],
"summary": "Report: Required applications vs installed (per PC).",
"description": "Report: Required applications vs installed (per PC).\n\n**Auth:** permission:reports.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/reports/software-compliance -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"data": [],
"generated": "2026-01-01T00:00:00.000000",
"message": "No required applications defined",
"report": "software_compliance"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "appid",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/scripts": {
"get": {
"tags": [
"core-scripts"
],
"summary": "List scripts (active by default).",
"description": "List scripts (active by default).\n\n**Auth:** permission:endpoints.runscript\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/scripts -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-scripts"
],
"summary": "Create a script catalog entry (body uploaded separately).",
"description": "Create a script catalog entry (body uploaded separately).\n\n**Auth:** permission:endpoints.runscript\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/scripts -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"captureoutput": false,
"createddate": "2026-01-01T00:00:00.000000Z",
"errormode": "default",
"filename": null,
"hasbody": false,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"runcontext": "system",
"scriptdescription": null,
"scriptid": 1,
"scriptname": "autologon",
"sha256": null,
"workingdirectory": "C:\\Program Files\\Sysinternals"
},
"message": "Script created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"scriptname": "autologon",
"workingdirectory": "C:\\Program Files\\Sysinternals"
}
}
}
}
}
},
"/api/scripts/{script_id}": {
"delete": {
"tags": [
"core-scripts"
],
"summary": "UNDOCUMENTED: scripts.delete_script has no docstring.",
"description": "UNDOCUMENTED: scripts.delete_script has no docstring.\n\n**Auth:** permission:endpoints.runscript\n\n**Params:** path: script_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/scripts/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "script_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-scripts"
],
"summary": "UNDOCUMENTED: scripts.get_script has no docstring.",
"description": "UNDOCUMENTED: scripts.get_script has no docstring.\n\n**Auth:** permission:endpoints.runscript\n\n**Params:** path: script_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/scripts/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "script_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-scripts"
],
"summary": "UNDOCUMENTED: scripts.update_script has no docstring.",
"description": "UNDOCUMENTED: scripts.update_script has no docstring.\n\n**Auth:** permission:endpoints.runscript\n\n**Params:** path: script_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/scripts/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"captureoutput": true,
"createddate": "2026-01-01T00:00:00.000000Z",
"errormode": "default",
"filename": null,
"hasbody": false,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"runcontext": "system",
"scriptdescription": "now documented",
"scriptid": 1,
"scriptname": "keep-my-flag",
"sha256": null,
"workingdirectory": null
},
"message": "Script updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "script_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: script_id (int); body: JSON (fields not yet documented)"
},
"example": {
"scriptdescription": "now documented"
}
}
}
}
}
},
"/api/scripts/{script_id}/body": {
"post": {
"tags": [
"core-scripts"
],
"summary": "Upload (or replace) the .ps1 body for a script.",
"description": "Upload (or replace) the .ps1 body for a script.\n\n**Auth:** permission:endpoints.runscript\n\n**Params:** path: script_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/scripts/1/body -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"bytes": 23,
"captureoutput": false,
"createddate": "2026-01-01T00:00:00.000000Z",
"errormode": "default",
"filename": "script-1.ps1",
"hasbody": true,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"runcontext": "system",
"scriptdescription": null,
"scriptid": 1,
"scriptname": "digest-check",
"sha256": "<redacted:digest>",
"uploadedfilename": "digest-check.ps1",
"workingdirectory": null
},
"message": "Script body uploaded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "script_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: script_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/scripts/body/{filename}": {
"get": {
"tags": [
"core-scripts"
],
"summary": "Operator-facing script body download (JWT/RBAC).",
"description": "Operator-facing script body download (JWT/RBAC).\n\n**Auth:** permission:endpoints.runscript\n\n**Params:** path: filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/scripts/body/example.png -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/search": {
"get": {
"tags": [
"core-search"
],
"summary": "Global search across multiple entity types.",
"description": "Global search across multiple entity types.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/search -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"counts": {
"knowledgebase": 2
},
"degraded": [
"Employee"
],
"query": "zzkeyword",
"results": [
{
"id": 1,
"linkurl": "u",
"relevance": 25.0,
"subtitle": "Livesearchapp",
"title": "Zzrunbook for the live one",
"type": "knowledgebase",
"url": "/knowledgebase/1"
},
{
"id": 3,
"linkurl": "u",
"relevance": 25.0,
"subtitle": null,
"title": "Zzrunbook with no topic",
"type": "knowledgebase",
"url": "/knowledgebase/3"
}
],
"total": 2,
"total_all": 2
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "q",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": ""
}
}
]
}
},
"/api/search/suggest": {
"get": {
"tags": [
"core-search"
],
"summary": "A better spelling for a query that found nothing, or null.",
"description": "A better spelling for a query that found nothing, or null.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/search/suggest -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"query": "keyecne",
"suggestion": "keyence"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "q",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": ""
}
}
]
}
},
"/api/settings": {
"get": {
"tags": [
"core-settings"
],
"summary": "List all settings, optionally filtered by category.",
"description": "List all settings, optionally filtered by category.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"category": "auth",
"createddate": "2026-01-01T00:00:00.000000Z",
"description": "SAML Assertion Consumer Service URL",
"key": "saml_acs_url",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"settingid": 111,
"value": "",
"valuetype": "string"
},
{
"category": "auth",
"createddate": "2026-01-01T00:00:00.000000Z",
"description": "SAML group name that grants admin role",
"key": "saml_admin_group",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"settingid": 114,
"value": "",
"valuetype": "string"
},
{
"category": "auth",
"createddate": "2026-01-01T00:00:00.000000Z",
"description": "Allow local username/password login when SAML is enabled",
"key": "saml_allow_local_login",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"settingid": 112,
"value": true,
"valuetype": "boolean"
},
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "category",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-settings"
],
"summary": "Create a new setting (admin only).",
"description": "Create a new setting (admin only).\n\n**Auth:** permission:settings.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/settings/{key}": {
"get": {
"tags": [
"core-settings"
],
"summary": "Get a single setting by key.",
"description": "Get a single setting by key.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** path: key (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"category": "plugin.endpoints",
"createddate": "2026-01-01T00:00:00.000000Z",
"description": "Accept a one-line install bootstrap token in the ?t= query string as well as the X-Endpoint-Bootstrap-Token header. On (the default) keeps the pasted install commands and the Download .ps1 link workin...",
"key": "plugin.endpoints.bootstrapquerytoken",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"settingid": 1,
"value": false,
"valuetype": "boolean"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "key",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
},
"put": {
"tags": [
"core-settings"
],
"summary": "Update a setting value.",
"description": "Update a setting value.\n\n**Auth:** permission:settings.edit\n\n**Params:** path: key (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/settings/x -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"category": "plugin.endpoints",
"createddate": "2026-01-01T00:00:00.000000Z",
"description": "Accept a one-line install bootstrap token in the ?t= query string as well as the X-Endpoint-Bootstrap-Token header. On (the default) keeps the pasted install commands and the Download .ps1 link workin...",
"key": "plugin.endpoints.bootstrapquerytoken",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"settingid": 1,
"value": false,
"valuetype": "boolean"
},
"message": "Setting updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "key",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: key (string); body: JSON (fields not yet documented)"
},
"example": {
"value": "<redacted:address>"
}
}
}
}
}
},
"/api/settings/asset-import/import": {
"post": {
"tags": [
"core-settings"
],
"summary": "Validate uploaded CSVs and, when commit=true, load them.",
"description": "Validate uploaded CSVs and, when commit=true, load them.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/asset-import/import -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/settings/asset-import/script": {
"get": {
"tags": [
"core-settings"
],
"summary": "Download Collect-ShopDB.ps1 with this site's CSV path embedded.",
"description": "Download Collect-ShopDB.ps1 with this site's CSV path embedded.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings/asset-import/script -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/settings/asset-import/templates": {
"get": {
"tags": [
"core-settings"
],
"summary": "List the importable CSV tables in the order they must be uploaded.",
"description": "List the importable CSV tables in the order they must be uploaded.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings/asset-import/templates -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"tables": [
{
"filename": "assetstatuses.csv",
"table": "assetstatuses"
},
{
"filename": "assettypes.csv",
"table": "assettypes"
},
{
"filename": "locationtypes.csv",
"table": "locationtypes"
},
"<trimmed for the example: 1 more>"
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/settings/asset-import/templates/{tablename}": {
"get": {
"tags": [
"core-settings"
],
"summary": "Download a generated CSV template for a single importable table.",
"description": "Download a generated CSV template for a single importable table.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: tablename (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings/asset-import/templates/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "tablename",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/settings/asset-import/winc/batches": {
"get": {
"tags": [
"core-settings"
],
"summary": "List applied/undone WINC import batches, newest first (for the undo UI).",
"description": "List applied/undone WINC import batches, newest first (for the undo UI).\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings/asset-import/winc/batches -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"batches": [
{
"batchid": "<redacted:token>",
"createdat": "2026-01-01 00:00:00.000000",
"createdby": "<redacted:person>",
"kind": "winc-machine-adoption",
"rowcount": 1,
"status": "undone",
"undoneat": "2026-01-01 00:00:00.000000"
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/settings/asset-import/winc/commit": {
"post": {
"tags": [
"core-settings"
],
"summary": "Apply a WINC plan reversibly. Requires acknowledgment for needs-create.",
"description": "Apply a WINC plan reversibly. Requires acknowledgment for needs-create.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/asset-import/winc/commit -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"batchid": "<redacted:token>",
"blocking": false,
"committed": true,
"kind": "winc-machine-adoption",
"needscreate": {
"businessunit": {
"Large Parts": 1
}
},
"planhash": "<redacted:secret>",
"rowcount": 1,
"summary": {
"ambiguous_match": 0,
"businessunit_blank": 0,
"businessunit_needs-create": 1,
"businessunit_resolved": 0,
"businessunit_unresolved": 0,
"export_rows": 2,
"in_scope": 1,
"location_blank": 0,
"location_needs-create": 0,
"location_resolved": 1,
"location_unresolved": 0,
"non_workstation_rows": 1,
"skipped_no_existing_machine": 0
},
"uncreatable": {},
"unresolved": {}
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/settings/asset-import/winc/preview": {
"post": {
"tags": [
"core-settings"
],
"summary": "Read-only WINC analysis: report what a commit would do. Writes nothing.",
"description": "Read-only WINC analysis: report what a commit would do. Writes nothing.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/asset-import/winc/preview -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"blocking": true,
"committed": false,
"kind": "winc-machine-adoption",
"needscreate": {
"businessunit": {
"Large Parts": 1
},
"location": {
"T6": 1
}
},
"planhash": "<redacted:secret>",
"rowcount": 1,
"summary": {
"ambiguous_match": 0,
"businessunit_blank": 0,
"businessunit_needs-create": 1,
"businessunit_resolved": 0,
"businessunit_unresolved": 0,
"export_rows": 1,
"in_scope": 1,
"location_blank": 0,
"location_needs-create": 1,
"location_resolved": 0,
"location_unresolved": 0,
"non_workstation_rows": 0,
"skipped_no_existing_machine": 0
},
"uncreatable": {
"location": {
"T6": 1
}
},
"unresolved": {}
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/settings/asset-import/winc/undo": {
"post": {
"tags": [
"core-settings"
],
"summary": "Reverse an applied WINC import batch by id. Conservative and reversible.",
"description": "Reverse an applied WINC import batch by id. Conservative and reversible.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/asset-import/winc/undo -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"batchid": "<redacted:token>",
"conflicts": [
{
"column": null,
"operation": "insert",
"reason": "still referenced by dashboarddefaults.businessunitid",
"table": "businessunits",
"targetid": 1
}
],
"reverted": 3
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"batchid": "<redacted:token>"
}
}
}
}
}
},
"/api/settings/branding-logo": {
"post": {
"tags": [
"core-settings"
],
"summary": "Upload a branding logo image and point the matching setting at it.",
"description": "Upload a branding logo image and point the matching setting at it.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/branding-logo -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"key": "site_favicon",
"value": "/api/settings/branding/logo-favicon.ico"
},
"message": "Logo uploaded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/settings/branding/{filename}": {
"get": {
"tags": [
"core-settings"
],
"summary": "Serve an uploaded branding logo (public - kiosks/print pages read it).",
"description": "Serve an uploaded branding logo (public - kiosks/print pages read it).\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** path: filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings/branding/example.png\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/settings/map-blueprint": {
"post": {
"tags": [
"core-settings"
],
"summary": "Upload a floor-map blueprint image and point the setting at it.",
"description": "Upload a floor-map blueprint image and point the setting at it.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/map-blueprint -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/settings/map-blueprint/{filename}": {
"get": {
"tags": [
"core-settings"
],
"summary": "Serve an uploaded blueprint image (public - kiosks read it).",
"description": "Serve an uploaded blueprint image (public - kiosks read it).\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** path: filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/settings/map-blueprint/example.png\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/settings/seed": {
"post": {
"tags": [
"core-settings"
],
"summary": "Seed default settings if they don't exist.",
"description": "Seed default settings if they don't exist.\n\n**Auth:** permission:settings.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/seed -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"created": 112
},
"message": "112 default settings created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {}
}
}
}
}
},
"/api/settings/test-email": {
"post": {
"tags": [
"core-settings"
],
"summary": "Send a test email to verify SMTP configuration.",
"description": "Send a test email to verify SMTP configuration.\n\n**Auth:** permission:settings.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/settings/test-email -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"error": "[Errno -2] Name or service not known",
"sent": false
},
"message": "Test email failed: [Errno -2] Name or service not known",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"to": "<redacted:email>"
}
}
}
}
}
},
"/api/setup/checklist": {
"get": {
"tags": [
"core-setup"
],
"summary": "What is configured and what is not, with a link to each fix.",
"description": "What is configured and what is not, with a link to each fix.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/setup/checklist -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/setup/complete": {
"post": {
"tags": [
"core-setup"
],
"summary": "Flag the first-run setup as finished.",
"description": "Flag the first-run setup as finished.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/setup/complete -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/setup/create-admin": {
"post": {
"tags": [
"core-setup"
],
"summary": "Create the first admin. Only works while there are zero users, setup has not been marked complete, and the caller...",
"description": "Create the first admin. Only works while there are zero users, setup has not been marked complete, and the caller proves operator control (setup token or a loopback request).\n\n**Auth:** none (first run only: refused once an admin exists)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/setup/create-admin -H 'Content-Type: application/json' -d '{}'\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/setup/health": {
"get": {
"tags": [
"core-setup"
],
"summary": "Post-setup reality check, including whether a restart is outstanding.",
"description": "Post-setup reality check, including whether a restart is outstanding.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/setup/health -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/setup/needs-admin": {
"get": {
"tags": [
"core-setup"
],
"summary": "True when no users exist yet - the app's very first run. Public so the login screen can offer to create the first admin.",
"description": "True when no users exist yet - the app's very first run. Public so the login screen can offer to create the first admin.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/setup/needs-admin\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"needsadmin": false
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
}
}
},
"/api/setup/seed-reference": {
"post": {
"tags": [
"core-setup"
],
"summary": "Seed core reference data + permissions + default settings. Idempotent - reuses the same routines as the `flask seed...",
"description": "Seed core reference data + permissions + default settings. Idempotent - reuses the same routines as the `flask seed ...` CLI commands.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/setup/seed-reference -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/setup/seed-starter": {
"post": {
"tags": [
"core-setup"
],
"summary": "Add common vendors that are not already present. Idempotent.",
"description": "Add common vendors that are not already present. Idempotent.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/setup/seed-starter -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/shopdbbackups": {
"get": {
"tags": [
"core-shopdbbackups"
],
"summary": "List every retained backup set, newest first, with a compatibility flag.",
"description": "List every retained backup set, newest first, with a compatibility flag.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/shopdbbackups -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"count": 0,
"lastgoodat": null,
"requestid": "00000000",
"retention": {
"keepdaily": 5,
"keepmonthly": 6,
"keepweekly": 4
},
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"core-shopdbbackups"
],
"summary": "Kick off an on-demand backup run.",
"description": "Kick off an on-demand backup run.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/shopdbbackups -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/shopdbbackups/{snapshotid}": {
"get": {
"tags": [
"core-shopdbbackups"
],
"summary": "Return one set's full manifest plus a resolved compatibility verdict.",
"description": "Return one set's full manifest plus a resolved compatibility verdict.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: snapshotid (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/shopdbbackups/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "snapshotid",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/shopdbbackups/{snapshotid}/restore": {
"post": {
"tags": [
"core-shopdbbackups"
],
"summary": "Queue a restore of a set, gated on schema compatibility.",
"description": "Queue a restore of a set, gated on schema compatibility.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: snapshotid (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/shopdbbackups/x/restore -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "snapshotid",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: snapshotid (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/shopdbbackups/finalize-restore": {
"post": {
"tags": [
"core-shopdbbackups"
],
"summary": "Run the post-restore schema upgrade in the app context.",
"description": "Run the post-restore schema upgrade in the app context.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/shopdbbackups/finalize-restore -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"queued": true,
"snapshotid": "wj-2026-09-06T120000Z"
},
"message": "Schema upgrade queued.",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/shopdbbackups/history": {
"get": {
"tags": [
"core-shopdbbackups"
],
"summary": "Return the recorded history of backup and restore runs, newest first.",
"description": "Return the recorded history of backup and restore runs, newest first.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/shopdbbackups/history -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"backups": [],
"restores": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/shopdbbackups/settings": {
"get": {
"tags": [
"core-shopdbbackups"
],
"summary": "Return destination + retention config for the settings pane.",
"description": "Return destination + retention config for the settings pane.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/shopdbbackups/settings -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"backupsroot": "/backups",
"destinationkind": "local",
"destinationkinds": [
"local",
"smb",
"aws"
],
"fields": {},
"isarmed": true,
"retention": {
"keepdaily": 5,
"keepmonthly": 6,
"keepweekly": 4
}
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"put": {
"tags": [
"core-shopdbbackups"
],
"summary": "Persist the backup destination kind and its credential/config fields.",
"description": "Persist the backup destination kind and its credential/config fields.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/shopdbbackups/settings -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"backupsroot": "/backups",
"destinationkind": "local",
"destinationkinds": [
"local",
"smb",
"aws"
],
"fields": {},
"isarmed": true,
"retention": {
"keepdaily": 5,
"keepmonthly": 6,
"keepweekly": 4
}
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {}
}
}
}
}
},
"/api/shopdbbackups/status": {
"get": {
"tags": [
"core-shopdbbackups"
],
"summary": "Return the live status of the most recent backup and restore runs.",
"description": "Return the live status of the most recent backup and restore runs.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/shopdbbackups/status -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"backup": null,
"restore": null
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/supportteams": {
"get": {
"tags": [
"core-supportteams"
],
"summary": "List support teams (with contacts). ?active and ?teamname filters.",
"description": "List support teams (with contacts). ?active and ?teamname filters.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/supportteams -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": false,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"supportteamid": 1,
"teamname": "Retired",
"teamurl": null,
"webhookurl": null
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "teamname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-supportteams"
],
"summary": "Create a new support team.",
"description": "Create a new support team.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/supportteams -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"supportteamid": 1,
"teamname": "Controls",
"teamurl": "https://servicenow.example/group/controls",
"webhookurl": null
},
"message": "Support team created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"createddate": "2026-01-01 00:00:00",
"modifieddate": "2026-01-01T00:00:00",
"teamname": "Legacy"
}
}
}
}
}
},
"/api/supportteams/{team_id}": {
"delete": {
"tags": [
"core-supportteams"
],
"summary": "Delete a support team; 409 while any application references it.",
"description": "Delete a support team; 409 while any application references it.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: team_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/supportteams/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "Support team deleted",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "team_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-supportteams"
],
"summary": "Get a single support team with its contacts.",
"description": "Get a single support team with its contacts.\n\n**Auth:** permission:assets.view\n\n**Params:** path: team_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/supportteams/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"contacts": [
{
"contactid": 2,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "First",
"sortorder": 1,
"sso": "111",
"supportteamid": 1
},
{
"contactid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "Second",
"sortorder": 2,
"sso": "222",
"supportteamid": 1
}
],
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"supportteamid": 1,
"teamname": "Controls",
"teamurl": null,
"webhookurl": null
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "team_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-supportteams"
],
"summary": "Update a support team.",
"description": "Update a support team.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: team_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/supportteams/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"contacts": [],
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"supportteamid": 1,
"teamname": "Controls Renamed",
"teamurl": "https://x.example",
"webhookurl": null
},
"message": "Support team updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "team_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: team_id (int); body: JSON (fields not yet documented)"
},
"example": {
"teamname": "Controls Renamed",
"teamurl": "https://x.example"
}
}
}
}
}
},
"/api/supportteams/{team_id}/contacts": {
"post": {
"tags": [
"core-supportteams"
],
"summary": "Add a contact to a support team.",
"description": "Add a contact to a support team.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: team_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/supportteams/1/contacts -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"contactid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "Second",
"sortorder": 2,
"sso": "222",
"supportteamid": 1
},
"message": "Contact created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "team_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: team_id (int); body: JSON (fields not yet documented)"
},
"example": {
"createddate": "2026-01-01 00:00:00",
"modifieddate": "2026-01-01T00:00:00",
"name": "LegacyOwner"
}
}
}
}
}
},
"/api/supportteams/{team_id}/contacts/{contact_id}": {
"delete": {
"tags": [
"core-supportteams"
],
"summary": "Delete a support-team contact.",
"description": "Delete a support-team contact.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: team_id (int), contact_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/supportteams/1/contacts/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "Contact deleted",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "team_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "contact_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-supportteams"
],
"summary": "Update a support-team contact.",
"description": "Update a support-team contact.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: team_id (int), contact_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/supportteams/1/contacts/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"contactid": 2,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "First Updated",
"sortorder": 1,
"sso": "111",
"supportteamid": 1
},
"message": "Contact updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "team_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "contact_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: team_id (int), contact_id (int); body: JSON (fields not yet documented)"
},
"example": {
"name": "First Updated"
}
}
}
}
}
},
"/api/users": {
"get": {
"tags": [
"core-users"
],
"summary": "List all users.",
"description": "List all users.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/users -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"createddate": "2026-01-01T00:00:00.000000Z",
"directpermissions": [],
"email": "<redacted:person>",
"failedlogins": 0,
"firstname": "<redacted:person>",
"isactive": true,
"islocked": false,
"lastlogindate": "2026-01-01T00:00:00Z",
"lastname": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"mustchangepassword": "<redacted:secret>",
"permissions": [
"apitokens.create",
"applications.create",
"applications.delete",
"<trimmed for the example: 1 more>"
],
"roles": [
{
"color": null,
"roleid": 1,
"rolename": "admin"
}
],
"userid": 1,
"username": "<redacted:person>"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"core-users"
],
"summary": "Create a new user.",
"description": "Create a new user.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/users -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"directpermissions": [
"endpoints.restart"
],
"email": "<redacted:person>",
"failedlogins": 0,
"firstname": "<redacted:person>",
"isactive": true,
"islocked": false,
"lastlogindate": null,
"lastname": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"mustchangepassword": "<redacted:secret>",
"permissions": [
"applications.view",
"assets.view",
"backups.download",
"<trimmed for the example: 1 more>"
],
"roles": [
{
"color": "#0DCAF0",
"roleid": 3,
"rolename": "technician"
}
],
"userid": 2,
"username": "<redacted:person>",
"warning": "User created but the welcome email could not be sent."
},
"message": "User created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"directpermissions": [
"endpoints.runscript"
],
"email": "<redacted:person>",
"password": "<redacted:secret>",
"roles": [],
"sendwelcome": false,
"username": "<redacted:person>"
}
}
}
}
}
},
"/api/users/{userid}": {
"delete": {
"tags": [
"core-users"
],
"summary": "Delete a user.",
"description": "Delete a user.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: userid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/users/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "User deleted",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "userid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-users"
],
"summary": "Get a single user.",
"description": "Get a single user.\n\n**Auth:** jwt\n\n**Params:** path: userid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/users/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"directpermissions": [],
"email": "<redacted:person>",
"failedlogins": 0,
"firstname": "<redacted:person>",
"isactive": true,
"islocked": false,
"lastlogindate": "2026-01-01T00:00:00Z",
"lastname": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"mustchangepassword": "<redacted:secret>",
"permissions": [],
"roles": [],
"userid": 1,
"username": "<redacted:person>"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "userid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-users"
],
"summary": "Update a user.",
"description": "Update a user.\n\n**Auth:** jwt\n\n**Params:** path: userid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/users/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"directpermissions": [],
"email": "<redacted:person>",
"failedlogins": 0,
"firstname": "<redacted:person>",
"isactive": true,
"islocked": false,
"lastlogindate": null,
"lastname": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"mustchangepassword": "<redacted:secret>",
"permissions": [],
"roles": [],
"userid": 2,
"username": "<redacted:person>"
},
"message": "User updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "userid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: userid (int); body: JSON (fields not yet documented)"
},
"example": {
"password": "<redacted:secret>"
}
}
}
}
}
},
"/api/users/permissions": {
"get": {
"tags": [
"core-users"
],
"summary": "List assignable permissions grouped by category.",
"description": "List assignable permissions grouped by category.\n\n**Auth:** jwt\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/users/permissions -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/users/roles": {
"get": {
"tags": [
"core-users"
],
"summary": "List all roles with their permissions.",
"description": "List all roles with their permissions.\n\n**Auth:** jwt\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/users/roles -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"color": null,
"description": "Administrator",
"grantable": null,
"isadmin": true,
"isguest": false,
"permissions": [],
"roleid": 1,
"rolename": "admin",
"usercount": 1
},
{
"color": "#6C757D",
"description": "Anyone who is not signed in. Holds nothing by default; grant it a permission to open that up to people with no account.",
"grantable": [
"applications.view",
"assets.view",
"computers.view",
"<trimmed for the example: 1 more>"
],
"isadmin": false,
"isguest": true,
"permissions": [],
"roleid": 2,
"rolename": "guest",
"usercount": 0
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"core-users"
],
"summary": "Create a new role.",
"description": "Create a new role.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/users/roles -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"color": "#ff8800",
"description": "colorful",
"permissions": [],
"roleid": 2,
"rolename": "painters"
},
"message": "Role created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"color": "#ff8800",
"description": "colorful",
"permissions": [],
"rolename": "painters"
}
}
}
}
}
},
"/api/users/roles/{roleid}": {
"delete": {
"tags": [
"core-users"
],
"summary": "Delete a role.",
"description": "Delete a role.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: roleid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/users/roles/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "roleid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-users"
],
"summary": "Update a role.",
"description": "Update a role.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: roleid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/users/roles/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"color": "#6C757D",
"description": "Anyone who is not signed in. Holds nothing by default; grant it a permission to open that up to people with no account.",
"permissions": [
"reports.view"
],
"roleid": 2,
"rolename": "guest"
},
"message": "Role updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "roleid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: roleid (int); body: JSON (fields not yet documented)"
},
"example": {
"permissions": [
"reports.view"
]
}
}
}
}
}
},
"/api/vendors": {
"get": {
"tags": [
"core-vendors"
],
"summary": "List all vendors.",
"description": "List all vendors.\n\n**Auth:** permission:assets.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/vendors -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"supportemail": "<redacted:person>",
"supportphone": "<redacted:person>",
"vendor": "Acme",
"vendorid": 1,
"website": null
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "vendor",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"core-vendors"
],
"summary": "Create a new vendor.",
"description": "Create a new vendor.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/vendors -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"supportemail": "<redacted:person>",
"supportphone": "<redacted:person>",
"vendor": "Unscoped Vendor",
"vendorid": 1,
"website": null
},
"message": "Vendor created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"createddate": "2026-01-01 00:00:00",
"vendor": "Legacy Vendor"
}
}
}
}
}
},
"/api/vendors/{vendor_id}": {
"delete": {
"tags": [
"core-vendors"
],
"summary": "Delete (deactivate) a vendor.",
"description": "Delete (deactivate) a vendor.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: vendor_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/vendors/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "vendor_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"core-vendors"
],
"summary": "Get a single vendor.",
"description": "Get a single vendor.\n\n**Auth:** permission:assets.view\n\n**Params:** path: vendor_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/vendors/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "vendor_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"core-vendors"
],
"summary": "Update a vendor.",
"description": "Update a vendor.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: vendor_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/vendors/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "vendor_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: vendor_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/backups/asset/{assetid}": {
"get": {
"tags": [
"plugin-backups"
],
"summary": "Revision history for one asset, newest first.",
"description": "Revision history for one asset, newest first.\n\n**Auth:** permission:backups.view\n\n**Params:** path: assetid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/backups/asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "kind",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/backups/asset/{assetid}/info": {
"get": {
"tags": [
"plugin-backups"
],
"summary": "A kind's 'at a glance' card, built from its LATEST revision.",
"description": "A kind's 'at a glance' card, built from its LATEST revision.\n\n**Auth:** permission:backups.view\n\n**Params:** path: assetid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/backups/asset/1/info -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "kind",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/backups/dashboard/stale": {
"get": {
"tags": [
"plugin-backups"
],
"summary": "Chains whose backup has stopped running.",
"description": "Chains whose backup has stopped running.\n\n**Auth:** permission:backups.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/backups/dashboard/stale -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/backups/kinds": {
"get": {
"tags": [
"plugin-backups"
],
"summary": "Registered backup kinds, for UI that needs to enumerate them.",
"description": "Registered backup kinds, for UI that needs to enumerate them.\n\n**Auth:** permission:backups.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/backups/kinds -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assettypes": [
"machine"
],
"displayname": "<redacted:person>",
"formats": [
{
"ext": ".reg",
"hint": "Restore with the Load... button in the NTLARS settings dialog.",
"id": "ntlars",
"label": "NTLARS Load... (.reg)",
"mimetype": "application/octet-stream"
},
{
"ext": ".reg",
"hint": "Use when importing outside NTLARS on a 64-bit machine.",
"id": "wow6432node",
"label": "Direct reg import (.reg, WOW6432Node)",
"mimetype": "application/octet-stream"
}
],
"key": "ntlars",
"storagebackend": "shopdb"
},
{
"assettypes": [
"machine"
],
"displayname": "<redacted:person>",
"formats": [],
"key": "partmarker",
"storagebackend": "share"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/backups/revisions/{backuprevisionid}": {
"get": {
"tags": [
"plugin-backups"
],
"summary": "One revision, including its parsed payload where there is one.",
"description": "One revision, including its parsed payload where there is one.\n\n**Auth:** permission:backups.view\n\n**Params:** path: backuprevisionid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/backups/revisions/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "backuprevisionid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/backups/revisions/{backuprevisionid}/diff": {
"get": {
"tags": [
"plugin-backups"
],
"summary": "Diff two revisions of the same asset+kind.",
"description": "Diff two revisions of the same asset+kind.\n\n**Auth:** permission:backups.view\n\n**Params:** path: backuprevisionid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/backups/revisions/1/diff -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"againstid": 1,
"backuprevisionid": 2,
"changecount": 1,
"changes": [
{
"after": "OKUMA",
"aftertype": "REG_SZ",
"before": "",
"beforetype": "REG_SZ",
"change": "changed",
"keypath": "General",
"valuename": "Cnc"
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "backuprevisionid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "against",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/backups/revisions/{backuprevisionid}/download": {
"get": {
"tags": [
"plugin-backups"
],
"summary": "Render a revision back to its native file format.",
"description": "Render a revision back to its native file format.\n\n**Auth:** permission:backups.download\n\n**Params:** path: backuprevisionid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/backups/revisions/1/download -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "backuprevisionid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/computers": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "List all computers with filtering and pagination.",
"description": "List all computers with filtering and pagination.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"accessmethods": [],
"assetid": 1,
"assetnumber": "PC-1",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "computer",
"businessunitid": null,
"computer": {
"accessprotocolnames": [],
"assetid": 1,
"azuredevicecategory": null,
"azuredeviceid": null,
"azureobjectid": null,
"computerid": 1,
"computertypeid": 1,
"computertypename": "Standard",
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"isactive": true,
"lastboottime": null,
"lastreporteddate": null,
"loggedinuser": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"osid": null,
"vendorid": null
},
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "assetnumber",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "businessunit_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "dir",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "asc"
}
},
{
"name": "location_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "os_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "osid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "shopfloor",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "sort",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "hostname"
}
},
{
"name": "type_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "typeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-computers"
],
"summary": "Create new computer (creates both Asset and Computer records).",
"description": "Create new computer (creates both Asset and Computer records).\n\n**Auth:** permission:computers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/computers -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"accessmethods": [],
"assetid": 1,
"assetnumber": "AUDIT-PC-1",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "computer",
"businessunitid": null,
"computer": {
"accessprotocolnames": [],
"assetid": 1,
"azuredevicecategory": null,
"azuredeviceid": null,
"azureobjectid": null,
"computerid": 1,
"computertypeid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"isactive": true,
"lastboottime": null,
"lastreporteddate": null,
"loggedinuser": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"osid": null,
"vendorid": null
},
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statuscolor": null,
"statusid": 1,
"statusname": "In Use"
},
"message": "Computer created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"assetnumber": "PC-IMPORT-1",
"createddate": "2026-01-01 00:00:00",
"hostname": "<redacted:host>",
"modifieddate": "2026-01-01T00:00:00"
}
}
}
}
}
},
"/api/computers/{computer_id}": {
"delete": {
"tags": [
"plugin-computers"
],
"summary": "Delete (soft delete) computer.",
"description": "Delete (soft delete) computer.\n\n**Auth:** permission:computers.delete\n\n**Params:** path: computer_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/computers/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "computer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-computers"
],
"summary": "Get a single computer with full details.",
"description": "Get a single computer with full details.\n\n**Auth:** permission:computers.view\n\n**Params:** path: computer_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"accessmethods": [],
"assetid": 1,
"assetnumber": "PC-2001",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "computer",
"businessunitid": null,
"communications": [],
"computer": {
"accessprotocolnames": [],
"assetid": 1,
"azuredevicecategory": null,
"azuredeviceid": null,
"azureobjectid": null,
"computerid": 1,
"computertypeid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"imageurl": "/api/models/images/model-1.png",
"isactive": true,
"lastboottime": null,
"lastreporteddate": null,
"loggedinuser": null,
"modelname": "IMG-MODEL-1",
"modelnumberid": 1,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"osid": null,
"vendorid": null
},
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "computer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-computers"
],
"summary": "Update computer (both Asset and Computer records).",
"description": "Update computer (both Asset and Computer records).\n\n**Auth:** permission:computers.edit\n\n**Params:** path: computer_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/computers/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"accessmethods": [
{
"id": 1,
"link": "rdp://auditpc1",
"name": "RDP",
"port": null,
"portoverride": null,
"protocolid": 1,
"scheme": "rdp"
}
],
"assetid": 1,
"assetnumber": "AUDIT-PC-1",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "computer",
"businessunitid": null,
"computer": {
"accessprotocolnames": [
"RDP"
],
"assetid": 1,
"azuredevicecategory": null,
"azuredeviceid": null,
"azureobjectid": null,
"computerid": 1,
"computertypeid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"isactive": true,
"lastboottime": null,
"lastreporteddate": null,
"loggedinuser": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"osid": null,
"vendorid": null
},
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statuscolor": null,
"statusid": 1,
"statusname": "In Use"
},
"message": "Computer updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "computer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: computer_id (int); body: JSON (fields not yet documented)"
},
"example": {
"gaugelabreference": "GL-2",
"maintenancereference": "MNT-2"
}
}
}
}
}
},
"/api/computers/{computer_id}/apps": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Get all installed applications for a computer.",
"description": "Get all installed applications for a computer.\n\n**Auth:** permission:computers.view\n\n**Params:** path: computer_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/1/apps -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "computer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-computers"
],
"summary": "Add an installed application to a computer.",
"description": "Add an installed application to a computer.\n\n**Auth:** permission:computers.create\n\n**Params:** path: computer_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/computers/1/apps -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "computer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: computer_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/computers/{computer_id}/apps/{app_id}": {
"delete": {
"tags": [
"plugin-computers"
],
"summary": "Remove an installed application from a computer.",
"description": "Remove an installed application from a computer.\n\n**Auth:** permission:computers.delete\n\n**Params:** path: computer_id (int), app_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/computers/1/apps/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "computer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/computers/{computer_id}/report": {
"post": {
"tags": [
"plugin-computers"
],
"summary": "Report computer status (for agent-based reporting).",
"description": "Report computer status (for agent-based reporting).\n\n**Auth:** permission:computers.create\n\n**Params:** path: computer_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/computers/1/report -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "computer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: computer_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/computers/asset/{asset_id}/policypanel": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Keyvalue panel: which policy governs this endpoint, and what it allows.",
"description": "Keyvalue panel: which policy governs this endpoint, and what it allows.\n\n**Auth:** permission:computers.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/asset/1/policypanel -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/computers/by-asset/{asset_id}": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Get computer data by asset ID.",
"description": "Get computer data by asset ID.\n\n**Auth:** permission:computers.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/by-asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/computers/by-hostname/{hostname}": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Get computer by hostname.",
"description": "Get computer by hostname.\n\n**Auth:** permission:computers.view\n\n**Params:** path: hostname (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/by-hostname/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "hostname",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/computers/client-script": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "The collector reporter, stamped with THIS site's values.",
"description": "The collector reporter, stamped with THIS site's values.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/client-script -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/computers/dashboard/quiet": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "PCs that WERE reporting, have stopped, and are still meant to be in use.",
"description": "PCs that WERE reporting, have stopped, and are still meant to be in use.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/dashboard/quiet -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"computerid": 2,
"hostname": "<redacted:host>",
"lastreported": "2026-01-01T00:00:00.000000Z",
"quietdays": 9
},
{
"computerid": 1,
"hostname": "<redacted:host>",
"lastreported": "2026-01-01T00:00:00.000000Z",
"quietdays": 2
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/computers/dashboard/sharedmachines": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Machine numbers claimed by more than one PC, with nothing filed under them.",
"description": "Machine numbers claimed by more than one PC, with nothing filed under them.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/dashboard/sharedmachines -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assetid": 1,
"machinenumber": "2026",
"pccount": 2,
"pcs": "PCONE, PCTWO"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/computers/dashboard/summary": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Get computer dashboard summary data.",
"description": "Get computer dashboard summary data.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/dashboard/summary -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"byos": [],
"bytype": [],
"nonshopfloor": 0,
"shopfloor": 0,
"total": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/computers/display-kiosks": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Reporting display kiosks, for the Dashboard Defaults picker.",
"description": "Reporting display kiosks, for the Dashboard Defaults picker.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/display-kiosks -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"computerid": 1,
"fqdn": "<redacted:host>",
"hostname": "<redacted:host>",
"serialnumber": "<redacted:host>"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/computers/policies/actions": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "The allowlisted action names + labels a policy may reference.",
"description": "The allowlisted action names + labels a policy may reference.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/policies/actions -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"action": "service_start",
"description": "Start a Windows service by name on the endpoint.",
"kind": "command",
"label": "Start service",
"mayauthor": true,
"requiredpermission": null
},
{
"action": "service_stop",
"description": "Stop a running Windows service by name on the endpoint.",
"kind": "command",
"label": "Stop service",
"mayauthor": true,
"requiredpermission": null
},
{
"action": "service_status",
"description": "Report whether a named Windows service is running.",
"kind": "command",
"label": "Check service",
"mayauthor": true,
"requiredpermission": null
},
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/computers/policies/business": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.list_business_policies has no docstring.",
"description": "UNDOCUMENTED: computers.list_business_policies has no docstring.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/policies/business -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.create_business_policy has no docstring.",
"description": "UNDOCUMENTED: computers.create_business_policy has no docstring.\n\n**Auth:** permission:computers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/computers/policies/business -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/computers/policies/business/{policy_id}": {
"delete": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.delete_business_policy has no docstring.",
"description": "UNDOCUMENTED: computers.delete_business_policy has no docstring.\n\n**Auth:** permission:computers.delete\n\n**Params:** path: policy_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/computers/policies/business/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "policy_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.get_business_policy has no docstring.",
"description": "UNDOCUMENTED: computers.get_business_policy has no docstring.\n\n**Auth:** permission:computers.view\n\n**Params:** path: policy_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/policies/business/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "policy_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.update_business_policy has no docstring.",
"description": "UNDOCUMENTED: computers.update_business_policy has no docstring.\n\n**Auth:** permission:computers.edit\n\n**Params:** path: policy_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/computers/policies/business/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "policy_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: policy_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/computers/policies/configuration": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.list_configuration_policies has no docstring.",
"description": "UNDOCUMENTED: computers.list_configuration_policies has no docstring.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/policies/configuration -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.create_configuration_policy has no docstring.",
"description": "UNDOCUMENTED: computers.create_configuration_policy has no docstring.\n\n**Auth:** permission:computers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/computers/policies/configuration -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"actions": [
{
"action": "run_script",
"configurationpolicyactionid": 1,
"configurationpolicyid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"desiredstate": null,
"intervalminutes": null,
"isactive": true,
"mode": "gate",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"params": null,
"sortorder": 0
}
],
"configurationpolicyid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "Legitimate",
"scopejson": null,
"source": "local"
},
"message": "Configuration policy created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"actions": [
{
"action": "run_script"
}
],
"name": "Legitimate"
}
}
}
}
}
},
"/api/computers/policies/configuration/{policy_id}": {
"delete": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.delete_configuration_policy has no docstring.",
"description": "UNDOCUMENTED: computers.delete_configuration_policy has no docstring.\n\n**Auth:** permission:computers.delete\n\n**Params:** path: policy_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/computers/policies/configuration/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "policy_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.get_configuration_policy has no docstring.",
"description": "UNDOCUMENTED: computers.get_configuration_policy has no docstring.\n\n**Auth:** permission:computers.view\n\n**Params:** path: policy_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/policies/configuration/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "policy_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.update_configuration_policy has no docstring.",
"description": "UNDOCUMENTED: computers.update_configuration_policy has no docstring.\n\n**Auth:** permission:computers.edit\n\n**Params:** path: policy_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/computers/policies/configuration/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"actions": [
{
"action": "run_script",
"configurationpolicyactionid": 1,
"configurationpolicyid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"desiredstate": null,
"intervalminutes": null,
"isactive": true,
"mode": "gate",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"params": null,
"sortorder": 0
}
],
"configurationpolicyid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"description": "clearer wording",
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "New Name",
"scopejson": null,
"source": "local"
},
"message": "Configuration policy updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "policy_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: policy_id (int); body: JSON (fields not yet documented)"
},
"example": {
"description": "clearer wording",
"name": "New Name"
}
}
}
}
}
},
"/api/computers/policies/effective/{asset_id}": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "Preview the resolved effective policy for one endpoint (debug/UI).",
"description": "Preview the resolved effective policy for one endpoint (debug/UI).\n\n**Auth:** permission:computers.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/policies/effective/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/computers/protocols": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "List access protocols. ?active=false includes disabled ones.",
"description": "List access protocols. ?active=false includes disabled ones.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/protocols -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
}
]
},
"post": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.create_protocol has no docstring.",
"description": "UNDOCUMENTED: computers.create_protocol has no docstring.\n\n**Auth:** permission:computers.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/computers/protocols -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/computers/protocols/{protocol_id}": {
"delete": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.delete_protocol has no docstring.",
"description": "UNDOCUMENTED: computers.delete_protocol has no docstring.\n\n**Auth:** permission:computers.edit\n\n**Params:** path: protocol_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/computers/protocols/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "protocol_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"patch": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.update_protocol has no docstring.",
"description": "UNDOCUMENTED: computers.update_protocol has no docstring.\n\n**Auth:** permission:computers.edit\n\n**Params:** path: protocol_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/computers/protocols/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "protocol_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": false,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: protocol_id (int); body: JSON (fields not yet documented)"
}
}
}
}
},
"put": {
"tags": [
"plugin-computers"
],
"summary": "UNDOCUMENTED: computers.update_protocol has no docstring.",
"description": "UNDOCUMENTED: computers.update_protocol has no docstring.\n\n**Auth:** permission:computers.edit\n\n**Params:** path: protocol_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/computers/protocols/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "protocol_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: protocol_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/computers/types": {
"get": {
"tags": [
"plugin-computers"
],
"summary": "List all computer types.",
"description": "List all computer types.\n\n**Auth:** permission:computers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/types -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-computers"
],
"summary": "Create a new computer type.",
"description": "Create a new computer type.\n\n**Auth:** permission:computers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/computers/types -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/computers/types/{type_id}": {
"delete": {
"tags": [
"plugin-computers"
],
"summary": "Delete a computer type. Refused if any PC still uses it.",
"description": "Delete a computer type. Refused if any PC still uses it.\n\n**Auth:** permission:computers.delete\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/computers/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-computers"
],
"summary": "Get a single computer type.",
"description": "Get a single computer type.\n\n**Auth:** permission:computers.view\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/computers/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-computers"
],
"summary": "Update a computer type.",
"description": "Update a computer type.\n\n**Auth:** permission:computers.edit\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/computers/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List reported endpoint states.",
"description": "List reported endpoint states.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/ -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"agentversion": null,
"alias": "Bay 3 Controller",
"assetid": 1,
"assetnumber": "fleetbox",
"computerid": 1,
"computertype": null,
"computertypeid": null,
"cpupercent": null,
"createdat": "2026-01-01T00:00:00.000000Z",
"credentialstate": "<redacted:secret>",
"domain": null,
"endpointstateid": 1,
"health": {
"label": "no agent",
"level": "unknown"
},
"hostname": "<redacted:host>",
"idleseconds": null,
"lastboottime": null,
"lastreportedat": null,
"loggedinuser": null,
"machines": [],
"memorypercent": null,
"mtconnectcheckedat": null,
"mtconnectrunning": null,
"pendingreboot": null,
"status": "never",
"trayversion": null,
"uptimedisplay": null,
"uptimeseconds": null
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "computertypeid",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "credentialstate",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "sort",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "status",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/{asset_id}": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Get the current state for one endpoint by asset id.",
"description": "Get the current state for one endpoint by asset id.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"actionminimums": {
"collect_log": "1.16.0"
},
"agentcurrent": "1.6.3",
"agentversion": "1.20.0",
"assetid": 2,
"cpupercent": null,
"createdat": "2026-01-01T00:00:00.000000Z",
"credential": {
"credentialprefix": "<redacted:secret>",
"enrolledvia": "auto",
"issuedat": "2026-01-01T00:00:00.000000Z",
"lastusedat": "2026-01-01T00:00:00.000000Z",
"reenrollblocked": true,
"reenrollblockedreason": "rollback",
"revokedat": "2026-01-01T00:00:00.000000Z",
"state": "reenrollblocked",
"statelabel": "Re-enroll blocked"
},
"domain": null,
"endpointstateid": 2,
"hostname": "<redacted:host>",
"idleseconds": null,
"lastboottime": null,
"lastreportedat": "2026-01-01T00:00:00.000000Z",
"loggedinuser": null,
"memorypercent": null,
"mtconnectcheckedat": null,
"mtconnectrunning": null,
"pendingreboot": null,
"status": "reporting",
"trayversion": null,
"uptimedisplay": null,
"uptimeseconds": null
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/{asset_id}/agentupgrade": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Push the published agent build to one endpoint.",
"description": "Push the published agent build to one endpoint.\n\n**Auth:** permission:endpoints.agentupdate\n\n**Params:** path: asset_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/1/agentupgrade -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"action": "run_script",
"assetid": 1,
"claimedat": null,
"completedat": null,
"createdat": "2026-01-01T00:00:00.000000Z",
"endpointcommandid": 1,
"requestedby": "<redacted:person>",
"resultmessage": null,
"status": "pending",
"target": "script:1",
"targetkind": "script"
},
"message": "Command queued",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: asset_id (int); body: JSON (fields not yet documented)"
},
"example": {
"action": "run_script",
"target": "script:1"
}
}
}
}
}
},
"/api/endpoints/{asset_id}/commands": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Recent commands for one endpoint, newest first (operator view).",
"description": "Recent commands for one endpoint, newest first (operator view).\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1/commands -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Queue an allowlisted command for one endpoint.",
"description": "Queue an allowlisted command for one endpoint.\n\n**Auth:** permission:endpoints.command\n\n**Params:** path: asset_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/1/commands -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"action": "collect_log",
"assetid": 1,
"claimedat": null,
"completedat": null,
"createdat": "2026-01-01T00:00:00.000000Z",
"endpointcommandid": 1,
"requestedby": "<redacted:person>",
"resultmessage": null,
"status": "pending",
"target": "C:\\logs\\app.log",
"targetkind": "logpath"
},
"message": "Command queued",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: asset_id (int); body: JSON (fields not yet documented)"
},
"example": {
"action": "service_status",
"overridereason": "line down, need status",
"policyoverride": true,
"target": "spooler"
}
}
}
}
}
},
"/api/endpoints/{asset_id}/events": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List curated Windows events for one endpoint, newest first.",
"description": "List curated Windows events for one endpoint, newest first.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1/events -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "eventid",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/{asset_id}/holdableactions": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Desired-mode actions on this endpoint, with current hold state.",
"description": "Desired-mode actions on this endpoint, with current hold state.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1/holdableactions -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"action": "service_start",
"held": false
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/{asset_id}/lock": {
"delete": {
"tags": [
"plugin-endpoints"
],
"summary": "Lift the quarantine on this endpoint.",
"description": "Lift the quarantine on this endpoint.\n\n**Auth:** permission:endpoints.command\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/endpoints/1/lock -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "The endpoint lock standing on this endpoint, or null.",
"description": "The endpoint lock standing on this endpoint, or null.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1/lock -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"endpointlockid": 1,
"lockedat": "2026-01-01T00:00:00.000000Z",
"lockedbyuserid": 1,
"lockedbyusername": "<redacted:person>",
"reason": "visible to all",
"releasedat": null,
"releasedbyusername": "<redacted:person>"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Quarantine this endpoint against non-admin commands.",
"description": "Quarantine this endpoint against non-admin commands.\n\n**Auth:** permission:endpoints.command\n\n**Params:** path: asset_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/1/lock -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"endpointlockid": 1,
"lockedat": "2026-01-01T00:00:00.000000Z",
"lockedbyuserid": 1,
"lockedbyusername": "<redacted:person>",
"reason": "locked but still reconciled",
"releasedat": null,
"releasedbyusername": "<redacted:person>"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: asset_id (int); body: JSON (fields not yet documented)"
},
"example": {
"reason": "locked but still reconciled"
}
}
}
}
}
},
"/api/endpoints/{asset_id}/logcollections": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Collected-log history for one endpoint, newest first.",
"description": "Collected-log history for one endpoint, newest first.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1/logcollections -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/{asset_id}/policyholds": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Active break-glass holds for one endpoint.",
"description": "Active break-glass holds for one endpoint.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1/policyholds -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"action": "service_stop",
"createdbyusername": "<redacted:person>",
"expiresat": "2026-01-01T00:00:00.000000",
"reason": "vendor on site"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Deliberately suspend desired-state reconciliation for one or more actions.",
"description": "Deliberately suspend desired-state reconciliation for one or more actions.\n\n**Auth:** permission:endpoints.command\n\n**Params:** path: asset_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/1/policyholds -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"action": "service_stop",
"createdbyusername": "<redacted:person>",
"expiresat": "2026-01-01T00:00:00.000000",
"reason": "stripping the enclosure"
},
{
"action": "service_start",
"createdbyusername": "<redacted:person>",
"expiresat": "2026-01-01T00:00:00.000000",
"reason": "stripping the enclosure"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: asset_id (int); body: JSON (fields not yet documented)"
},
"example": {
"actions": [
"service_start",
"service_stop"
],
"minutes": 60,
"reason": "stripping the enclosure"
}
}
}
}
}
},
"/api/endpoints/{asset_id}/policyholds/{action}": {
"delete": {
"tags": [
"plugin-endpoints"
],
"summary": "End a hold early, resuming reconciliation of one action.",
"description": "End a hold early, resuming reconciliation of one action.\n\n**Auth:** permission:endpoints.command\n\n**Params:** path: asset_id (int), action (string)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/endpoints/1/policyholds/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "action",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/{asset_id}/scriptruns": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "The last few run_script commands for one endpoint, newest first.",
"description": "The last few run_script commands for one endpoint, newest first.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/1/scriptruns -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"action": "run_script",
"assetid": 1,
"claimedat": null,
"completedat": null,
"createdat": "2026-01-01T00:00:00Z",
"endpointcommandid": 6,
"requestedby": "<redacted:person>",
"resultdetail": null,
"resultmessage": null,
"scriptname": "test-open-notepad",
"status": "succeeded",
"target": "script:1",
"targetkind": null
},
{
"action": "run_script",
"assetid": 1,
"claimedat": null,
"completedat": null,
"createdat": "2026-01-01T00:00:00Z",
"endpointcommandid": 5,
"requestedby": "<redacted:person>",
"resultdetail": null,
"resultmessage": null,
"scriptname": "test-open-notepad",
"status": "succeeded",
"target": "script:1",
"targetkind": null
},
{
"action": "run_script",
"assetid": 1,
"claimedat": null,
"completedat": null,
"createdat": "2026-01-01T00:00:00Z",
"endpointcommandid": 4,
"requestedby": "<redacted:person>",
"resultdetail": null,
"resultmessage": null,
"scriptname": "test-open-notepad",
"status": "succeeded",
"target": "script:1",
"targetkind": null
},
"<trimmed for the example: 1 more>"
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "limit",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 5
}
}
]
}
},
"/api/endpoints/adoptiontool/package": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Bundle the adoption tool as a downloadable ZIP.",
"description": "Bundle the adoption tool as a downloadable ZIP.\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/adoptiontool/package -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/agentkey": {
"delete": {
"tags": [
"plugin-endpoints"
],
"summary": "Revoke the endpoint agent key: stop all managed-token endpoint traffic.",
"description": "Revoke the endpoint agent key: stop all managed-token endpoint traffic.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/endpoints/agentkey -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"envkeyfallback": true,
"key": null,
"provisioned": false,
"revoked": 0
},
"message": "Endpoint agent key revoked",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Report the endpoint agent key state (no secret).",
"description": "Report the endpoint agent key state (no secret).\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/agentkey -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/agentkey/regenerate": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Mint a fresh endpoint agent key, revoking any previous one.",
"description": "Mint a fresh endpoint agent key, revoking any previous one.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/agentkey/regenerate -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"envkeyfallback": false,
"key": {
"createddate": "2026-01-01T00:00:00.000000Z",
"displayprefix": "<redacted:secret>",
"expiresat": null,
"isactive": true,
"isexpired": false,
"lastusedat": null,
"name": "Endpoint agent key",
"resourcescopes": null,
"scopes": [
"collector.ingest.endpoints"
],
"tokenid": 1,
"tokenprefix": "<redacted:secret>",
"userid": 1
},
"provisioned": true,
"secret": "<redacted:secret>",
"warning": "Save this key now. It will not be shown again. Configure it as the agent X-API-Key."
},
"message": "Endpoint agent key generated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {}
}
}
}
}
},
"/api/endpoints/alerts": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Fleet alerts for one endpoint by hostname (collector-token auth).",
"description": "Fleet alerts for one endpoint by hostname (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/alerts -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"message": "Scheduled maintenance at 3:30 PM",
"notificationId": 1,
"notificationid": 1,
"timeout": 0,
"title": "Scheduled maintenance at 3:30 PM",
"type": "Fleet Alert",
"typeColor": "#ffc107",
"typecolor": "#ffc107"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "hostname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/alerts/{notification_id}/acknowledge": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent acknowledges a fleet alert (collector-token auth).",
"description": "Agent acknowledges a fleet alert (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** path: notification_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/alerts/1/acknowledge -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"acknowledged": true
},
"message": "Alert already acknowledged",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "notification_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: notification_id (int); body: JSON (fields not yet documented)"
},
"example": {
"assetid": 1,
"hostname": "<redacted:host>"
}
}
}
}
}
},
"/api/endpoints/apppackage/{appversionid}": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent-facing installer download (collector-token auth).",
"description": "Agent-facing installer download (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** path: appversionid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/apppackage/1 -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "appversionid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/apppackage/app/{app_id}": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent-facing installer download by APP (collector-token auth).",
"description": "Agent-facing installer download by APP (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** path: app_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/apppackage/app/1 -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/apppackage/app/{app_id}/{filename}": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent-facing installer download by APP (collector-token auth).",
"description": "Agent-facing installer download by APP (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** path: app_id (int), filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/apppackage/app/1/example.png -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "app_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/activity": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List panel: one chronological feed of what happened to this endpoint.",
"description": "List panel: one chronological feed of what happened to this endpoint.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/activity -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/applications": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Table panel: the installed-software (SBOM) snapshot for this endpoint.",
"description": "Table panel: the installed-software (SBOM) snapshot for this endpoint.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/applications -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/diskhealth": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Physical drive health rows.",
"description": "Physical drive health rows.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/diskhealth -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/hardware": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Keyvalue panel: processor, memory and system chassis inventory.",
"description": "Keyvalue panel: processor, memory and system chassis inventory.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/hardware -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/interfaces": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Table panel: every hardware NIC the agent last reported.",
"description": "Table panel: every hardware NIC the agent last reported.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/interfaces -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/iphistory": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Table panel: every address this asset has held, newest change first.",
"description": "Table panel: every address this asset has held, newest change first.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/iphistory -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/listeners": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Table panel: TCP sockets in LISTEN, with the owning process.",
"description": "Table panel: TCP sockets in LISTEN, with the owning process.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/listeners -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/mappeddrives": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List panel: mapped network drives with a health badge each.",
"description": "List panel: mapped network drives with a health badge each.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/mappeddrives -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/osinfo": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Keyvalue panel: operating system, firmware and domain membership.",
"description": "Keyvalue panel: operating system, firmware and domain membership.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/osinfo -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/recentevents": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List panel: the endpoint's most recent curated events, newest first.",
"description": "List panel: the endpoint's most recent curated events, newest first.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/recentevents -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/services": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List panel: monitored services/processes with a run-state badge per row.",
"description": "List panel: monitored services/processes with a run-state badge per row.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/services -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"action": {
"running": false,
"start": "process_start",
"status": "process_status",
"stop": "process_stop",
"target": "dncMain.exe",
"targetkind": "process"
},
"drift": true,
"kind": "process",
"name": "eDNC",
"statecolor": "gray",
"statelabel": "Unknown"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/status": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Keyvalue panel: the endpoint's current status snapshot.",
"description": "Keyvalue panel: the endpoint's current status snapshot.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/status -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"agentbehind": false,
"agentcurrent": "1.6.3",
"agentversion": "1.20.0",
"credential": {
"credentialprefix": "<redacted:secret>",
"enrolledvia": "auto",
"issuedat": "2026-01-01T00:00:00.000000Z",
"lastusedat": "2026-01-01T00:00:00.000000Z",
"reenrollblocked": true,
"reenrollblockedreason": "rollback",
"revokedat": "2026-01-01T00:00:00.000000Z",
"state": "reenrollblocked",
"statelabel": "Re-enroll blocked"
},
"fields": [
{
"label": "Agent",
"mono": true,
"value": "1.20.0"
},
{
"format": "datetime",
"label": "Last reported",
"mono": false,
"value": "2026-01-01T00:00:00.000000Z"
},
{
"label": "Credential",
"mono": false,
"value": "Re-enroll blocked"
},
"<trimmed for the example: 1 more>"
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/storage": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Tabs panel: volume capacity and physical drive health as two sections.",
"description": "Tabs panel: volume capacity and physical drive health as two sections.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/storage -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/telemetrymeta": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Lightweight freshness probe for the panels.",
"description": "Lightweight freshness probe for the panels.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/telemetrymeta -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/asset/{asset_id}/usercontext": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Keyvalue panel: session-scoped data from the interactive user probe.",
"description": "Keyvalue panel: session-scoped data from the interactive user probe.\n\n**Auth:** permission:endpoints.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/asset/1/usercontext -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/collect": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent telemetry ingest. Same handler as POST /api/collector/endpoints.",
"description": "Agent telemetry ingest. Same handler as POST /api/collector/endpoints.\n\n**Auth:** api-key (endpoints collector token)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/collect -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"action": "created",
"assetid": 1,
"identityvalue": "BAY-01",
"status": "ok",
"warnings": []
},
"message": "endpoints collector created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"agentversion": "1.20.0",
"hostname": "<redacted:host>"
}
}
}
}
}
},
"/api/endpoints/commands/{command_id}/result": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent reports a claimed command's outcome (collector-token auth).",
"description": "Agent reports a claimed command's outcome (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** path: command_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/commands/1/result -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"action": "mtconnect_status",
"assetid": 1,
"claimedat": null,
"completedat": "2026-01-01T00:00:00.000000Z",
"createdat": "2026-01-01T00:00:00.000000Z",
"endpointcommandid": 1,
"requestedby": "<redacted:person>",
"resultmessage": null,
"status": "succeeded",
"target": null,
"targetkind": null
},
"message": "Result recorded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "command_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "hostname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: command_id (int); body: JSON (fields not yet documented)"
},
"example": {
"succeeded": true
}
}
}
}
}
},
"/api/endpoints/commands/next": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent long-poll: claim the next pending command for a hostname.",
"description": "Agent long-poll: claim the next pending command for a hostname.\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/commands/next -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"action": "mtconnect_status",
"endpointcommandid": 1,
"target": null,
"targetkind": null
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "hostname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/dashboard/enrollmentpending": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "One queue row while enroll requests wait for an admin, else nothing.",
"description": "One queue row while enroll requests wait for an admin, else nothing.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/dashboard/enrollmentpending -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"pendingcount": 2,
"summary": "2 PCs waiting for enrollment approval"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/dashboard/quiet": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Endpoints that reported before, then went quiet past the window.",
"description": "Endpoints that reported before, then went quiet past the window.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/dashboard/quiet -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/dashboard/reenrollblocked": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "PCs kept from re-enrolling for more than 7 days.",
"description": "PCs kept from re-enrolling for more than 7 days.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/dashboard/reenrollblocked -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assetid": 2,
"blockeddays": 9,
"computerid": 2,
"hostname": "<redacted:host>",
"reason": "rollback"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/dashboard/stability": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Endpoints with recent crash/shutdown/corruption events.",
"description": "Endpoints with recent crash/shutdown/corruption events.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/dashboard/stability -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/dashboard/summary": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "High-level fleet counts for the endpoints dashboard.",
"description": "High-level fleet counts for the endpoints dashboard.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/dashboard/summary -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/enroll": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "A PC asks for its own credential.",
"description": "A PC asks for its own credential.\n\n**Auth:** none (per-IP rate limited and capped; a valid fleet key only decides auto-enroll)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/enroll -H 'Content-Type: application/json' -d '{}'\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"credential": "<redacted:secret>",
"status": "enrolled"
},
"message": "Endpoint enrolled",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"agentversion": "1.20.0",
"deviceid": null,
"enrollnonce": "mmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmmm",
"hostname": "<redacted:host>",
"serialnumber": "<redacted:host>"
}
}
}
}
}
},
"/api/endpoints/enrollment": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Credential state of every computer, plus pending and recent requests.",
"description": "Credential state of every computer, plus pending and recent requests.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/enrollment -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"computers": [
{
"assetid": 1,
"credentialprefix": "<redacted:secret>",
"enrolledvia": "auto",
"hostname": "<redacted:host>",
"issuedat": "2026-01-01T00:00:00.000000Z",
"lastusedat": null,
"reenrollblocked": false,
"reenrollblockedreason": null,
"serialnumber": "<redacted:host>",
"state": "enrolled"
},
{
"assetid": 2,
"credentialprefix": "<redacted:secret>",
"enrolledvia": null,
"hostname": "<redacted:host>",
"issuedat": null,
"lastusedat": null,
"reenrollblocked": false,
"reenrollblockedreason": null,
"serialnumber": "<redacted:host>",
"state": "notenrolled"
},
{
"assetid": 3,
"credentialprefix": "<redacted:secret>",
"enrolledvia": null,
"hostname": "<redacted:host>",
"issuedat": null,
"lastusedat": null,
"reenrollblocked": false,
"reenrollblockedreason": null,
"serialnumber": "<redacted:host>",
"state": "pending"
}
],
"counts": {
"enrolled": 1,
"notenrolled": 1,
"pending": 1,
"pendingcomputers": 1
},
"requests": [
{
"agentversion": "1.20.0",
"decidedat": null,
"decidedby": null,
"deviceid": null,
"hostname": "<redacted:host>",
"lastseenat": "2026-01-01T00:00:00.000000Z",
"matchedassetid": 3,
"reason": "no serial on record",
"requestedat": "2026-01-01T00:00:00.000000Z",
"requestid": "00000000",
"serialnumber": "<redacted:host>",
"sourceip": "127.0.0.1",
"status": "pending"
},
{
"agentversion": "1.20.0",
"decidedat": null,
"decidedby": null,
"deviceid": null,
"hostname": "<redacted:host>",
"lastseenat": "2026-01-01T00:00:00.000000Z",
"matchedassetid": 1,
"reason": null,
"requestedat": "2026-01-01T00:00:00.000000Z",
"requestid": "00000000",
"serialnumber": "<redacted:host>",
"sourceip": "127.0.0.1",
"status": "issued"
}
],
"settings": {
"autoenroll": true,
"maxpendingenrollments": 500,
"revokeddeniessharedkey": false,
"sharedkeyallowed": true
}
},
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 3,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "state",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/enrollment/assets/{assetid}/allow-reenroll": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Lift a re-enrollment block. The PC enrolls on its next attempt.",
"description": "Lift a re-enrollment block. The PC enrolls on its next attempt.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: assetid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/enrollment/assets/1/allow-reenroll -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"credentialid": 1,
"credentialprefix": "<redacted:secret>",
"enrolledvia": "auto",
"issuedat": "2026-01-01T00:00:00.000000Z",
"lastusedat": null,
"reenrollblocked": false,
"reenrollblockedreason": null,
"revokedat": "2026-01-01T00:00:00.000000Z",
"revokedby": "testadmin"
},
"message": "Re-enrollment allowed",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: assetid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/enrollment/assets/{assetid}/revoke": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Un-enroll a PC. Its agent gets CREDENTIAL_INVALID and enrolls again.",
"description": "Un-enroll a PC. Its agent gets CREDENTIAL_INVALID and enrolls again.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: assetid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/enrollment/assets/1/revoke -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"credentialid": 1,
"credentialprefix": "<redacted:secret>",
"enrolledvia": "auto",
"issuedat": "2026-01-01T00:00:00.000000Z",
"lastusedat": null,
"reenrollblocked": true,
"reenrollblockedreason": "rollback",
"revokedat": "2026-01-01T00:00:00.000000Z",
"revokedby": "testadmin"
},
"message": "Endpoint credential revoked",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: assetid (int); body: JSON (fields not yet documented)"
},
"example": {
"blockreenroll": true,
"reason": "rollback"
}
}
}
}
}
},
"/api/endpoints/enrollment/migration": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Per-computer readiness to move onto per-PC credentials, plus waves.",
"description": "Per-computer readiness to move onto per-PC credentials, plus waves.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/enrollment/migration -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"computers": [
{
"agentversion": "1.19.0",
"assetid": 2,
"blockers": [],
"hostname": "<redacted:host>",
"lastreportedat": "2026-01-01T00:00:00.000000Z",
"state": "ready"
},
{
"agentversion": "1.19.0",
"assetid": 3,
"blockers": [],
"hostname": "<redacted:host>",
"lastreportedat": "2026-01-01T00:00:00.000000Z",
"state": "ready"
},
{
"agentversion": "1.20.0",
"assetid": 1,
"blockers": [
"awaiting enrollment"
],
"hostname": "<redacted:host>",
"lastreportedat": "2026-01-01T00:00:00.000000Z",
"state": "blocked"
}
],
"counts": {
"blocked": 1,
"enrolled": 0,
"notreporting": 0,
"pending": 0,
"ready": 2,
"upgrading": 0
},
"target": "1.20.0",
"waves": [
{
"createdat": "2026-01-01T00:00:00Z",
"createdby": "<redacted:person>",
"done": false,
"enrolled": 0,
"failed": 1,
"queued": 3,
"size": 3,
"waveid": 1
},
{
"createdat": "2026-01-01T00:00:00Z",
"createdby": "<redacted:person>",
"done": false,
"enrolled": 0,
"failed": 0,
"queued": 2,
"size": 2,
"waveid": 2
}
]
},
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 3,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "state",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/enrollment/migration/wave": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Push the agent upgrade to a batch of READY PCs.",
"description": "Push the agent upgrade to a batch of READY PCs.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/enrollment/migration/wave -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"queued": [
1
],
"retried": [],
"skipped": [
{
"assetid": 2,
"reason": "offline"
},
{
"assetid": 3,
"reason": "notreporting"
},
{
"assetid": 999999,
"reason": "not a computer"
}
],
"waveid": 1
},
"message": "1 PC(s) queued",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"action": "run_script",
"target": "script:1"
}
}
}
}
}
},
"/api/endpoints/enrollment/requests/{requestid}/approve": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Bind a pending request to the asset the admin picked.",
"description": "Bind a pending request to the asset the admin picked.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: requestid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/enrollment/requests/1/approve -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"agentversion": "1.20.0",
"decidedat": "2026-01-01T00:00:00.000000Z",
"decidedby": "testadmin",
"deviceid": null,
"hostname": "<redacted:host>",
"hostnameresult": "<redacted:host>",
"lastseenat": "2026-01-01T00:00:00.000000Z",
"matchedassetid": 1,
"reason": null,
"requestedat": "2026-01-01T00:00:00.000000Z",
"requestid": "00000000",
"serialnumber": "<redacted:host>",
"sourceip": "127.0.0.1",
"status": "approved"
},
"message": "Enroll request approved; that computer was renamed to the hostname the PC reports",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "requestid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: requestid (int); body: JSON (fields not yet documented)"
},
"example": {
"assetid": 1,
"sethostname": "<redacted:host>"
}
}
}
}
}
},
"/api/endpoints/enrollment/requests/{requestid}/reject": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "UNDOCUMENTED: endpoints.reject_enroll_request has no docstring.",
"description": "UNDOCUMENTED: endpoints.reject_enroll_request has no docstring.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: requestid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/enrollment/requests/1/reject -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"agentversion": "1.20.0",
"decidedat": "2026-01-01T00:00:00.000000Z",
"decidedby": "testadmin",
"deviceid": null,
"hostname": "<redacted:host>",
"lastseenat": "2026-01-01T00:00:00.000000Z",
"matchedassetid": 1,
"reason": "awaiting approval",
"requestedat": "2026-01-01T00:00:00.000000Z",
"requestid": "00000000",
"serialnumber": "<redacted:host>",
"sourceip": "127.0.0.1",
"status": "rejected"
},
"message": "Enroll request rejected",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "requestid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: requestid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/enrollment/settings": {
"put": {
"tags": [
"plugin-endpoints"
],
"summary": "Change the enrollment settings.",
"description": "Change the enrollment settings.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/endpoints/enrollment/settings -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"autoenroll": true,
"maxpendingenrollments": 500,
"revokeddeniessharedkey": false,
"sharedkeyallowed": false
},
"message": "Enrollment settings saved",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"revokeddeniessharedkey": true
}
}
}
}
}
},
"/api/endpoints/logcollections/{collection_id}": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "One collected log including its content, for the scrollable pane.",
"description": "One collected log including its content, for the scrollable pane.\n\n**Auth:** permission:endpoints.updateapp\n\n**Params:** path: collection_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/logcollections/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "collection_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/logcollections/{collection_id}/download": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Serve a collected log as a file attachment.",
"description": "Serve a collected log as a file attachment.\n\n**Auth:** permission:endpoints.updateapp\n\n**Params:** path: collection_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/logcollections/1/download -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "collection_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/monitors": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List monitor definitions (shipped and local).",
"description": "List monitor definitions (shipped and local).\n\n**Auth:** permission:endpoints.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/monitors -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Create a user-defined (local) monitor definition.",
"description": "Create a user-defined (local) monitor definition.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/monitors -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/monitors/{monitor_id}": {
"delete": {
"tags": [
"plugin-endpoints"
],
"summary": "Delete a local monitor definition. Shipped rows are protected.",
"description": "Delete a local monitor definition. Shipped rows are protected.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: monitor_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/endpoints/monitors/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "monitor_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-endpoints"
],
"summary": "Update a local monitor definition. Shipped rows are read-only.",
"description": "Update a local monitor definition. Shipped rows are read-only.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: monitor_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/endpoints/monitors/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createdat": "2026-01-01T00:00:00.000000Z",
"datacollectorpath": null,
"displayname": "<redacted:person>",
"endpointmonitorid": 1,
"isactive": false,
"kind": "process",
"launchpath": "C:\\Program Files\\Dnc\\bin\\DncMain.exe",
"logcollectorpath": null,
"processname": "UDC",
"servicename": null,
"source": "shipped"
},
"message": "Monitor updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "monitor_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: monitor_id (int); body: JSON (fields not yet documented)"
},
"example": {
"launchpath": "D:\\Dnc\\bin\\DncMain.exe"
}
}
}
}
}
},
"/api/endpoints/monitors/resolve": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Resolve the monitor set for a PC type (agent runtime fetch).",
"description": "Resolve the monitor set for a PC type (agent runtime fetch).\n\n**Auth:** permission:endpoints.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/monitors/resolve -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "pctype",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/monitors/resolved": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent watch list: the monitors this endpoint should report on.",
"description": "Agent watch list: the monitors this endpoint should report on.\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/monitors/resolved -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"processes": [
{
"app": "Edge",
"launchpath": "C:\\Program Files (x86)\\Microsoft\\Edge\\Application\\msedge.exe",
"name": "msedge.exe"
}
],
"services": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "hostname",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/endpoints/operatorreports": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent uploads one operator issue report (collector-token auth).",
"description": "Agent uploads one operator issue report (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/operatorreports -H \"X-API-Key: $KEY\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"createdat": "2026-01-01T00:00:00.000000Z",
"details": "the CMM app will not start",
"hasimage": true,
"imagebytesize": 70,
"imagemimetype": "image/png",
"operatorreportid": 1,
"reason": "Other (free text)",
"reportedhostname": "<redacted:host>"
},
"message": "Operator report received",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/operatorreports/{operatorreportid}/image": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Serve one operator report's screenshot.",
"description": "Serve one operator report's screenshot.\n\n**Auth:** permission:endpoints.operatorreports\n\n**Params:** path: operatorreportid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/operatorreports/1/image -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "operatorreportid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/panel/{asset_id}/operatorreports": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Operator Reports panel: this PC's recent operator issue reports.",
"description": "Operator Reports panel: this PC's recent operator issue reports.\n\n**Auth:** permission:endpoints.operatorreports\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/panel/1/operatorreports -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"reports": [
{
"assetid": 1,
"createdat": "2026-01-01T00:00:00.000000Z",
"details": "second",
"hasimage": false,
"imagebytesize": null,
"imagemimetype": null,
"operatorreportid": 2,
"reason": "Other (free text)",
"reportedhostname": "<redacted:host>"
},
{
"assetid": 1,
"createdat": "2026-01-01T00:00:00.000000Z",
"details": "first",
"hasimage": false,
"imagebytesize": null,
"imagemimetype": null,
"operatorreportid": 1,
"reason": "Other (free text)",
"reportedhostname": "<redacted:host>"
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/scriptbody/{script_id}": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Agent-facing script body download (collector-token auth).",
"description": "Agent-facing script body download (collector-token auth).\n\n**Auth:** api-key (endpoint agent credential, or the fleet key while sharedkeyallowed is on)\n\n**Params:** path: script_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/scriptbody/1 -H \"X-API-Key: $KEY\"\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "script_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/endpoints/settings/server-cert": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Get details about the current server certificate.",
"description": "Get details about the current server certificate.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/settings/server-cert -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"expires_in_days": 29,
"is_self_signed": true,
"issuer": "CN = pin.example.test",
"not_after": "Oct 18 18:57:47 2026 GMT",
"not_before": "Sep 17 18:57:47 2026 GMT",
"san_list": [],
"sha1thumbprint": "<redacted:digest>",
"spkisha256": "<redacted:digest>",
"subject_cn": "pin.example.test",
"thumbprint": "99:F1:E1:1D:5A:66:EE:44:8C:CA:5C:D8:BF:EA:C3:F3:8F:82:40:D3:5E:C9:4D:F0:AC:0B:3C:AD:80:D7:C1:DF"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/settings/server-cert/download": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "The PUBLIC server certificate as a DER .cer file, never the key.",
"description": "The PUBLIC server certificate as a DER .cer file, never the key.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/settings/server-cert/download -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/settings/server-cert/generate": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Generate a new self-signed server certificate.",
"description": "Generate a new self-signed server certificate.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/settings/server-cert/generate -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"message": "Certificate generated successfully. Nginx is restarting."
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"cn": "shopdb.example.test",
"days": 30,
"san": "<redacted:address>"
}
}
}
}
}
},
"/api/endpoints/settings/server-cert/live": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "The certificate PCs actually receive from this site's public address.",
"description": "The certificate PCs actually receive from this site's public address.\n\n**Auth:** permission:endpoints.fleet\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/settings/server-cert/live -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"configured": true,
"error": "Could not read the certificate from shopdb.example.test:443 (Connection refused)",
"matchesfile": false,
"presentedsha1thumbprint": null,
"presentedspkisha256": null,
"url": "https://shopdb.example.test"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/settings/server-cert/upload": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Upload a new server certificate and private key.",
"description": "Upload a new server certificate and private key.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/settings/server-cert/upload -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"message": "Certificate uploaded successfully. Nginx is restarting."
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/siteagent": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Report whether the site agent build has a prebuilt binary staged.",
"description": "Report whether the site agent build has a prebuilt binary staged.\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/siteagent -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"agentcurrent": null,
"agentlegacy": null,
"agentstaged": false,
"agentversions": [],
"certavailable": true,
"serverpin": "<redacted:digest>",
"sharedkeyallowed": false,
"traycurrent": null,
"traylegacy": null,
"traystaged": false,
"trayversions": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/siteagent/binaries/{binkey}": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "List staged versions for a binary (agent or tray), newest first.",
"description": "List staged versions for a binary (agent or tray), newest first.\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** path: binkey (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/siteagent/binaries/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "binkey",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Stage an uploaded binary as a new version.",
"description": "Stage an uploaded binary as a new version.\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** path: binkey (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/siteagent/binaries/x -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"binary": "agent",
"current": "<redacted:address>",
"registration": {
"agentversion": "<redacted:address>",
"appid": 1,
"appname": "ShopDB Endpoint Agent",
"contents": {
"agent": {
"filename": "shopdbagent.exe",
"sha256": "<redacted:digest>",
"version": "<redacted:address>"
}
},
"created": false,
"installpath": "/api/applications/package/1/shopdb-endpoint-agent.zip",
"ok": true,
"sha256": "<redacted:digest>",
"size": 135
},
"versions": [
{
"iscurrent": true,
"size": 130,
"uploadedat": "2026-01-01T00:00:00.000000Z",
"version": "<redacted:address>"
},
{
"iscurrent": false,
"size": 130,
"uploadedat": "2026-01-01T00:00:00.000000Z",
"version": "<redacted:address>"
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "binkey",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: binkey (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/siteagent/binaries/{binkey}/adopt": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Adopt the unmanaged legacy flat file into the version store.",
"description": "Adopt the unmanaged legacy flat file into the version store.\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** path: binkey (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/siteagent/binaries/x/adopt -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "binkey",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: binkey (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/siteagent/binaries/{binkey}/current": {
"put": {
"tags": [
"plugin-endpoints"
],
"summary": "Point 'current' at an already-staged version (roll back or forward).",
"description": "Point 'current' at an already-staged version (roll back or forward).\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** path: binkey (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/endpoints/siteagent/binaries/x/current -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"binary": "agent",
"current": "<redacted:address>",
"registration": {
"agentversion": "<redacted:address>",
"appid": 1,
"appname": "ShopDB Endpoint Agent",
"contents": {
"agent": {
"filename": "shopdbagent.exe",
"sha256": "<redacted:digest>",
"version": "<redacted:address>"
}
},
"created": false,
"installpath": "/api/applications/package/1/shopdb-endpoint-agent.zip",
"ok": true,
"sha256": "<redacted:digest>",
"size": 135
},
"versions": [
{
"iscurrent": false,
"size": 258,
"uploadedat": "2026-01-01T00:00:00.000000Z",
"version": "<redacted:address>"
},
{
"iscurrent": true,
"size": 258,
"uploadedat": "2026-01-01T00:00:00.000000Z",
"version": "<redacted:address>"
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "binkey",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: binkey (string); body: JSON (fields not yet documented)"
},
"example": {
"version": "<redacted:address>"
}
}
}
}
}
},
"/api/endpoints/siteagent/binaries/{binkey}/detect": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Read the PE file version of an uploaded EXE without staging it.",
"description": "Read the PE file version of an uploaded EXE without staging it.\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** path: binkey (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/siteagent/binaries/x/detect -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "binkey",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: binkey (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/siteagent/bootstrap.ps1": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "The PowerShell the one-line command downloads, runs and deletes.",
"description": "The PowerShell the one-line command downloads, runs and deletes.\n\n**Auth:** api-key (single-use bootstrap token in the X-Endpoint-Bootstrap-Token header, or ?t= while that is enabled; per-IP rate limited, 404 when not usable)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/siteagent/bootstrap.ps1\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/siteagent/bootstrap/package": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "The keyless agent package the bootstrap script installs.",
"description": "The keyless agent package the bootstrap script installs.\n\n**Auth:** api-key (single-use bootstrap token in the X-Endpoint-Bootstrap-Token header, or ?t= while that is enabled; per-IP rate limited, 404 when not usable)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/siteagent/bootstrap/package\n```",
"security": [
{
"apiKeyAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/endpoints/siteagent/bootstrap/tokens": {
"get": {
"tags": [
"plugin-endpoints"
],
"summary": "Every bootstrap token, newest first. Never a secret.",
"description": "Every bootstrap token, newest first. Never a secret.\n\n**Auth:** jwt + role:admin\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/endpoints/siteagent/bootstrap/tokens -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"tokens": [
{
"createdat": "2026-01-01T00:00:00.000000Z",
"createdby": "<redacted:person>",
"expiresat": "2026-01-01T00:00:00.000000Z",
"lastusedat": null,
"lastusedip": null,
"maxuses": 25,
"remaining": 25,
"revokedat": null,
"state": "active",
"tokenid": 1,
"tokenprefix": "<redacted:secret>",
"usecount": 0
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
},
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Mint one short-lived bootstrap token. The secret is returned ONCE.",
"description": "Mint one short-lived bootstrap token. The secret is returned ONCE.\n\n**Auth:** jwt + role:admin\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/siteagent/bootstrap/tokens -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"command": "powershell -ExecutionPolicy Bypass -c \"try { New-Item -ItemType Directory -Force -Path 'C:\\Program Files\\ShopDB\\bootstrap' | Out-Null; icacls 'C:\\Program Files\\ShopDB\\bootstrap' /inheritance:r /grant ...",
"scripturl": "https://shopdb.test/shopdb/api/endpoints/siteagent/bootstrap.ps1?t=<redacted:token>&via=download",
"secret": "<redacted:secret>",
"token": {
"createdat": "2026-01-01T00:00:00.000000Z",
"createdby": "<redacted:person>",
"expiresat": "2026-01-01T00:00:00.000000Z",
"lastusedat": null,
"lastusedip": null,
"maxuses": 500,
"remaining": 500,
"revokedat": null,
"state": "active",
"tokenid": 1,
"tokenprefix": "<redacted:secret>",
"usecount": 0
}
},
"message": "Bootstrap token created. The command is shown once.",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"hours": 6,
"maxuses": 3
}
}
}
}
}
},
"/api/endpoints/siteagent/bootstrap/tokens/{tokenid}/revoke": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Kill a bootstrap token now. Already-revoked is a no-op, not an error.",
"description": "Kill a bootstrap token now. Already-revoked is a no-op, not an error.\n\n**Auth:** jwt + role:admin\n\n**Params:** path: tokenid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/siteagent/bootstrap/tokens/1/revoke -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"token": {
"createdat": "2026-01-01T00:00:00.000000Z",
"createdby": "<redacted:person>",
"expiresat": "2026-01-01T00:00:00.000000Z",
"lastusedat": null,
"lastusedip": null,
"maxuses": 25,
"remaining": 25,
"revokedat": "2026-01-01T00:00:00.000000Z",
"state": "revoked",
"tokenid": 1,
"tokenprefix": "<redacted:secret>",
"usecount": 0
}
},
"message": "Bootstrap token revoked",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "tokenid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: tokenid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/endpoints/siteagent/package": {
"post": {
"tags": [
"plugin-endpoints"
],
"summary": "Bundle the site agent as a downloadable ZIP.",
"description": "Bundle the site agent as a downloadable ZIP.\n\n**Auth:** permission:endpoints.agentpackage\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/endpoints/siteagent/package -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"baseurl": "https://shopdb.test",
"bundlecert": true,
"cadenceseconds": 900,
"collectorkey": "<redacted:token>",
"nextserverpin": "<redacted:digest>"
}
}
}
}
}
},
"/api/guides": {
"get": {
"tags": [
"plugin-guides"
],
"summary": "Published guides, plus the caller's own drafts if they can author.",
"description": "Published guides, plus the caller's own drafts if they can author.\n\n**Auth:** permission:guides.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/guides -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"canedit": false,
"checklistitems": 0,
"createdat": "2026-01-01T00:00:00.000000Z",
"guideid": 1,
"ispublished": true,
"publishedat": "2026-01-01T00:00:00.000000Z",
"revision": 2,
"slug": "published-procedure",
"status": "published",
"summary": null,
"tags": [],
"title": "Published procedure",
"updatedat": "2026-01-01T00:00:00.000000Z"
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "q",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "tag",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-guides"
],
"summary": "UNDOCUMENTED: guides.create_guide has no docstring.",
"description": "UNDOCUMENTED: guides.create_guide has no docstring.\n\n**Auth:** permission:guides.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/guides -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"blocks": [],
"createdat": "2026-01-01T00:00:00.000000Z",
"guideid": 1,
"publishedat": null,
"revision": 1,
"slug": "replacing-a-marker-controler",
"status": "draft",
"summary": null,
"tags": [],
"title": "Replacing a marker controler",
"updatedat": "2026-01-01T00:00:00.000000Z"
},
"message": "Guide created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"blocks": [],
"title": "Replacing a marker controler"
}
}
}
}
}
},
"/api/guides/{guideid}": {
"delete": {
"tags": [
"plugin-guides"
],
"summary": "UNDOCUMENTED: guides.delete_guide has no docstring.",
"description": "UNDOCUMENTED: guides.delete_guide has no docstring.\n\n**Auth:** permission:guides.delete\n\n**Params:** path: guideid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/guides/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "guideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-guides"
],
"summary": "UNDOCUMENTED: guides.update_guide has no docstring.",
"description": "UNDOCUMENTED: guides.update_guide has no docstring.\n\n**Auth:** permission:guides.view\n\n**Params:** path: guideid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/guides/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"blocks": [],
"createdat": "2026-01-01T00:00:00.000000Z",
"guideid": 1,
"publishedat": null,
"revision": 2,
"saved": true,
"slug": "replacing-a-marker-controler",
"status": "draft",
"summary": null,
"tags": [],
"title": "Replacing a marker controller",
"updatedat": "2026-01-01T00:00:00.000000Z"
},
"message": "Saved",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "guideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: guideid (int); body: JSON (fields not yet documented)"
},
"example": {
"blocks": [],
"title": "Replacing a marker controller"
}
}
}
}
}
},
"/api/guides/{guideid}/publish": {
"post": {
"tags": [
"plugin-guides"
],
"summary": "UNDOCUMENTED: guides.publish_guide has no docstring.",
"description": "UNDOCUMENTED: guides.publish_guide has no docstring.\n\n**Auth:** permission:guides.publish\n\n**Params:** path: guideid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/guides/1/publish -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "guideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: guideid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/guides/{guideid}/restore/{revisionid}": {
"post": {
"tags": [
"plugin-guides"
],
"summary": "UNDOCUMENTED: guides.restore_revision has no docstring.",
"description": "UNDOCUMENTED: guides.restore_revision has no docstring.\n\n**Auth:** permission:guides.view\n\n**Params:** path: guideid (int), revisionid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/guides/1/restore/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "guideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
},
{
"name": "revisionid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: guideid (int), revisionid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/guides/{guideid}/revisions": {
"get": {
"tags": [
"plugin-guides"
],
"summary": "UNDOCUMENTED: guides.list_revisions has no docstring.",
"description": "UNDOCUMENTED: guides.list_revisions has no docstring.\n\n**Auth:** permission:guides.view\n\n**Params:** path: guideid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/guides/1/revisions -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "guideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/guides/{guideid}/unpublish": {
"post": {
"tags": [
"plugin-guides"
],
"summary": "UNDOCUMENTED: guides.unpublish_guide has no docstring.",
"description": "UNDOCUMENTED: guides.unpublish_guide has no docstring.\n\n**Auth:** permission:guides.publish\n\n**Params:** path: guideid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/guides/1/unpublish -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "guideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: guideid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/guides/{guideid}/working": {
"get": {
"tags": [
"plugin-guides"
],
"summary": "The working copy, for the editor.",
"description": "The working copy, for the editor.\n\n**Auth:** permission:guides.view\n\n**Params:** path: guideid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/guides/1/working -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "guideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/guides/{slug}": {
"get": {
"tags": [
"plugin-guides"
],
"summary": "What a reader gets: the published revision.",
"description": "What a reader gets: the published revision.\n\n**Auth:** permission:guides.view\n\n**Params:** path: slug (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/guides/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "slug",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/guides/images": {
"post": {
"tags": [
"plugin-guides"
],
"summary": "Take a pasted or dropped image.",
"description": "Take a pasted or dropped image.\n\n**Auth:** permission:guides.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/guides/images -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"bytesize": 40,
"createdat": "2026-01-01T00:00:00.000000Z",
"filename": "screenshot.png",
"guideid": null,
"guideimageid": 1,
"mimetype": "image/png",
"url": "/api/guides/images/1"
},
"message": "Image uploaded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/guides/images/{imageid}": {
"get": {
"tags": [
"plugin-guides"
],
"summary": "The image itself, under the same rule as the guide that holds it.",
"description": "The image itself, under the same rule as the guide that holds it.\n\n**Auth:** permission:guides.view\n\n**Params:** path: imageid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/guides/images/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "imageid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/guides/revisions/{revisionid}": {
"get": {
"tags": [
"plugin-guides"
],
"summary": "One revision by id.",
"description": "One revision by id.\n\n**Auth:** permission:guides.view\n\n**Params:** path: revisionid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/guides/revisions/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"blocks": [
{
"id": "b1",
"text": "secret draft wording",
"type": "paragraph"
}
],
"createdat": "2026-01-01T00:00:00.000000Z",
"createdby": "<redacted:person>",
"guideid": 1,
"guiderevisionid": 1,
"note": null,
"revision": 1,
"shorthash": "<redacted:secret>",
"summary": null,
"tags": [],
"title": "Published procedure"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "revisionid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/guides/tags": {
"get": {
"tags": [
"plugin-guides"
],
"summary": "Every tag in use, with a count, for the filter chips.",
"description": "Every tag in use, with a count, for the filter chips.\n\n**Auth:** permission:guides.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/guides/tags -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/knowledgebase": {
"get": {
"tags": [
"plugin-knowledgebase"
],
"summary": "List all knowledge base articles.",
"description": "List all knowledge base articles.\n\n**Auth:** permission:kb.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/knowledgebase -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"appid": 1,
"application": {
"appid": 1,
"appname": "Spotfire"
},
"clicks": 0,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"keywords": "install",
"lastupdated": "2026-01-01T00:00:00.000000Z",
"linkid": 3,
"linkurl": "https://kb.example/c",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"shortdescription": "Spotfire install guide"
},
{
"appid": 1,
"application": {
"appid": 1,
"appname": "Spotfire"
},
"clicks": 0,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"keywords": "export",
"lastupdated": "2026-01-01T00:00:00.000000Z",
"linkid": 2,
"linkurl": "https://kb.example/b",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"shortdescription": "Export a visualization"
},
{
"appid": 1,
"application": {
"appid": 1,
"appname": "Spotfire"
},
"clicks": 0,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"keywords": "login",
"lastupdated": "2026-01-01T00:00:00.000000Z",
"linkid": 1,
"linkurl": "https://kb.example/a",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"shortdescription": "Dashboard login steps"
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 3,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "appid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "linkurl",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "order",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "desc"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "shortdescription",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "sort",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "clicks"
}
}
]
},
"post": {
"tags": [
"plugin-knowledgebase"
],
"summary": "Create a new knowledge base article.",
"description": "Create a new knowledge base article.\n\n**Auth:** permission:kb.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/knowledgebase -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appid": null,
"clicks": 0,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"keywords": "printer reset",
"lastupdated": "2026-01-01T00:00:00.000000Z",
"linkid": 1,
"linkurl": "https://kb.example/printer-reset",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"shortdescription": "How to reset a printer"
},
"message": "Article created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"keywords": "printer reset",
"linkurl": "https://kb.example/printer-reset",
"shortdescription": "How to reset a printer"
}
}
}
}
}
},
"/api/knowledgebase/{link_id}": {
"delete": {
"tags": [
"plugin-knowledgebase"
],
"summary": "Delete (deactivate) a knowledge base article.",
"description": "Delete (deactivate) a knowledge base article.\n\n**Auth:** permission:kb.delete\n\n**Params:** path: link_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/knowledgebase/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "link_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-knowledgebase"
],
"summary": "Get a single knowledge base article.",
"description": "Get a single knowledge base article.\n\n**Auth:** permission:kb.view\n\n**Params:** path: link_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/knowledgebase/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"appid": null,
"application": null,
"clicks": 0,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"keywords": "printer reset",
"lastupdated": "2026-01-01T00:00:00.000000Z",
"linkid": 1,
"linkurl": "https://kb.example/printer-reset",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"shortdescription": "How to reset a printer"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "link_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-knowledgebase"
],
"summary": "Update a knowledge base article.",
"description": "Update a knowledge base article.\n\n**Auth:** permission:kb.edit\n\n**Params:** path: link_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/knowledgebase/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "link_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: link_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/knowledgebase/{link_id}/click": {
"post": {
"tags": [
"plugin-knowledgebase"
],
"summary": "Increment the click counter for an article the caller is allowed to read.",
"description": "Increment the click counter for an article the caller is allowed to read.\n\n**Auth:** permission:kb.view\n\n**Params:** path: link_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/knowledgebase/1/click -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "link_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: link_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/knowledgebase/stats": {
"get": {
"tags": [
"plugin-knowledgebase"
],
"summary": "Get knowledge base statistics.",
"description": "Get knowledge base statistics.\n\n**Auth:** permission:kb.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/knowledgebase/stats -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"totalarticles": 0,
"totalclicks": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/machines": {
"get": {
"tags": [
"plugin-machines"
],
"summary": "List all machines with filtering and pagination.",
"description": "List all machines with filtering and pagination.\n\n**Auth:** permission:machines.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/machines -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assetid": 1,
"assetnumber": "2007",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "machine",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"dualpathpartner": {
"assetid": 2,
"assetnumber": "2008",
"machineid": 2
},
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"machine": {
"assetid": 1,
"controllermodelid": null,
"controllervendorid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"islocationonly": false,
"lastmaintenancedate": null,
"machineid": 1,
"machinetypeid": null,
"maintenanceintervaldays": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"nextmaintenancedate": null,
"requiresmanualconfig": false,
"vendorid": null
},
"maintenancereference": null,
"mapverifiedat": null,
"mapx": 100,
"mapy": 100,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": 100,
"ownmapy": 100,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "assetnumber",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "businessunit_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "dir",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "asc"
}
},
{
"name": "location_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "sort",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "assetnumber"
}
},
{
"name": "type_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "typeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "vendor_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "vendorid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-machines"
],
"summary": "Create new machine (creates both Asset and Machine records).",
"description": "Create new machine (creates both Asset and Machine records).\n\n**Auth:** permission:machines.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/machines -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "MAINT-DATE-1",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "machine",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"machine": {
"assetid": 1,
"controllermodelid": null,
"controllervendorid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"islocationonly": false,
"lastmaintenancedate": "2026-01-01",
"machineid": 1,
"machinetypeid": null,
"maintenanceintervaldays": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"nextmaintenancedate": "2026-01-01",
"requiresmanualconfig": false,
"vendorid": null
},
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "Maintenance date probe",
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
},
"message": "Machine created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"assetnumber": "MAINT-DATE-1",
"lastmaintenancedate": "2026-01-01",
"name": "Maintenance date probe",
"nextmaintenancedate": "2026-01-01"
}
}
}
}
}
},
"/api/machines/{machine_id}": {
"delete": {
"tags": [
"plugin-machines"
],
"summary": "Delete (soft delete) machine.",
"description": "Delete (soft delete) machine.\n\n**Auth:** permission:machines.delete\n\n**Params:** path: machine_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/machines/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "machine_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-machines"
],
"summary": "Get a single machine item with full details.",
"description": "Get a single machine item with full details.\n\n**Auth:** permission:machines.view\n\n**Params:** path: machine_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/machines/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "2007",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "machine",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"dualpathpartner": {
"assetid": 2,
"assetnumber": "2008",
"machineid": 2
},
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"machine": {
"assetid": 1,
"controllermodelid": null,
"controllervendorid": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"islocationonly": false,
"lastmaintenancedate": null,
"machineid": 1,
"machinetypeid": null,
"maintenanceintervaldays": null,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"nextmaintenancedate": null,
"requiresmanualconfig": false,
"vendorid": null
},
"maintenancereference": null,
"mapverifiedat": null,
"mapx": 100,
"mapy": 100,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": 100,
"ownmapy": 100,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "machine_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-machines"
],
"summary": "Update machine (both Asset and Machine records).",
"description": "Update machine (both Asset and Machine records).\n\n**Auth:** permission:machines.edit\n\n**Params:** path: machine_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/machines/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "machine_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: machine_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/machines/by-asset/{asset_id}": {
"get": {
"tags": [
"plugin-machines"
],
"summary": "Get machine data by asset ID.",
"description": "Get machine data by asset ID.\n\n**Auth:** permission:machines.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/machines/by-asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/machines/dashboard/outofservice": {
"get": {
"tags": [
"plugin-machines"
],
"summary": "Machines whose status says they are not running.",
"description": "Machines whose status says they are not running.\n\n**Auth:** permission:machines.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/machines/dashboard/outofservice -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/machines/dashboard/summary": {
"get": {
"tags": [
"plugin-machines"
],
"summary": "Get machine dashboard summary data.",
"description": "Get machine dashboard summary data.\n\n**Auth:** permission:machines.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/machines/dashboard/summary -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"bystatus": [
{
"count": 1,
"status": "In Use"
}
],
"bytype": [],
"total": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/machines/types": {
"get": {
"tags": [
"plugin-machines"
],
"summary": "List all machine types.",
"description": "List all machine types.\n\n**Auth:** permission:machines.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/machines/types -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-machines"
],
"summary": "Create a new machine type.",
"description": "Create a new machine type.\n\n**Auth:** permission:machines.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/machines/types -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/machines/types/{type_id}": {
"delete": {
"tags": [
"plugin-machines"
],
"summary": "Delete a machine type. Refused if any asset still uses it.",
"description": "Delete a machine type. Refused if any asset still uses it.\n\n**Auth:** permission:machines.delete\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/machines/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-machines"
],
"summary": "Get a single machine type.",
"description": "Get a single machine type.\n\n**Auth:** permission:machines.view\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/machines/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-machines"
],
"summary": "Update a machine type.",
"description": "Update a machine type.\n\n**Auth:** permission:machines.edit\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/machines/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/network": {
"get": {
"tags": [
"plugin-network"
],
"summary": "List all network devices with filtering and pagination.",
"description": "List all network devices with filtering and pagination.\n\n**Auth:** permission:network.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/network -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assetid": 1,
"assetnumber": "NET-1",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "network_device",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"ipaddress": "<redacted:host>",
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"networkdevice": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"firmwareversion": null,
"hostname": "<redacted:host>",
"isactive": true,
"ismanaged": false,
"ispoe": false,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"networkdeviceid": 1,
"networkdevicetypeid": 1,
"networkdevicetypename": "Switch",
"portcount": null,
"rackunit": null,
"vendorid": 1,
"vendorname": "Cisco"
},
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "assetnumber",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "businessunit_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "dir",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "asc"
}
},
{
"name": "location_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "managed",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "poe",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "sort",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "hostname"
}
},
{
"name": "type_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "typeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "vendor_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "vendorid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-network"
],
"summary": "Create new network device (creates both Asset and NetworkDevice records).",
"description": "Create new network device (creates both Asset and NetworkDevice records).\n\n**Auth:** permission:network.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/network -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "APNL-Dock-Door-4",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "network_device",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"ipaddress": "<redacted:host>",
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "Dock Door 4",
"networkdevice": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"firmwareversion": null,
"hostname": "<redacted:host>",
"isactive": true,
"ismanaged": false,
"ispoe": false,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"networkdeviceid": 1,
"networkdevicetypeid": 1,
"networkdevicetypename": "Access Panel",
"portcount": null,
"rackunit": null,
"vendorid": null
},
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
},
"message": "Network device created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"assetnumber": "SW-CORE-01",
"hostname": "<redacted:host>",
"ipaddress": "<redacted:host>",
"name": "Core switch"
}
}
}
}
}
},
"/api/network/{device_id}": {
"delete": {
"tags": [
"plugin-network"
],
"summary": "Delete (soft delete) network device.",
"description": "Delete (soft delete) network device.\n\n**Auth:** permission:network.delete\n\n**Params:** path: device_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/network/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "device_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-network"
],
"summary": "Get a single network device with full details.",
"description": "Get a single network device with full details.\n\n**Auth:** permission:network.view\n\n**Params:** path: device_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "AST-networkdevice",
"assettypecolor": null,
"assettypeid": 3,
"assettypename": "network_device",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": "GL-2",
"ipaddress": "<redacted:host>",
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": "MNT-2",
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"networkdevice": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"firmwareversion": null,
"hostname": "<redacted:host>",
"isactive": true,
"ismanaged": false,
"ispoe": false,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"networkdeviceid": 1,
"networkdevicetypeid": null,
"portcount": null,
"rackunit": null,
"vendorid": null
},
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "device_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-network"
],
"summary": "Update network device (both Asset and NetworkDevice records).",
"description": "Update network device (both Asset and NetworkDevice records).\n\n**Auth:** permission:network.edit\n\n**Params:** path: device_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/network/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "AST-networkdevice",
"assettypecolor": null,
"assettypeid": 3,
"assettypename": "network_device",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": "GL-2",
"ipaddress": "<redacted:host>",
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": "MNT-2",
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"networkdevice": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"firmwareversion": null,
"hostname": "<redacted:host>",
"isactive": true,
"ismanaged": false,
"ispoe": false,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"networkdeviceid": 1,
"networkdevicetypeid": null,
"portcount": null,
"rackunit": null,
"vendorid": null
},
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"serialnumber": "<redacted:host>",
"statusid": 1
},
"message": "Network device updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "device_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: device_id (int); body: JSON (fields not yet documented)"
},
"example": {
"gaugelabreference": "GL-2",
"maintenancereference": "MNT-2"
}
}
}
}
}
},
"/api/network/by-asset/{asset_id}": {
"get": {
"tags": [
"plugin-network"
],
"summary": "Get network device data by asset ID.",
"description": "Get network device data by asset ID.\n\n**Auth:** permission:network.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/by-asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/network/by-hostname/{hostname}": {
"get": {
"tags": [
"plugin-network"
],
"summary": "Get network device by hostname.",
"description": "Get network device by hostname.\n\n**Auth:** permission:network.view\n\n**Params:** path: hostname (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/by-hostname/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "hostname",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/network/dashboard/summary": {
"get": {
"tags": [
"plugin-network"
],
"summary": "Get network device dashboard summary data.",
"description": "Get network device dashboard summary data.\n\n**Auth:** permission:network.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/dashboard/summary -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"bytype": [],
"byvendor": [],
"nonpoe": 0,
"poe": 0,
"total": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/network/subnets": {
"get": {
"tags": [
"plugin-network"
],
"summary": "List all subnets with filtering and pagination.",
"description": "List all subnets with filtering and pagination.\n\n**Auth:** permission:network.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/subnets -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "type",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "vlanid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-network"
],
"summary": "Create a new subnet.",
"description": "Create a new subnet.\n\n**Auth:** permission:network.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/network/subnets -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"broadcastaddress": null,
"cidr": "<redacted:address>",
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"dhcpenabled": true,
"dhcprangeend": null,
"dhcprangestart": null,
"dns1": null,
"dns2": null,
"gatewayip": null,
"isactive": true,
"locationid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "Attached",
"networkaddress": null,
"subnetid": 1,
"subnetmask": null,
"subnettype": null,
"vlanid": 1,
"vlanname": "In use",
"vlannumber": 77
},
"message": "Subnet created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"cidr": "<redacted:address>",
"name": "Attached",
"vlanid": 1
}
}
}
}
}
},
"/api/network/subnets/{subnet_id}": {
"delete": {
"tags": [
"plugin-network"
],
"summary": "Delete (soft delete) a subnet.",
"description": "Delete (soft delete) a subnet.\n\n**Auth:** permission:network.delete\n\n**Params:** path: subnet_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/network/subnets/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "subnet_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-network"
],
"summary": "Get a single subnet plus the network devices whose primary IP falls in its CIDR range.",
"description": "Get a single subnet plus the network devices whose primary IP falls in its CIDR range.\n\n**Auth:** permission:network.view\n\n**Params:** path: subnet_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/subnets/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "subnet_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-network"
],
"summary": "Update a subnet.",
"description": "Update a subnet.\n\n**Auth:** permission:network.edit\n\n**Params:** path: subnet_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/network/subnets/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "subnet_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: subnet_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/network/types": {
"get": {
"tags": [
"plugin-network"
],
"summary": "List all network device types.",
"description": "List all network device types.\n\n**Auth:** permission:network.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/types -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-network"
],
"summary": "Create a new network device type.",
"description": "Create a new network device type.\n\n**Auth:** permission:network.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/network/types -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"color": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"icon": null,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"networkdevicetype": "Door Controller",
"networkdevicetypeid": 1,
"prefix": "DOOR"
},
"message": "Network device type created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"networkdevicetype": "Door Controller",
"prefix": "DOOR"
}
}
}
}
}
},
"/api/network/types/{type_id}": {
"delete": {
"tags": [
"plugin-network"
],
"summary": "Delete a network device type. Refused if any device still uses it.",
"description": "Delete a network device type. Refused if any device still uses it.\n\n**Auth:** permission:network.delete\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/network/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-network"
],
"summary": "Get a single network device type.",
"description": "Get a single network device type.\n\n**Auth:** permission:network.view\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-network"
],
"summary": "Update a network device type.",
"description": "Update a network device type.\n\n**Auth:** permission:network.edit\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/network/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"color": null,
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"icon": null,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"networkdevicetype": "Door Controller",
"networkdevicetypeid": 1,
"prefix": "DR"
},
"message": "Network device type updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
},
"example": {
"prefix": "DR"
}
}
}
}
}
},
"/api/network/vlans": {
"get": {
"tags": [
"plugin-network"
],
"summary": "List all VLANs with filtering and pagination.",
"description": "List all VLANs with filtering and pagination.\n\n**Auth:** permission:network.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/vlans -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "type",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-network"
],
"summary": "Create a new VLAN.",
"description": "Create a new VLAN.\n\n**Auth:** permission:network.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/network/vlans -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000Z",
"description": null,
"isactive": true,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": "VLAN 4094",
"subnetcount": 0,
"vlanid": 1,
"vlannumber": 4094,
"vlantype": null
},
"message": "VLAN created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"name": "VLAN 4094",
"vlannumber": 4094
}
}
}
}
}
},
"/api/network/vlans/{vlan_id}": {
"delete": {
"tags": [
"plugin-network"
],
"summary": "Delete (soft delete) a VLAN.",
"description": "Delete (soft delete) a VLAN.\n\n**Auth:** permission:network.delete\n\n**Params:** path: vlan_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/network/vlans/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "vlan_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-network"
],
"summary": "Get a single VLAN with its subnets.",
"description": "Get a single VLAN with its subnets.\n\n**Auth:** permission:network.view\n\n**Params:** path: vlan_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/network/vlans/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "vlan_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-network"
],
"summary": "Update a VLAN.",
"description": "Update a VLAN.\n\n**Auth:** permission:network.edit\n\n**Params:** path: vlan_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/network/vlans/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "vlan_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: vlan_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/notifications": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "List all notifications with filtering and pagination.",
"description": "List all notifications with filtering and pagination.\n\n**Auth:** permission:notifications.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "current",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "false"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "ticketnumber",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "type_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "typeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-notifications"
],
"summary": "Create a new notification.",
"description": "Create a new notification.\n\n**Auth:** permission:notifications.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/notifications -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"alertfleet": true,
"alertscope": {
"computertype": "CMM PC",
"hostname": [
"<redacted:host>",
"<redacted:host>"
]
},
"alerttimeout": 0,
"appid": null,
"businessunitid": null,
"employeename": "<redacted:person>",
"employeesso": "<redacted:person>",
"enddate": null,
"endtime": null,
"isactive": true,
"iscurrent": true,
"isshopfloor": false,
"link": null,
"linkurl": null,
"message": "Line 3 is down",
"notification": "Line 3 is down",
"notificationid": 1,
"notificationtypeid": 1,
"startdate": "2026-01-01T00:00:00.000000+00:00",
"starttime": "2026-01-01T00:00:00.000000+00:00",
"ticketnumber": null,
"title": "Line 3 is down",
"typecolor": "#d93f3f",
"typename": "Fleet Alert"
},
"message": "Notification created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"alertfleet": true,
"alertscope": {
"computertype": "CMM PC",
"hostname": [
"<redacted:host>",
"<redacted:host>"
]
},
"notification": "Line 3 is down",
"notificationtypeid": 1
}
}
}
}
}
},
"/api/notifications/{notification_id}": {
"delete": {
"tags": [
"plugin-notifications"
],
"summary": "Delete (soft delete) a notification.",
"description": "Delete (soft delete) a notification.\n\n**Auth:** permission:notifications.delete\n\n**Params:** path: notification_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/notifications/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "notification_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-notifications"
],
"summary": "Get a single notification.",
"description": "Get a single notification.\n\n**Auth:** permission:notifications.view\n\n**Params:** path: notification_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "notification_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-notifications"
],
"summary": "Update a notification.",
"description": "Update a notification.\n\n**Auth:** permission:notifications.edit\n\n**Params:** path: notification_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/notifications/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"alertfleet": false,
"alertscope": null,
"alerttimeout": 0,
"appid": null,
"businessunitid": null,
"employeename": "<redacted:person>",
"employeesso": "<redacted:person>",
"enddate": null,
"endtime": null,
"isactive": true,
"iscurrent": true,
"isshopfloor": false,
"link": null,
"linkurl": null,
"message": "Line 3 is down",
"notification": "Line 3 is down",
"notificationid": 1,
"notificationtypeid": 1,
"startdate": "2026-01-01T00:00:00.000000+00:00",
"starttime": "2026-01-01T00:00:00.000000+00:00",
"ticketnumber": null,
"title": "Line 3 is down",
"typecolor": "#d93f3f",
"typename": "Fleet Alert"
},
"message": "Notification updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "notification_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: notification_id (int); body: JSON (fields not yet documented)"
},
"example": {
"alertfleet": null,
"alerttimeout": null
}
}
}
}
}
},
"/api/notifications/active": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "Get currently active notifications for display.",
"description": "Get currently active notifications for display.\n\n**Auth:** permission:notifications.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/active -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"notifications": [],
"total": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/notifications/calendar": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "Get notifications in FullCalendar event format.",
"description": "Get notifications in FullCalendar event format.\n\n**Auth:** permission:notifications.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/calendar -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "end",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "start",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/notifications/dashboard/active": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "Notifications currently showing on the floor.",
"description": "Notifications currently showing on the floor.\n\n**Auth:** permission:notifications.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/dashboard/active -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/notifications/dashboard/summary": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "Get notifications dashboard summary.",
"description": "Get notifications dashboard summary.\n\n**Auth:** permission:notifications.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/dashboard/summary -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"active": 0,
"bytype": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/notifications/employee/{sso}": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "Get recognitions for a specific employee by SSO.",
"description": "Get recognitions for a specific employee by SSO.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** path: sso (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/employee/x\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "sso",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/notifications/shopfloor": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "Get notifications for shopfloor TV dashboard.",
"description": "Get notifications for shopfloor TV dashboard.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/shopfloor\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"configversion": "2b7c2d2f543f",
"current": [
{
"boardcategory": "Current Events",
"boardorder": 50,
"displaystyle": "grid",
"employeename": "<redacted:person>",
"employeepicture": "<redacted:person>",
"employeesso": "<redacted:person>",
"endtime": null,
"isactive": true,
"isshopfloor": true,
"link": null,
"notification": "press down",
"notificationid": 2,
"resolved": false,
"starttime": null,
"ticketnumber": null,
"typecolor": "#17a2b8",
"typename": "Incident"
},
{
"boardcategory": "Current Events",
"boardorder": 30,
"displaystyle": "grid",
"employeename": "<redacted:person>",
"employeepicture": "<redacted:person>",
"employeesso": "<redacted:person>",
"endtime": null,
"isactive": true,
"isshopfloor": true,
"link": null,
"notification": "retooling",
"notificationid": 1,
"resolved": false,
"starttime": null,
"ticketnumber": null,
"typecolor": "#17a2b8",
"typename": "Change"
}
],
"timestamp": "2026-01-01T00:00:00.000000",
"upcoming": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "businessunit",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/notifications/types": {
"get": {
"tags": [
"plugin-notifications"
],
"summary": "List all notification types.",
"description": "List all notification types.\n\n**Auth:** permission:notifications.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/notifications/types -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"boardcategory": "Alerts",
"boardorder": 100,
"displaystyle": "grid",
"expirydays": null,
"expiryhour": null,
"expiryminute": 0,
"expirymode": "none",
"gracewindowminutes": 0,
"isactive": true,
"notificationtypeid": 1,
"showemployeephoto": "<redacted:person>",
"splitperemployee": "<redacted:person>",
"typecolor": "#17a2b8",
"typedescription": null,
"typename": "Awareness"
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-notifications"
],
"summary": "Create a new notification type.",
"description": "Create a new notification type.\n\n**Auth:** permission:notifications.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/notifications/types -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"boardcategory": "Alerts",
"boardorder": 100,
"displaystyle": "grid",
"expirydays": null,
"expiryhour": null,
"expiryminute": 0,
"expirymode": "none",
"gracewindowminutes": 0,
"isactive": true,
"notificationtypeid": 1,
"showemployeephoto": "<redacted:person>",
"splitperemployee": "<redacted:person>",
"typecolor": "#17a2b8",
"typedescription": null,
"typename": "Awareness"
},
"message": "Notification type created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"boardcategory": "Alerts",
"displaystyle": "grid",
"typename": "Awareness"
}
}
}
}
}
},
"/api/notifications/types/{type_id}": {
"patch": {
"tags": [
"plugin-notifications"
],
"summary": "Update a notification type, including its auto-expiry rule.",
"description": "Update a notification type, including its auto-expiry rule.\n\n**Auth:** permission:notifications.create\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/notifications/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"boardcategory": "Alerts",
"boardorder": 100,
"displaystyle": "grid",
"expirydays": null,
"expiryhour": null,
"expiryminute": 0,
"expirymode": "none",
"gracewindowminutes": 0,
"isactive": true,
"notificationtypeid": 1,
"showemployeephoto": "<redacted:person>",
"splitperemployee": "<redacted:person>",
"typecolor": "#17a2b8",
"typedescription": null,
"typename": "Awareness"
},
"message": "Notification type updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": false,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
},
"example": {
"boardcategory": "Alerts"
}
}
}
}
},
"put": {
"tags": [
"plugin-notifications"
],
"summary": "Update a notification type, including its auto-expiry rule.",
"description": "Update a notification type, including its auto-expiry rule.\n\n**Auth:** permission:notifications.create\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/notifications/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"boardcategory": "Alerts",
"boardorder": 100,
"displaystyle": "grid",
"expirydays": null,
"expiryhour": null,
"expiryminute": 0,
"expirymode": "none",
"gracewindowminutes": 0,
"isactive": true,
"notificationtypeid": 1,
"showemployeephoto": "<redacted:person>",
"splitperemployee": "<redacted:person>",
"typecolor": "#17a2b8",
"typedescription": null,
"typename": "Awareness"
},
"message": "Notification type updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
},
"example": {
"boardcategory": "Alerts"
}
}
}
}
}
},
"/api/printers": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "List all printers with filtering and pagination.",
"description": "List all printers with filtering and pagination.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"assetid": 1,
"assetnumber": "PR-1",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "printer",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"ipaddress": "<redacted:host>",
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"printer": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"installpath": null,
"isactive": true,
"iscolor": false,
"iscsf": false,
"isduplex": false,
"isnetwork": true,
"modelname": "ZT411",
"modelnumberid": 1,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"pin": null,
"printerid": 1,
"printertypeid": 1,
"printertypename": "Thermal",
"sharename": null,
"vendorid": null,
"windowsname": null
},
"serialnumber": "<redacted:host>",
"statusid": 1
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "assetnumber",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "businessunit_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "businessunitid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "dir",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "asc"
}
},
{
"name": "location_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "locationid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "sort",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "hostname"
}
},
{
"name": "type_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "typeid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "vendor_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "vendorid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-printers"
],
"summary": "Create new printer (creates both Asset and Printer records).",
"description": "Create new printer (creates both Asset and Printer records).\n\n**Auth:** permission:printers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/printers -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "SpoolsInspection-Xerox",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "printer",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"printer": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"installpath": null,
"isactive": true,
"iscolor": false,
"iscsf": false,
"isduplex": false,
"isnetwork": true,
"modelname": "VersaLink C7125",
"modelnumberid": 1,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"pin": null,
"printerid": 1,
"printertypeid": null,
"sharename": null,
"vendorfrommodel": true,
"vendorid": null,
"vendorname": "Xerox",
"windowsname": null
},
"serialnumber": "<redacted:host>",
"statusid": 1
},
"message": "Printer created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"assetnumber": "CSF01-Materials-HP",
"hostname": "<redacted:host>",
"installpath": "<redacted:sharepath>",
"mapx": 120,
"mapy": 240
}
}
}
}
}
},
"/api/printers/{printer_id}": {
"delete": {
"tags": [
"plugin-printers"
],
"summary": "Delete (soft delete) printer.",
"description": "Delete (soft delete) printer.\n\n**Auth:** permission:printers.delete\n\n**Params:** path: printer_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/printers/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "printer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-printers"
],
"summary": "Get a single printer with full details.",
"description": "Get a single printer with full details.\n\n**Auth:** permission:printers.view\n\n**Params:** path: printer_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "PR-2001",
"assettypecolor": null,
"assettypeid": 1,
"assettypename": "printer",
"businessunitid": null,
"communications": [],
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"drivers": [],
"gaugelabreference": null,
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": null,
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"printer": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"imageurl": "/api/models/images/model-1.png",
"installpath": null,
"isactive": true,
"iscolor": false,
"iscsf": false,
"isduplex": false,
"isnetwork": true,
"modelname": "IMG-MODEL-1",
"modelnumberid": 1,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"pin": null,
"printerid": 1,
"printertypeid": null,
"sharename": null,
"vendorid": null,
"windowsname": null
},
"serialnumber": "<redacted:host>",
"statusid": 1
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "printer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-printers"
],
"summary": "Update printer (both Asset and Printer records).",
"description": "Update printer (both Asset and Printer records).\n\n**Auth:** permission:printers.edit\n\n**Params:** path: printer_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/printers/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "AST-printer",
"assettypecolor": null,
"assettypeid": 2,
"assettypename": "printer",
"businessunitid": null,
"createdby": "<redacted:person>",
"createddate": "2026-01-01T00:00:00.000000Z",
"deletedby": null,
"deleteddate": null,
"gaugelabreference": "GL-2",
"isactive": true,
"levelid": null,
"locationcode": null,
"locationid": null,
"maintenancereference": "MNT-2",
"mapverifiedat": null,
"mapx": null,
"mapy": null,
"modifiedby": "<redacted:person>",
"modifieddate": "2026-01-01T00:00:00.000000Z",
"name": null,
"notes": null,
"ownlevelid": null,
"ownlocationid": null,
"ownmapx": null,
"ownmapy": null,
"pluginid": 1,
"printer": {
"assetid": 1,
"createddate": "2026-01-01T00:00:00.000000Z",
"hostname": "<redacted:host>",
"installpath": null,
"isactive": true,
"iscolor": false,
"iscsf": false,
"isduplex": false,
"isnetwork": true,
"modelnumberid": null,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"pin": null,
"printerid": 1,
"printertypeid": null,
"sharename": null,
"vendorid": null,
"windowsname": null
},
"serialnumber": "<redacted:host>",
"statusid": 1
},
"message": "Printer updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "printer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: printer_id (int); body: JSON (fields not yet documented)"
},
"example": {
"gaugelabreference": "GL-2",
"maintenancereference": "MNT-2"
}
}
}
}
}
},
"/api/printers/{printer_id}/supplies": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Get supply levels from Zabbix (real-time lookup).",
"description": "Get supply levels from Zabbix (real-time lookup).\n\n**Auth:** permission:printers.view\n\n**Params:** path: printer_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/1/supplies -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "printer_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/printers/assignments/for-asset/{asset_id}": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "What THIS asset is assigned, without inheritance.",
"description": "What THIS asset is assigned, without inheritance.\n\n**Auth:** permission:printers.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/assignments/for-asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 4,
"defaultprinterassetid": null,
"printerassetids": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-printers"
],
"summary": "Reconcile one asset's whole printer assignment in a single call.",
"description": "Reconcile one asset's whole printer assignment in a single call.\n\n**Auth:** permission:printers.edit\n\n**Params:** path: asset_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/printers/assignments/for-asset/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 3,
"defaultprinterassetid": 4,
"printerassetids": [
4,
5
]
},
"message": "Printer assignment updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: asset_id (int); body: JSON (fields not yet documented)"
},
"example": {
"defaultprinterassetid": 4,
"printerassetids": [
4,
5
]
}
}
}
}
}
},
"/api/printers/assignments/seed-from-observed/{asset_id}": {
"post": {
"tags": [
"plugin-printers"
],
"summary": "Write what a PC observed as the assignment of the asset in the path.",
"description": "Write what a PC observed as the assignment of the asset in the path.\n\n**Auth:** permission:printers.edit\n\n**Params:** path: asset_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/printers/assignments/seed-from-observed/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: asset_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/printers/by-asset/{asset_id}": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Get printer data by asset ID.",
"description": "Get printer data by asset ID.\n\n**Auth:** permission:printers.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/by-asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/printers/dashboard/summary": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Get printer dashboard summary data.",
"description": "Get printer dashboard summary data.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/dashboard/summary -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"bytype": [],
"byvendor": [],
"criticalsupplies": 0,
"lowsupplies": 0,
"online": 0,
"total": 0,
"totalprinters": 0
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/printers/dashboard/supplies": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Printers needing a cartridge, flattened to one row per printer.",
"description": "Printers needing a cartridge, flattened to one row per printer.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/dashboard/supplies -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"rows": [
{
"iscritical": true,
"levelid": null,
"location": "Shop floor",
"mapx": null,
"mapy": null,
"printerid": 2,
"printername": "Bravo",
"supplies": [
{
"level": "critical",
"text": "Black Toner 0%",
"title": "No part number on file for this model"
}
],
"worstremaining": 0
},
{
"iscritical": true,
"levelid": null,
"location": "Shop floor",
"mapx": null,
"mapy": null,
"printerid": 3,
"printername": "Charlie",
"supplies": [
{
"level": "critical",
"text": "Black Toner 2%",
"title": "No part number on file for this model"
}
],
"worstremaining": 2
},
{
"iscritical": true,
"levelid": null,
"location": "Shop floor",
"mapx": null,
"mapy": null,
"printerid": 1,
"printername": "Alpha",
"supplies": [
{
"level": "critical",
"text": "Black Toner 4%",
"title": "No part number on file for this model"
}
],
"worstremaining": 4
},
"<trimmed for the example: 1 more>"
],
"unavailable": null
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/printers/drivers": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "List printer drivers. ?active=false includes inactive ones.",
"description": "List printer drivers. ?active=false includes inactive ones.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/drivers -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
}
]
},
"post": {
"tags": [
"plugin-printers"
],
"summary": "UNDOCUMENTED: printers_asset.create_driver has no docstring.",
"description": "UNDOCUMENTED: printers_asset.create_driver has no docstring.\n\n**Auth:** permission:printers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/printers/drivers -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"description": null,
"driverid": 1,
"drivername": "HP Universal Printing PCL 6",
"isactive": true,
"location": "<redacted:sharepath>",
"modelname": null,
"modelnumberid": null,
"name": "HP universal",
"vendorid": 1
},
"message": "Driver created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"drivername": "HP Universal Printing PCL 6",
"location": "<redacted:sharepath>",
"name": "HP universal",
"vendorid": 1
}
}
}
}
}
},
"/api/printers/drivers/{driver_id}": {
"delete": {
"tags": [
"plugin-printers"
],
"summary": "UNDOCUMENTED: printers_asset.delete_driver has no docstring.",
"description": "UNDOCUMENTED: printers_asset.delete_driver has no docstring.\n\n**Auth:** permission:printers.delete\n\n**Params:** path: driver_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/printers/drivers/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "driver_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-printers"
],
"summary": "UNDOCUMENTED: printers_asset.update_driver has no docstring.",
"description": "UNDOCUMENTED: printers_asset.update_driver has no docstring.\n\n**Auth:** permission:printers.edit\n\n**Params:** path: driver_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/printers/drivers/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"description": null,
"driverid": 1,
"drivername": "Xerox Global Print Driver PCL6",
"isactive": true,
"location": "<redacted:sharepath>",
"modelname": null,
"modelnumberid": null,
"name": "Xerox universal",
"vendorid": 2
},
"message": "Driver updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "driver_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: driver_id (int); body: JSON (fields not yet documented)"
},
"example": {
"drivername": "Xerox Global Print Driver PCL6",
"vendorid": 2
}
}
}
}
}
},
"/api/printers/for-host/{hostname}": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Printers assigned to a PC, by hostname, with what it takes to install one.",
"description": "Printers assigned to a PC, by hostname, with what it takes to install one.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** path: hostname (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/for-host/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "1001",
"defaultprinterid": null,
"hostname": "<redacted:host>",
"printers": [
{
"assetid": 4,
"driverid": null,
"driverlocation": null,
"drivername": null,
"hostname": "<redacted:host>",
"inheritedfromassetid": 3,
"installpath": null,
"ipaddress": "<redacted:host>",
"isdefault": false,
"port": null,
"printerid": 1,
"queuename": "PRINTER-A",
"sharename": null,
"windowsname": "PRINTER-A"
},
{
"assetid": 5,
"driverid": null,
"driverlocation": null,
"drivername": null,
"hostname": "<redacted:host>",
"inheritedfromassetid": 3,
"installpath": null,
"ipaddress": "<redacted:host>",
"isdefault": false,
"port": null,
"printerid": 2,
"queuename": "PRINTER-B",
"sharename": null,
"windowsname": "PRINTER-B"
},
{
"assetid": 6,
"driverid": null,
"driverlocation": null,
"drivername": null,
"hostname": "<redacted:host>",
"inheritedfromassetid": 3,
"installpath": null,
"ipaddress": "<redacted:host>",
"isdefault": false,
"port": null,
"printerid": 3,
"queuename": "PRINTER-C",
"sharename": null,
"windowsname": "PRINTER-C"
}
],
"source": "inherited"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "hostname",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/printers/install-batch": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Generate a Windows .bat that installs the selected printers.",
"description": "Generate a Windows .bat that installs the selected printers.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/install-batch -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "printerids",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/printers/install-list": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Flat, unpaginated list of network printers for the printer installer.",
"description": "Flat, unpaginated list of network printers for the printer installer.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/install-list -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"hostname": "<redacted:host>",
"installpath": "<redacted:sharepath>",
"ipaddress": "<redacted:host>",
"iscsf": false,
"levelid": null,
"locationname": null,
"machinenumber": "CSF01-Materials-HP",
"mapx": 120,
"mapy": 240,
"modelnumber": null,
"name": "CSF01-Materials-HP",
"printerid": 1,
"sharename": null,
"vendorname": "",
"windowsname": null
}
],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/printers/lookup": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Find a printer by IP or FQDN. Parity with the classic printerlookup.asp.",
"description": "Find a printer by IP or FQDN. Parity with the classic printerlookup.asp.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/lookup -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "fqdn",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "ip",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/printers/lowsupplies": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Get printers with low or critical supply levels.",
"description": "Get printers with low or critical supply levels.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/lowsupplies -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"printers": [],
"summary": {
"critical": 0,
"low": 0,
"total_checked": 0
}
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/printers/models": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "List models with a supply count, for the supply-management picker.",
"description": "List models with a supply count, for the supply-management picker.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/models -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [
{
"modelnumber": "TestModel C999",
"modelnumberid": 1,
"supplycount": 1,
"vendor": "TestVendor",
"vendorid": 1
}
],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 1,
"totalpages": 1
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "vendor_id",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "vendorid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "withsupplies",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": ""
}
}
]
}
},
"/api/printers/models/{modelnumberid}/supplies": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "List all supplies mapped to a model.",
"description": "List all supplies mapped to a model.\n\n**Auth:** permission:printers.view\n\n**Params:** path: modelnumberid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/models/1/supplies -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"modelnumber": "TestModel C999",
"modelnumberid": 1,
"supplies": [
{
"capacitytier": "standard",
"color": "black",
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"marketingname": "414A Black",
"modelnumber": "TestModel C999",
"modelnumberid": 1,
"modelsupplyid": 1,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"pageyield": 2400,
"partnumber": "W2020A",
"supplytype": "toner"
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "modelnumberid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-printers"
],
"summary": "Add a supply to a model.",
"description": "Add a supply to a model.\n\n**Auth:** permission:printers.create\n\n**Params:** path: modelnumberid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/printers/models/1/supplies -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"capacitytier": "standard",
"color": "black",
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"marketingname": "414A Black",
"modelnumber": "TestModel C999",
"modelnumberid": 1,
"modelsupplyid": 1,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"pageyield": 2400,
"partnumber": "W2020A",
"supplytype": "toner"
},
"message": "Supply added",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "modelnumberid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: modelnumberid (int); body: JSON (fields not yet documented)"
},
"example": {
"capacitytier": "standard",
"color": "black",
"marketingname": "414A Black",
"pageyield": 2400,
"partnumber": "W2020A",
"supplytype": "toner"
}
}
}
}
}
},
"/api/printers/observed/{hostname}": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "What a host last reported, each queue judged against what it is assigned.",
"description": "What a host last reported, each queue judged against what it is assigned.\n\n**Auth:** permission:printers.view\n\n**Params:** path: hostname (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/observed/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "hostname",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/printers/observed/for-asset/{asset_id}": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "The same comparison, reached from an asset page: one block per host.",
"description": "The same comparison, reached from an asset page: one block per host.\n\n**Auth:** permission:printers.view\n\n**Params:** path: asset_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/observed/for-asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assetid": 1,
"assetnumber": "1001",
"hosts": [
{
"assetid": 1,
"assetnumber": "1001",
"hostname": "<redacted:host>",
"observedat": "2026-01-01T00:00:00.000000",
"queues": [
{
"classification": "extra",
"driftfields": [],
"drivername": "HP Universal Printing PS",
"expecteddrivername": null,
"expectedportaddress": null,
"expectedqueuename": null,
"inheritedfromassetid": null,
"isassigneddefault": false,
"isdefault": true,
"isshared": false,
"portaddress": "<redacted:address>",
"portname": "IP_10.20.0.11",
"printerassetid": 5,
"printerid": 1,
"printername": "Bay label printer",
"queuename": "PRINTER-A"
},
{
"classification": "extra",
"driftfields": [],
"drivername": "HP Universal Printing PS",
"expecteddrivername": null,
"expectedportaddress": null,
"expectedqueuename": null,
"inheritedfromassetid": null,
"isassigneddefault": false,
"isdefault": false,
"isshared": false,
"portaddress": "<redacted:address>",
"portname": "IP_10.20.0.12",
"printerassetid": 6,
"printerid": 2,
"printername": "Bay laser printer",
"queuename": "PRINTER-B"
},
{
"classification": "unknown",
"driftfields": [],
"drivername": "HP Universal Printing PS",
"expecteddrivername": null,
"expectedportaddress": null,
"expectedqueuename": null,
"inheritedfromassetid": null,
"isassigneddefault": false,
"isdefault": false,
"isshared": false,
"portaddress": "<redacted:address>",
"portname": "IP_10.20.0.99",
"printerassetid": null,
"printerid": null,
"printername": null,
"queuename": "Reception Copier"
}
],
"seedcandidate": {
"defaultprinterassetid": 5,
"printerassetids": [
5,
6
],
"skipped": [
{
"drivername": "HP Universal Printing PS",
"isdefault": false,
"portaddress": "<redacted:address>",
"portname": "IP_10.20.0.99",
"queuename": "Reception Copier"
}
]
},
"source": "none",
"summary": {
"drifted": 0,
"extra": 2,
"matching": 0,
"missing": 0,
"unknown": 1
}
}
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "asset_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/printers/pc-default": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Default printer for a PC, by machine (asset) number.",
"description": "Default printer for a PC, by machine (asset) number.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/pc-default -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"printerid": 1,
"windowsname": "HP-CSF04-Materials"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "format",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "machine",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
}
},
"/api/printers/supplies/{modelsupplyid}": {
"delete": {
"tags": [
"plugin-printers"
],
"summary": "Delete a model supply.",
"description": "Delete a model supply.\n\n**Auth:** permission:printers.delete\n\n**Params:** path: modelsupplyid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/printers/supplies/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "Supply deleted",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "modelsupplyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-printers"
],
"summary": "Update a model supply.",
"description": "Update a model supply.\n\n**Auth:** permission:printers.edit\n\n**Params:** path: modelsupplyid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/printers/supplies/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"capacitytier": "high",
"color": "black",
"createddate": "2026-01-01T00:00:00.000000Z",
"isactive": true,
"marketingname": "414X Black",
"modelnumber": "TestModel C999",
"modelnumberid": 1,
"modelsupplyid": 1,
"modifieddate": "2026-01-01T00:00:00.000000Z",
"notes": null,
"pageyield": null,
"partnumber": "W2020A",
"supplytype": "toner"
},
"message": "Supply updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "modelsupplyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: modelsupplyid (int); body: JSON (fields not yet documented)"
},
"example": {
"capacitytier": "high",
"marketingname": "414X Black"
}
}
}
}
}
},
"/api/printers/supplies/forecast": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Days-to-empty and replacement counts per printer.",
"description": "Days-to-empty and replacement counts per printer.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/supplies/forecast -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"available": false,
"cartridges": [],
"days": 90,
"horizondays": 14,
"orderlist": [],
"reason": "Zabbix is not configured or not reachable",
"unestimated": []
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "days",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 90
}
}
]
}
},
"/api/printers/supplies/meta": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "Allowed values for supply type, color, and capacity tier (for the UI).",
"description": "Allowed values for supply type, color, and capacity tier (for the UI).\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/supplies/meta -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"capacitytiers": [
"standard",
"high",
"extrahigh",
"<trimmed for the example: 1 more>"
],
"colors": [
"black",
"cyan",
"magenta",
"<trimmed for the example: 1 more>"
],
"supplytypes": [
"toner",
"drum",
"waste",
"<trimmed for the example: 1 more>"
]
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/printers/supplies/refresh": {
"post": {
"tags": [
"plugin-printers"
],
"summary": "Clear cached Zabbix supply data so the next read pulls fresh values.",
"description": "Clear cached Zabbix supply data so the next read pulls fresh values.\n\n**Auth:** permission:printers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/printers/supplies/refresh -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"message": "Supply cache cleared",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {}
}
}
}
}
},
"/api/printers/types": {
"get": {
"tags": [
"plugin-printers"
],
"summary": "List all printer types.",
"description": "List all printer types.\n\n**Auth:** permission:printers.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/types -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"pagination": {
"hasnext": false,
"hasprev": false,
"page": 1,
"perpage": 20,
"total": 0,
"totalpages": 0
},
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "page",
"in": "query",
"required": false,
"schema": {
"type": "integer",
"default": 1
}
},
{
"name": "per_page",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "perpage",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "search",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-printers"
],
"summary": "Create a new printer type.",
"description": "Create a new printer type.\n\n**Auth:** permission:printers.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/printers/types -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/printers/types/{type_id}": {
"delete": {
"tags": [
"plugin-printers"
],
"summary": "Delete a printer type. Refused if any printer still uses it.",
"description": "Delete a printer type. Refused if any printer still uses it.\n\n**Auth:** permission:printers.delete\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/printers/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-printers"
],
"summary": "Get a single printer type.",
"description": "Get a single printer type.\n\n**Auth:** permission:printers.view\n\n**Params:** path: type_id (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/printers/types/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-printers"
],
"summary": "Update a printer type.",
"description": "Update a printer type.\n\n**Auth:** permission:printers.edit\n\n**Params:** path: type_id (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/printers/types/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "type_id",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: type_id (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/slides/{surface}": {
"get": {
"tags": [
"plugin-slides"
],
"summary": "UNDOCUMENTED: slides.list_slides has no docstring.",
"description": "UNDOCUMENTED: slides.list_slides has no docstring.\n\n**Auth:** permission:slides.view or slides.manage\n\n**Params:** path: surface (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/slides/x -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "surface",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
}
},
"/api/slides/{surface}/{slideid}": {
"patch": {
"tags": [
"plugin-slides"
],
"summary": "UNDOCUMENTED: slides.update_slide has no docstring.",
"description": "UNDOCUMENTED: slides.update_slide has no docstring.\n\n**Auth:** permission:slides.manage\n\n**Params:** path: surface (string), slideid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PATCH http://localhost:5001/api/slides/x/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "surface",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
},
{
"name": "slideid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": false,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: surface (string), slideid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/slides/{surface}/delete": {
"post": {
"tags": [
"plugin-slides"
],
"summary": "UNDOCUMENTED: slides.delete_slides has no docstring.",
"description": "UNDOCUMENTED: slides.delete_slides has no docstring.\n\n**Auth:** permission:slides.manage\n\n**Params:** path: surface (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/slides/x/delete -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "surface",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: surface (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/slides/{surface}/order": {
"post": {
"tags": [
"plugin-slides"
],
"summary": "UNDOCUMENTED: slides.reorder_slides has no docstring.",
"description": "UNDOCUMENTED: slides.reorder_slides has no docstring.\n\n**Auth:** permission:slides.manage\n\n**Params:** path: surface (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/slides/x/order -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "surface",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: surface (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/slides/{surface}/upload": {
"post": {
"tags": [
"plugin-slides"
],
"summary": "UNDOCUMENTED: slides.upload_slides has no docstring.",
"description": "UNDOCUMENTED: slides.upload_slides has no docstring.\n\n**Auth:** permission:slides.manage\n\n**Params:** path: surface (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/slides/x/upload -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "surface",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: surface (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/slides/feed": {
"get": {
"tags": [
"plugin-slides"
],
"summary": "Flat playlist for a surface. NOT wrapped in the success_response envelope so the screensaver's existing parser needs no...",
"description": "Flat playlist for a surface. NOT wrapped in the success_response envelope so the screensaver's existing parser needs no change.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/slides/feed\n```",
"security": [],
"responses": {
"200": {
"description": "Success. This route does NOT return the standard envelope; the example is a transcript of a real response.",
"content": {
"application/json": {
"example": {
"basepath": "/api/slides/img/lobby/",
"interval": 10,
"slides": [],
"success": true,
"surface": "lobby"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"parameters": [
{
"name": "surface",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "lobby"
}
}
]
}
},
"/api/slides/img/{surface}/{filename}": {
"get": {
"tags": [
"plugin-slides"
],
"summary": "Serve a slide image with a path-traversal guard.",
"description": "Serve a slide image with a path-traversal guard.\n\n**Auth:** none (reviewed: named in the public-read or mutation sweep)\n\n**Params:** path: surface (string), filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/slides/img/x/example.png\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "surface",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
},
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/tools/secrets": {
"post": {
"tags": [
"plugin-tools"
],
"summary": "Store an already-encrypted secret and return its token.",
"description": "Store an already-encrypted secret and return its token.\n\n**Auth:** jwt-optional (works signed out; the handler decides what shows)\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/tools/secrets -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
},
{}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"createddate": "2026-01-01T00:00:00.000000",
"expiresat": "2026-01-01T00:00:00.000000",
"token": "<redacted:secret>",
"viewcount": 0,
"viewsremaining": 100
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"ciphertext": "<redacted:token>",
"iv": "MTIzNDU2Nzg5MDEy",
"views": 100
}
}
}
}
}
},
"/api/tools/secrets/{token}": {
"get": {
"tags": [
"plugin-tools"
],
"summary": "Whether a link is still live, WITHOUT spending it.",
"description": "Whether a link is still live, WITHOUT spending it.\n\n**Auth:** none (the unguessable token in the path is the authorisation)\n\n**Params:** path: token (string)\n\n**Example:**\n```\ncurl http://localhost:5001/api/tools/secrets/x\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"available": false
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "token",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-tools"
],
"summary": "Hand over the ciphertext once, then spend the view.",
"description": "Hand over the ciphertext once, then spend the view.\n\n**Auth:** none (the unguessable token in the path is the authorisation; redeeming spends the secret)\n\n**Params:** path: token (string); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/tools/secrets/x -H 'Content-Type: application/json' -d '{}'\n```",
"security": [],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"ciphertext": "<redacted:token>",
"iv": "MTIzNDU2Nzg5MDEy"
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "token",
"in": "path",
"required": true,
"schema": {
"type": "string"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: token (string); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/warranty": {
"get": {
"tags": [
"plugin-warranty"
],
"summary": "List warranties. Filters: ?status=, ?assetid=, ?active=false.",
"description": "List warranties. Filters: ?status=, ?assetid=, ?active=false.\n\n**Auth:** permission:warranty.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/warranty -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "active",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "true"
}
},
{
"name": "assetid",
"in": "query",
"required": false,
"schema": {
"type": "integer"
}
},
{
"name": "servicetag",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "status",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
},
{
"name": "vendor",
"in": "query",
"required": false,
"schema": {
"type": "string"
}
}
]
},
"post": {
"tags": [
"plugin-warranty"
],
"summary": "UNDOCUMENTED: warranty.create_warranty has no docstring.",
"description": "UNDOCUMENTED: warranty.create_warranty has no docstring.\n\n**Auth:** permission:warranty.create\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/warranty -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assets": [],
"enddate": "2026-01-01",
"isactive": true,
"lastcheckeddate": null,
"notes": null,
"prooffilename": null,
"proofurl": null,
"provider": "manual",
"servicelevel": null,
"servicetag": "<redacted:host>",
"startdate": null,
"status": "active",
"statuscolor": "#4CAF50",
"vendor": "Acme",
"warrantyid": 1
},
"message": "Warranty created",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {
"enddate": "2026-01-01",
"servicetag": "<redacted:host>",
"vendor": "Acme"
}
}
}
}
}
},
"/api/warranty/{warrantyid}": {
"delete": {
"tags": [
"plugin-warranty"
],
"summary": "UNDOCUMENTED: warranty.delete_warranty has no docstring.",
"description": "UNDOCUMENTED: warranty.delete_warranty has no docstring.\n\n**Auth:** permission:warranty.delete\n\n**Params:** path: warrantyid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/warranty/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "warrantyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"get": {
"tags": [
"plugin-warranty"
],
"summary": "UNDOCUMENTED: warranty.get_warranty has no docstring.",
"description": "UNDOCUMENTED: warranty.get_warranty has no docstring.\n\n**Auth:** permission:warranty.view\n\n**Params:** path: warrantyid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/warranty/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "warrantyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"put": {
"tags": [
"plugin-warranty"
],
"summary": "UNDOCUMENTED: warranty.update_warranty has no docstring.",
"description": "UNDOCUMENTED: warranty.update_warranty has no docstring.\n\n**Auth:** permission:warranty.edit\n\n**Params:** path: warrantyid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X PUT http://localhost:5001/api/warranty/1 -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"assets": [],
"enddate": null,
"isactive": true,
"lastcheckeddate": null,
"notes": null,
"prooffilename": null,
"proofurl": null,
"provider": "manual",
"servicelevel": null,
"servicetag": "<redacted:host>",
"startdate": null,
"status": "unknown",
"statuscolor": "#9E9E9E",
"vendor": "Acme",
"warrantyid": 1
},
"message": "Warranty updated",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "warrantyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: warrantyid (int); body: JSON (fields not yet documented)"
},
"example": {
"enddate": ""
}
}
}
}
}
},
"/api/warranty/{warrantyid}/proof": {
"delete": {
"tags": [
"plugin-warranty"
],
"summary": "Remove a warranty's proof document.",
"description": "Remove a warranty's proof document.\n\n**Auth:** permission:warranty.edit\n\n**Params:** path: warrantyid (int)\n\n**Example:**\n```\ncurl -X DELETE http://localhost:5001/api/warranty/1/proof -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"enddate": null,
"isactive": true,
"lastcheckeddate": null,
"notes": null,
"prooffilename": null,
"proofurl": null,
"provider": "manual",
"servicelevel": null,
"servicetag": "<redacted:host>",
"startdate": null,
"status": "unknown",
"statuscolor": "#9E9E9E",
"vendor": "Dell",
"warrantyid": 1
},
"message": "Proof removed",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "warrantyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
},
"post": {
"tags": [
"plugin-warranty"
],
"summary": "Upload (or replace) the proof-of-cover document for a warranty.",
"description": "Upload (or replace) the proof-of-cover document for a warranty.\n\n**Auth:** permission:warranty.edit\n\n**Params:** path: warrantyid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/warranty/1/proof -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"enddate": null,
"isactive": true,
"lastcheckeddate": null,
"notes": null,
"prooffilename": "Dell invoice 4471.pdf",
"proofurl": "/api/warranty/proof/warranty-1.pdf",
"provider": "manual",
"servicelevel": null,
"servicetag": "<redacted:host>",
"startdate": null,
"status": "unknown",
"statuscolor": "#9E9E9E",
"vendor": "Dell",
"warrantyid": 1
},
"message": "Proof uploaded",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "warrantyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: warrantyid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/warranty/{warrantyid}/refresh": {
"post": {
"tags": [
"plugin-warranty"
],
"summary": "UNDOCUMENTED: warranty.refresh_warranty has no docstring.",
"description": "UNDOCUMENTED: warranty.refresh_warranty has no docstring.\n\n**Auth:** permission:warranty.edit\n\n**Params:** path: warrantyid (int); body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/warranty/1/refresh -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "warrantyid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "path: warrantyid (int); body: JSON (fields not yet documented)"
}
}
}
}
}
},
"/api/warranty/asset/{assetid}": {
"get": {
"tags": [
"plugin-warranty"
],
"summary": "Warranties covering one asset (for the asset-detail panel).",
"description": "Warranties covering one asset (for the asset-detail panel).\n\n**Auth:** permission:warranty.view\n\n**Params:** path: assetid (int)\n\n**Example:**\n```\ncurl http://localhost:5001/api/warranty/asset/1 -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "assetid",
"in": "path",
"required": true,
"schema": {
"type": "integer"
}
}
]
}
},
"/api/warranty/dashboard/expiring": {
"get": {
"tags": [
"plugin-warranty"
],
"summary": "Warranties running out, and ones that already have.",
"description": "Warranties running out, and ones that already have.\n\n**Auth:** permission:warranty.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/warranty/dashboard/expiring -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": [],
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/warranty/proof/{filename}": {
"get": {
"tags": [
"plugin-warranty"
],
"summary": "Download a proof document.",
"description": "Download a proof document.\n\n**Auth:** permission:warranty.view\n\n**Params:** path: filename (path)\n\n**Example:**\n```\ncurl http://localhost:5001/api/warranty/proof/example.png -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
},
"404": {
"description": "No such record."
}
},
"parameters": [
{
"name": "filename",
"in": "path",
"required": true,
"schema": {
"type": "string",
"description": "may contain slashes"
}
}
]
}
},
"/api/warranty/report": {
"get": {
"tags": [
"plugin-warranty"
],
"summary": "Counts + lists bucketed by derived status.",
"description": "Counts + lists bucketed by derived status.\n\n**Auth:** permission:warranty.view\n\n**Params:** not documented\n\n**Example:**\n```\ncurl http://localhost:5001/api/warranty/report -H \"Authorization: Bearer $TOK\"\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"buckets": {
"active": [],
"expired": [],
"expiring": [],
"unknown": []
},
"counts": {
"active": 0,
"expired": 0,
"expiring": 0,
"unknown": 0
}
},
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
}
}
},
"/api/warranty/sync/dell": {
"post": {
"tags": [
"plugin-warranty"
],
"summary": "Look up every asset serial (= Dell service tag) that has no warranty yet and create warranties for the ones Dell...",
"description": "Look up every asset serial (= Dell service tag) that has no warranty yet and create warranties for the ones Dell recognizes.\n\n**Auth:** permission:warranty.edit\n\n**Params:** body: JSON (fields not yet documented)\n\n**Example:**\n```\ncurl -X POST http://localhost:5001/api/warranty/sync/dell -H \"Authorization: Bearer $TOK\" -H 'Content-Type: application/json' -d '{}'\n```",
"security": [
{
"bearerAuth": []
}
],
"responses": {
"200": {
"description": "Success. Body is the success_response envelope: {status, data, meta}.",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/SuccessEnvelope"
},
"example": {
"data": {
"candidates": 0,
"created": 0,
"matched": 0,
"updated": 0
},
"message": "No PCs need a warranty lookup.",
"meta": {
"requestid": "00000000",
"timestamp": "2026-01-01T00:00:00.000000Z"
},
"status": "success"
}
}
}
},
"default": {
"description": "Error. Body is the error envelope; the code and message are nested under data.error.",
"content": {
"application/json": {
"$ref": "#/components/schemas/ErrorEnvelope"
}
}
},
"401": {
"description": "Missing or invalid credentials."
},
"403": {
"description": "Authenticated, but not permitted."
}
},
"parameters": [
{
"name": "all",
"in": "query",
"required": false,
"schema": {
"type": "string",
"default": "false"
}
}
],
"requestBody": {
"required": true,
"content": {
"application/json": {
"schema": {
"type": "object",
"additionalProperties": true,
"description": "body: JSON (fields not yet documented)"
},
"example": {}
}
}
}
}
}
}
}