Create Accountor Login
Docs

The Engine Call Contract

Part of the MountDev Ops Workspace documentation. Updated November 5, 2026

MountDev Ops Workspace documentation | Updated November 5, 2026

Our Commitment

MountDev Ops is built security first. Your business data belongs to you, and you can export all of it at any time. We never use analytics or tracking of any kind inside MountDev Ops.

Every update passes all 2,733 automated checks before it ships, plus screen tests on 9 screen sizes for everything it changes.

What the Contract Is

Some work needs MountDev's shared engine, such as a check that needs a service MountDev runs for every account. The engine keeps nothing about any account. Your workspace calls it, hands over the facts and the keys that one call needs, and gets an answer back. When the call ends, the engine has stored nothing, and your workspace has kept your data and your keys.

This page is the one contract every such call follows. Every capability the engine offers uses the same envelope, the same errors, the same limits, and the same rules for what is never written down.

The Rules in Short

  • Every call carries your account's own token. A token works for one account only.
  • The keys a call needs travel in that call only. The engine never saves them and never logs them.
  • The engine never writes to any account's tables. A capability is given only the facts and keys of the call, with no database and no storage, and returns a result. Your workspace decides what to keep.
  • The engine records only ids and counts. It never records what was in a call.
  • A call that is missing the keys its capability needs is refused before anything runs.
  • Until account tokens are issued (plan item R1.2), every token is refused, so no call can run yet.

Making a Call

A call is one POST from your workspace to the engine over the service connection between them, at /internal/engine/call. It is not a public address. It has an Authorization: Bearer <token> header, a Content-Type: application/json header, and a JSON body, the request envelope.

FieldRequiredWhat it holds
accountYesThe account id the token belongs to, up to 64 letters, digits, _, and -. It must match the token.
capabilityYesThe name of what to run, such as engine/ping: a group, a /, then a name, in lower case.
idempotency_keyYesA key your workspace makes for this one attempt, 8 to 128 letters, digits, ., _, :, and -. See Repeating a Call.
inputsNoThe facts the capability needs, as a JSON object. Empty when left out.
credentialsYesThe keys the capability needs, by name, as a JSON object with at most 32 entries. It is {} for a capability that needs no key, but it must always be sent.

The engine checks the token first, before it reads the body, and then checks that account is the account the token belongs to. Token issuing is a separate step (plan item R1.2); this contract only says how a token is checked.

The Answer

A call that ran returns status 200 and the response envelope:

FieldWhat it holds
oktrue.
resultWhat the capability returned.
usageCounts only, as whole numbers under short lower case names. calls is always there and is 1; a capability adds its own, such as messages. Your workspace turns these into the account's usage.
retrynull when the call finished.
idempotency_keyThe key you sent, so you can match the answer to the attempt.

A call that did not run, or failed, returns the error envelope:

{ "ok": false, "error": { "code": "credentials_missing", "message": "This call needs 2 keys that were not sent." }, "retry": null }

message is one plain sentence. It never repeats a key or the token. retry is null, or { "after_seconds": 30 } (at most 3600) when trying the same call again later can work, and the same number is sent in a Retry-After header. Only a capability that fails because a service it called is busy or away can ask for a retry.

Error Codes

StatuscodeMeaning
400bad_requestThe body could not be read, is not valid JSON, or is not one JSON object.
400credentials_missingcredentials was not sent as an object, has more than 32 entries, or lacks a key the capability needs.
400bad_idempotency_keyThe idempotency key is missing or the wrong shape.
401unauthorizedThe token is missing, wrong, or revoked. Nothing else about the call is read.
403account_mismatchThe token is valid but belongs to a different account than account.
404not_foundNo such capability.
405method_not_allowedThe call was not a POST.
413too_largeThe body is over the size limit.
415unsupported_typeThe call was not sent as JSON.
422bad_inputsThe capability refused the facts. The message says what to fix in plain words.
429rate_limitedToo many calls in a short time. A retry hint is sent.
500handler_failedThe capability failed unexpectedly. The message is always "That did not work. Please try again."
502upstream_unavailableA service the capability called failed. A retry hint may be sent.
503unavailableThe engine cannot take calls right now.

Limits

LimitValue
Request body256 KB
Keys in credentials32
Idempotency key8 to 128 characters
Retry hintUp to 3600 seconds

Repeating a Call

The engine keeps nothing, so it cannot remember an earlier attempt, and it does not drop a repeated call by itself. It passes the idempotency_key to the capability, and a capability that does something outside the engine passes the same key to that service. Your workspace makes one key per attempt, reuses it only to repeat that same attempt after a retry hint, and drops a repeated answer itself. A capability that only reads can ignore the key.

What Is Never Recorded

  • The engine writes one log line per call: the account id, the capability name, the status, the result code, the size of the call in bytes, and the time taken. Both ids are checked against their allowed shape first, so a bad value is logged as -. The line never holds inputs, credentials, the token, or result.
  • A key from credentials never appears in a log line, an error, or a response. Before any answer leaves the engine, every key value that was sent in the same call (3 characters or longer) is replaced with [removed], wherever it appears in the result, its names, and the error message.
  • The engine writes to no table of any account. A capability receives only the account, capability, inputs, credentials, and idempotency key, so it has nothing to write with, and the engine's tests fail if one tries.
  • An account's token is never logged.

The First Capability

engine/ping exists so the contract can be tested end to end. It needs no key. Sent an optional message of text up to 200 characters, it returns { "pong": true, "account": "<the account>", "message": "<the message>" } and counts one message. It reads and writes nothing. Real capabilities are added one at a time, each with its own page, and each follows this contract without exception.

Ask Us Anything

We’d love to hear from you!