Loading documentation

Access required

Your account doesn't have access to the documentation. Contact your administrator.

Sign out
Skip to main content

Claim-Cost Classification

Status: beta Category: claimcost Added: 2026-07-06 Last reviewed: 2026-07-06

Summary

Classify the likely cost of a workers' compensation claim from three de-identified inputs — the injury, the body part, and the worker's age. One call returns two independent classifications: a binary cost tier (High / Low) and a three-band cost band (High / Medium / Low). Each carries a confidence and the full probability distribution, so you can apply your own threshold instead of taking the top label as final.

This is a statistical model, not clinical or actuarial advice. It does not set a reserve, price a policy, or make a claim decision — it estimates a cost category from a narrow feature set. Treat the output as one signal among many.

Endpoint

FieldValue
MethodPOST
Path/api/claimcost/classify
Full URLhttps://engine.tripod-health.com/api/claimcost/classify
AuthenticationAPI key (required)
Request bodyapplication/json
Response bodyapplication/json
IdempotentYes (deterministic classifier — the same input yields the same output)
Rate-limitedYes

Purpose

Use this endpoint when you have a coded injury, a coded body part, and an age, and you want a fast cost-category read. It is built to triage or prioritize — to separate the claims likely to run expensive from the ones likely to stay cheap — not to produce a dollar figure.

The two valid input vocabularies are fixed and case-sensitive at the word level. Fetch them from GET /api/claimcost/categories and validate or populate your inputs against that list; an unrecognized value returns 400.

Authentication

Send a valid API key in the apikey header. A missing or unknown key returns 401 Unauthenticated at the gateway before the request reaches the engine. See authentication.

Request

Headers

HeaderRequiredDescription
apikeyYesConsumer API key.
Content-TypeYesMust be application/json.
X-Request-IDNoOptional client-generated correlation ID. If omitted, one is generated and echoed in the X-Request-ID response header.

Path parameters

None.

Query parameters

None.

Body

{
"injury": "strain or tear",
"bodyPart": "low back area",
"age": 47
}

Body fields

FieldTypeRequiredConstraintsDescription
injurystringYesnon-empty, ≤ 200 chars, must match a known categoryThe injury cause/nature. Case-insensitive, but the words must match one of the accepted injuries values verbatim.
bodyPartstringYesnon-empty, ≤ 200 chars, must match a known categoryThe affected body part. Case-insensitive, but the words must match one of the accepted bodyParts values verbatim. Maps to the model's body_part.
ageintegerYes0 ≤ age ≤ 120The worker's age as a whole number of years.

Category matching is exact after case-folding and trimming: "low back area", "Low Back Area", and "LOW BACK AREA" are equivalent, but "lower back" is not a known value and returns 400. Unknown top-level fields are ignored.

De-identification requirement

Like every endpoint, the body is scanned for identifiers inbound. age must be a whole number of years — never a date of birth. A date-shaped value is both wrong for the model and an identifier shape that returns 400 DeIdentificationViolation. Do not add names, dates, record numbers, or free-text notes to the body. See conventions.md.

Response

Success — 200 OK

{
"model": "claimcost",
"version": "0.2.0",
"costTier": {
"prediction": "High",
"confidence": 0.82,
"probabilities": {
"High": 0.82,
"Low": 0.18
}
},
"costBand": {
"prediction": "Medium",
"confidence": 0.54,
"probabilities": {
"High": 0.3,
"Medium": 0.54,
"Low": 0.16
}
}
}

Response fields

FieldTypeAlways presentDescription
modelstringYesThe model that answered (claimcost).
versionstringYesThe model version that produced this result. Reported by the model; expect it to advance as the model is retrained.
costTierobjectYesThe binary cost classification (High / Low).
costTier.predictionstringYesThe winning label: High or Low.
costTier.confidencenumberYesProbability of the winning label, 0.01.0.
costTier.probabilitiesobjectYesFull probability map keyed by label (High, Low); values sum to ~1.0.
costBandobjectYesThe three-band cost classification (High / Medium / Low).
costBand.predictionstringYesThe winning label: High, Medium, or Low.
costBand.confidencenumberYesProbability of the winning label, 0.01.0.
costBand.probabilitiesobjectYesFull probability map keyed by label (High, Medium, Low); values sum to ~1.0.

costTier and costBand are independent classifications from the same inputs, not two views of one score. They can disagree (a Low tier with a Medium band is possible); use whichever granularity fits your use, or both.

There is no request_id or timestamp in the success body; read the X-Request-ID response header to correlate a successful call. Error responses carry both in the envelope.

Status codes

CodeMeaningWhen
200OKClassification succeeded.
400ValidationErrorMissing or empty injury / bodyPart, a value over 200 characters, a non-integer or out-of-range age, or an unrecognized injury / bodyPart category. The field extra names the offender for field-shape errors; an unknown-category message quotes the offending value.
400DeIdentificationViolationThe body contained an identifier shape (e.g. a date supplied for age).
401UnauthenticatedMissing or invalid API key.
402PaymentRequiredInsufficient credits or an exhausted budget. See credits.md.
413PayloadTooLargeBody exceeds the 512 KB limit.
415UnsupportedMediaTypeContent-Type is not application/json.
429RateLimitedPer-consumer rate limit exceeded. See Retry-After.
500InternalErrorUnexpected server-side failure. Include request_id when reporting.
502UpstreamErrorThe model service was unreachable or returned an unexpected shape.
503ServiceUnavailableA required dependency is temporarily unhealthy.
504UpstreamTimeoutThe model call exceeded the engine's budget.

Error envelope

All non-2xx responses use the uniform envelope:

{
"timestamp": "2026-07-06T17:32:10.812Z",
"error": "ValidationError",
"message": "Field 'age' must be between 0 and 120",
"request_id": "8f2c3b1d-5e4a-4a9c-9b1e-2a7f1d3e4c5b",
"field": "age"
}

See errors.md for the full code list.

What a call costs

A successful classification is billed at a fixed per-call credit cost. Unlike /api/ask/run, the price does not vary with input size — this is a fixed-cost route like the analytics endpoints. The exact credits a call spent are returned in the X-Credits-Used header, and the dollar cost in X-Credits-Cost-USD; treat those as the source of truth for what you were charged. See credits.md for the credit model and where to find current per-route costs.

Validating inputs first with the cheap GET /api/claimcost/categories call avoids paying for a classify request that would only 400 on an unknown category.

Examples

curl — success

curl -sS -X POST "https://engine.tripod-health.com/api/claimcost/classify" \
-H "apikey: $ENGINE_API_KEY" \
-H "Content-Type: application/json" \
-d '{"injury":"strain or tear","bodyPart":"low back area","age":47}'

Expected response:

{
"model": "claimcost",
"version": "0.2.0",
"costTier": {
"prediction": "High",
"confidence": 0.82,
"probabilities": { "High": 0.82, "Low": 0.18 }
},
"costBand": {
"prediction": "Medium",
"confidence": 0.54,
"probabilities": { "High": 0.3, "Medium": 0.54, "Low": 0.16 }
}
}

curl — unknown category (400)

curl -sS -X POST "https://engine.tripod-health.com/api/claimcost/classify" \
-H "apikey: $ENGINE_API_KEY" \
-H "Content-Type: application/json" \
-H "X-Request-ID: docs-claimcost-unknown-injury" \
-w "\nHTTP %{http_code}\n" \
-d '{"injury":"lower back","bodyPart":"low back area","age":47}'

Receive (400):

{
"timestamp": "2026-07-06T17:32:10.812Z",
"error": "ValidationError",
"message": "unknown injury: 'LOWER BACK'",
"request_id": "docs-claimcost-unknown-injury"
}

Python (requests)

# Uses the call() helper from quickstart.md.
result = call("POST", "/api/claimcost/classify", body={
"injury": "strain or tear",
"bodyPart": "low back area",
"age": 47,
})
print(result["costTier"]["prediction"], result["costTier"]["confidence"])
print(result["costBand"]["prediction"], result["costBand"]["confidence"])

Node.js (native fetch)

// Uses the call() helper from quickstart.md.
const result = await call("POST", "/api/claimcost/classify", {
injury: "strain or tear",
bodyPart: "low back area",
age: 47,
});
console.log(result.costTier.prediction, result.costTier.confidence);
console.log(result.costBand.prediction, result.costBand.confidence);

TypeScript

interface CostClass {
prediction: string;
confidence: number;
probabilities: Record<string, number>;
}

interface ClaimcostClassifyResponse {
model: string;
version: string;
costTier: CostClass;
costBand: CostClass;
}

const result = await call<ClaimcostClassifyResponse>(
"POST",
"/api/claimcost/classify",
{ injury: "strain or tear", bodyPart: "low back area", age: 47 },
);

Intended use

  • Triage and prioritization — flag the claims most likely to run expensive so they get earlier attention.
  • Bulk scoring of coded injury records where you already hold a known injury cause, body part, and age.
  • Confidence-aware routing — read probabilities and apply your own threshold rather than trusting a narrow-margin top label.

Mistaken use

  • Do not treat the output as a dollar amount or a reserve. It is a cost category, not a figure. Setting a reserve is a human, actuarial decision.
  • Do not guess at category strings. An unlisted value returns 400. Fetch the accepted values from /api/claimcost/categories and match against them.
  • Do not send a date of birth in age. Send a whole number of years. A date trips the de-identification scan (400).
  • Do not use this for free-text questions about a claim. That is /api/ask/run. This endpoint takes a fixed feature set and returns fixed labels.

Debugging

  1. Capture the request_id from the error envelope or the X-Request-ID response header before anything else.
  2. 400 ValidationError with a field. A field-shape problem — injury / bodyPart missing, empty, or too long, or age not a whole number in 0120. Fix the named field.
  3. 400 ValidationError with no field, message unknown injury: / unknown body_part:. The value is not a recognized category. Pull the current list from /api/claimcost/categories.
  4. 400 DeIdentificationViolation. Something identifier-shaped is in the body — most often a date passed for age. Send an integer.
  5. 402 PaymentRequired. Out of credits or budget; see credits.md.
  6. 502 UpstreamError. The model service is unreachable or returned an unexpected shape. Retry with backoff; if it persists, check model-services-health.md and quote the request_id in a ticket.

Rate limits

Per-consumer limits are enforced at the gateway; see rate-limits.md. Responses include the standard RateLimit-* headers.

Change history

DateChange
2026-07-06Initial publication (beta).