Work-Relatedness Analyze
Status:
stableCategory:work_relatednessAdded:2026-07-01Last reviewed:2026-07-01
Summary
Answer the complete 29 CFR 1904.5 work-relatedness question over one
de-identified injury or illness case, for consumers who need the
work-relatedness determination without the full recordability
composite. Two cited AI analyses run concurrently — the 1904.5
presumption weighed dimension by dimension, and the nine
1904.5(b)(2) exceptions each ruled in or out — then a deterministic
combiner folds them into a single work_relatedness_score with a
components transparency block, a confidence report, and a merged
missing-information list.
⚠ The engine never makes the final determination. The
work_relatedness_scoreis weighted, cited decision support. A qualified professional reviews the dimensions, the exception rulings, and the citations, and makes the work-relatedness call. Treat every response from this endpoint as an input to that judgment, never as a substitute for it.
Endpoint
| Field | Value |
|---|---|
| Method | POST |
| Path | /api/work_relatedness/analyze |
| Full URL | https://engine.tripod-health.com/api/work_relatedness/analyze |
| Authentication | API key (required) |
| Request body | application/json |
| Response body | application/json |
| Idempotent | No (each call may reason slightly differently over the same case) |
| Rate-limited | Yes |
Expect latency in the tens of seconds: the two analyses run concurrently, but each is a substantial AI analysis. Set client timeouts to at least 90 seconds.
Every analysis's generated text passes the engine's outbound
de-identification scan before returning; identifier-shaped output
fails the call with 502 UpstreamError rather than scrubbing
silently.
Purpose
Work-relatedness is the gate every 1904 question passes through
first, and it is often the only question a triage or claims-intake
workflow needs answered. This endpoint gives an early work-related /
not-work-related signal with cited reasoning — grounded only in
stored regulation text and official OSHA guidance — and a
per-dimension breakdown that shows why: the work_relatedness
factor carries one determination per presumption dimension
(geography, mechanism, timing, corroboration, clinical consistency,
pre-existing contribution), and the exceptions factor rules each of
the nine 1904.5(b)(2) exceptions in or out individually.
The full recordability question is bigger than work-relatedness — it
also needs the new-case analysis and the recording criteria. For
that, use
POST /api/recordability/analyze.
Authentication
Standard API-key. Set apikey: $ENGINE_API_KEY on the request. See
authentication.md.
Request
Headers
| Header | Required | Notes |
|---|---|---|
apikey | Yes | Your engine API key. |
Content-Type | Yes | application/json. |
X-Request-ID | No | Echoed back; lets you correlate logs. |
Path parameters
None.
Query parameters
None.
Body
The body is the same de-identified case object every recordability
endpoint accepts, plus an optional lens. Only
case.incident.description and case.injury.description (and their
parent objects) are required — everything else is optional, and every
optional block you populate raises the confidence report's
input_completeness term. Unrecognized fields anywhere in the body
are rejected with 400 ValidationError.
{
"case": {
"incident": {
"description": "Employee slipped on ice in the company parking lot while walking from their parked car to the building entrance at the start of their shift, landing on their right side.",
"incident_date": "2026-06-22",
"reported_date": "2026-06-24",
"location_context": "parking_lot",
"activity_at_time": "walking from personal vehicle to the building entrance before clocking in",
"during_assigned_hours": false
},
"injury": {
"description": "Right shoulder pain and limited range of motion, worsening over two days after the fall.",
"body_part": "right shoulder",
"diagnosis": "rotator cuff strain",
"symptom_onset_date": "2026-06-22",
"onset_type": "acute"
},
"employee": {
"job_title": "warehouse associate",
"job_duties": "Repetitive overhead lifting of boxes up to 50 lbs, pallet loading, operating a manual pallet jack across an 8-hour shift.",
"tenure_bracket": "1-3 years"
},
"treatment": {
"provided": [
"ice pack applied on site",
"prescription naproxen",
"referral to physical therapy"
],
"provider_type": "occupational medicine clinic",
"prescription_issued": true
},
"prior_condition": {
"exists": true,
"description": "Prior right shoulder impingement treated with physical therapy, resolved eight months before this incident.",
"prior_incident_date": "2025-10-15"
},
"statements": [
{
"source": "employee",
"text": "I parked in the employee lot and slipped on a patch of ice near the walkway. I did not think it was serious until the shoulder got worse at work."
},
{
"source": "witness",
"text": "Another employee saw the fall from the entrance and helped the employee up."
}
],
"work_status": {
"days_away": 0,
"restricted_duty": true
}
},
"lens": "safety"
}
Body fields
| Field | Type | Required | Constraints | Description |
|---|---|---|---|---|
case | object | Yes | — | The de-identified case under analysis. |
case.incident | object | Yes | — | What happened. |
case.incident.description | string | Yes | 1–8,000 chars | Free-text narrative of the event or exposure. Refer to people by role, never by name. |
case.incident.incident_date | string (date) | No | YYYY-MM-DD | Date of the event or exposure. Anchors the timing-correlation dimension. |
case.incident.reported_date | string (date) | No | YYYY-MM-DD | When the incident was reported to the employer; the gap from incident_date weighs on corroboration. |
case.incident.location_context | enum | No | on_premises, parking_lot, company_travel, work_from_home, offsite_work, non_work_location, unknown | Where the event occurred; anchors the geographic-presumption dimension. |
case.incident.activity_at_time | string | No | ≤ 1,000 chars | What the employee was doing when the event occurred. |
case.incident.during_assigned_hours | boolean | No | — | Whether the event occurred during assigned working hours. |
case.injury | object | Yes | — | The resulting injury or illness. |
case.injury.description | string | Yes | 1–8,000 chars | Free-text narrative of the injury or illness. |
case.injury.body_part | string | No | ≤ 200 chars | Affected body part. |
case.injury.diagnosis | string | No | ≤ 500 chars | Clinical diagnosis, if one exists. |
case.injury.icd_category | string | No | ≤ 40 chars | ICD category code (structural descriptor, not a patient identifier). |
case.injury.symptom_onset_date | string (date) | No | YYYY-MM-DD | When symptoms first appeared; may differ from incident_date. Anchors timing correlation. |
case.injury.onset_type | enum | No | acute, gradual, unknown | Discrete acute event vs. gradual/cumulative onset. Changes how the timing dimension is weighed — see below. |
case.employee | object | No | — | Structural description of the job, never of the person. |
case.employee.job_title | string | No | ≤ 200 chars | Job title. |
case.employee.job_duties | string | No | ≤ 2,000 chars | What the job actually involves (physical demands, typical tasks); grounds the mechanism-plausibility dimension beyond a bare title. |
case.employee.department | string | No | ≤ 200 chars | Department or work area. |
case.employee.tenure_bracket | string | No | ≤ 40 chars | Tenure as a bracket (e.g. "1-3 years"), never a hire date. |
case.treatment | object | No | — | Treatment provided so far. |
case.treatment.provided | array of string | No | ≤ 25 entries, each 1–1,000 chars | Each treatment provided, one entry per intervention. |
case.treatment.provider_type | string | No | ≤ 200 chars | Type of provider (e.g. "occupational medicine clinic"). |
case.treatment.prescription_issued | boolean | No | — | Whether any prescription was issued. |
case.prior_condition | object | No | — | Pre-existing condition affecting the same region, if any. Grounds the preexisting-contribution dimension. |
case.prior_condition.exists | boolean | No | — | Whether a relevant prior condition exists. |
case.prior_condition.description | string | No | ≤ 4,000 chars | Free-text description of the prior condition and its resolution. |
case.prior_condition.prior_incident_date | string (date) | No | YYYY-MM-DD | Date of the prior incident or episode. |
case.statements | array | No | ≤ 20 entries | Statements gathered during the investigation. Grounds the corroboration dimension. |
case.statements[].source | enum | Yes (per entry) | employee, witness, clinician, employer, injury_report | Who the statement is from, by role. |
case.statements[].text | string | Yes (per entry) | 1–8,000 chars | The statement text. Refer to people by role only. |
case.work_status | object | No | — | Outcome facts (days away, restricted duty, job transfer, loss of consciousness, fatality). Accepted for body compatibility with the recordability endpoints; work-relatedness turns on cause, not outcome. |
case.work_status.days_away | integer | No | 0 ≤ n ≤ 3650 | Days away from work. |
case.work_status.restricted_duty | boolean | No | — | Whether the employee was placed on restricted duty. |
case.work_status.job_transfer | boolean | No | — | Whether the employee was transferred to another job. |
case.work_status.loss_of_consciousness | boolean | No | — | Whether the employee lost consciousness. |
case.work_status.fatality | boolean | No | — | Whether the case was fatal. |
lens | enum | No | safety, occupational_medicine | Reasoning-style flavor only: safety frames the reasoning in exposure/process terms, occupational_medicine in clinical terms. The determination itself never differs by lens. |
De-identification requirement
The case must describe a person structurally, never identifiably.
Free-text fields must not contain names, initials, SSN-shaped values,
email addresses, or phone numbers — refer to people by role
("the employee," "a witness," "the treating clinician"). Precise
calendar dates are normally rejected as potential dates of birth, but
the four named event-date fields — incident_date, reported_date,
symptom_onset_date, and prior_incident_date — are exempt: an
event date does not identify a person, and the gaps between these
dates are exactly what the timing-correlation dimension weighs. A
body containing an identifier returns 400 DeIdentificationViolation
naming the offending field. See the
De-identification contract section
below and
conventions.md.
Response
Success — 200 OK
The response below is a real run over the example case above — a
parking-lot slip with a prior shoulder condition, a genuinely gray
case. For readability, each factor's reasoning is compacted to its
opening sentences, citations are trimmed to two or three per
factor, and repeated items and missing_information entries in the
exceptions factor are trimmed; in production, reasoning runs
several paragraphs per factor, citations run up to 12, and all nine
exceptions are ruled in or out individually. The score, components,
confidence, and all likelihoods, leanings, and certainties are
verbatim, and the six work_relatedness dimension items appear in
full.
{
"work_relatedness_score": 0.697,
"components": {
"presumption_likelihood": 0.82,
"exceptions_likelihood": 0.15,
"exception_weight": 1
},
"confidence": {
"overall": 0.91,
"tier": "high",
"breakdown": {
"input_completeness": 1,
"model_certainty": 0.85
}
},
"factors": {
"work_relatedness": {
"likelihood": 0.82,
"leaning": "yes",
"reasoning": "The core work-relatedness analysis turns on three strong pillars and one substantive exception to evaluate.\n\n**Geographic presumption is satisfied.** The employee was in the company parking lot—a controlled space under the employer's premises.",
"citations": [
{
"source_type": "regulation",
"ref": "1904.5(a)",
"quote": "You must consider an injury or illness to be work-related if an event or exposure in the work environment either caused or contributed to the resulting condition or significantly aggravated a pre-existing injury or illness."
},
{
"source_type": "faq",
"ref": "5-10",
"quote": "Company parking lots are part of the employer's premises and therefore part of the establishment. These areas are under the control of the employer, i.e. those parking areas where the employer can limit access (such as parking lots limited to the employer's employees and visitors)."
},
{
"source_type": "regulation",
"ref": "1904.5(b)(2)(vii)",
"quote": "The injury or illness is caused by a motor vehicle accident and occurs on a company parking lot or company access road while the employee is commuting to or from work."
}
],
"items": [
{
"key": "geographic_presumption",
"determination": "yes",
"note": "Employee was in company parking lot, a controlled employer premise under 1904.5(b)(1) and guidance 5-10. Parking lots where the employer controls access are part of the work environment."
},
{
"key": "mechanism_plausibility",
"determination": "yes",
"note": "Slip on ice while walking to the building entrance is a plausible mechanism. The mechanism directly explains acute right shoulder strain from a fall landing on the right side."
},
{
"key": "timing_correlation",
"determination": "yes",
"note": "Incident and symptom onset both occurred on the day of the fall (acute). The two-day worsening is consistent with soft-tissue injury progression. Reporting two days later is a minor delay but does not undermine the temporal correlation."
},
{
"key": "corroboration",
"determination": "yes",
"note": "Witness employee saw the fall and assisted. Employee's account is consistent and straightforward. Reporting delay of two days is modest and supported by witness observation."
},
{
"key": "clinical_consistency",
"determination": "yes",
"note": "Right shoulder pain and rotator cuff strain are clinically consistent with a fall landing on the right side. Diagnosis and body part match the reported mechanism."
},
{
"key": "preexisting_contribution",
"determination": "unsure",
"note": "Prior right shoulder impingement was resolved approximately eight months before this incident. The acute fall may have caused a new injury or significantly aggravated the prior condition; the record does not clarify whether the current strain represents recurrence or fresh trauma. This ambiguity is minor given the acute mechanism and does not override the strong work-relatedness of the fall event itself."
}
],
"missing_information": [
"Clinical assessment of whether the rotator cuff strain represents a new injury or recurrence/aggravation of the prior impingement",
"Contemporaneous weather records or facility maintenance logs documenting ice or slip hazards in the parking lot on the date of the incident"
],
"certainty": 0.78
},
"exceptions": {
"likelihood": 0.15,
"leaning": "no",
"reasoning": "The employee slipped on ice while walking from their parked personal vehicle to the building entrance before clocking in. Work-relatedness is presumed for injuries in the work environment unless a specific exception applies (1904.5(a)).",
"citations": [
{
"source_type": "regulation",
"ref": "1904.5(b)(2)(vii)",
"quote": "The injury or illness is caused by a motor vehicle accident and occurs on a company parking lot or company access road while the employee is commuting to or from work."
},
{
"source_type": "regulation",
"ref": "1904.5(b)(2)(v)",
"quote": "The injury or illness is solely the result of an employee doing personal tasks (unrelated to their employment) at the establishment outside of the employee's assigned working hours."
},
{
"source_type": "faq",
"ref": "5-11",
"quote": "For purposes of OSHA recordkeeping injuries and illnesses occurring in the work environment are considered work-related. Punching in and out with a time clock does not affect the outcome for determining work-relatedness."
}
],
"items": [
{
"key": "1904.5(b)(2)(i)",
"determination": "no",
"note": "Employee was present as an employee (attending work), not as a member of the general public."
},
{
"key": "1904.5(b)(2)(v)",
"determination": "no",
"note": "Walking to the building entrance at the start of a shift to clock in is a work-related precondition, not a personal errand outside assigned working hours."
},
{
"key": "1904.5(b)(2)(vii)",
"determination": "no",
"note": "The exception applies only to motor vehicle accidents; the employee was walking and slipped on ice, not injured in a vehicle collision."
}
],
"missing_information": [
"Weather conditions or ice-control maintenance records for the date of the incident",
"Whether the employer designates the parking lot as part of its premises and has documented control over it"
],
"certainty": 0.92
}
},
"missing_information": [
"Clinical assessment of whether the rotator cuff strain represents a new injury or recurrence/aggravation of the prior impingement",
"Any prior workers' compensation claim or medical records documenting the resolution of the prior right shoulder impingement eight months earlier",
"Contemporaneous weather records or facility maintenance logs documenting ice or slip hazards in the parking lot on the date of the incident",
"Employer's standard practice or signage regarding parking-lot hazard communication or de-icing protocols"
],
"catalog_version": "0.20.0",
"request_id": "037da8fe-e2ff-49a4-b608-7a97b6b7365d",
"timestamp": "2026-07-02T00:45:02.077128+00:00"
}
How the combiner folds the two analyses
The components block is the transparency view of the deterministic
combiner:
work_relatedness_score = presumption_likelihood × (1 − exception_weight × exceptions_likelihood)
In the run above: 0.82 × (1 − 1 × 0.15) = 0.697. A strong
presumption discounted by a small residual exception likelihood —
the score carries both analyses, and the block lets you verify the
arithmetic yourself.
The six presumption dimensions
The work_relatedness factor's items array carries one
determination per dimension:
| Item key | What it weighs |
|---|---|
geographic_presumption | Was the employee in the work environment as 1904.5(b)(1) defines it when the event or exposure occurred? |
mechanism_plausibility | Can the reported mechanism plausibly produce this injury? Grounded in employee.job_duties — what the job actually involves, not just the title. |
timing_correlation | Do incident_date, symptom_onset_date, and reported_date line up with the reported mechanism? When onset_type is gradual, the analysis weighs the condition against the cumulative exposure window rather than a single event — a carpal-tunnel presentation is not penalized for lacking one incident date. |
corroboration | Do the statements from other sources support the account? A reporting delay weighs on the evidence but is never disqualifying by itself. |
clinical_consistency | Are the diagnosis and body part consistent with the reported mechanism and course? |
preexisting_contribution | Did a prior condition contribute, and does any aggravation by the workplace event qualify as significant under 1904.5(b)(4)? |
The exceptions factor's items array does the same for the nine
1904.5(b)(2) exceptions — one row per exception, keyed by its
regulation reference, each ruled yes, no, or unsure with a
one-row rationale.
Response fields
| Field | Type | Always present | Description |
|---|---|---|---|
work_relatedness_score | number | Yes | 0.000–1.000. Presumption discounted by exceptions per the combiner formula. Decision support for the reviewer, never a determination. |
components | object | Yes | Transparency block: the combiner's inputs. |
components.presumption_likelihood | number | Yes | 0–1. The work_relatedness factor's likelihood. |
components.exceptions_likelihood | number | Yes | 0–1. The exceptions factor's likelihood that some exception applies. |
components.exception_weight | number | Yes | The multiplier the combiner applies to exceptions_likelihood when discounting the presumption. |
confidence | object | Yes | How much to trust this run. |
confidence.overall | number | Yes | 0–1 blended confidence. |
confidence.tier | string | Yes | Banded label for overall (e.g. "high"). |
confidence.breakdown.input_completeness | number | Yes | 0–1. How much of the optional case structure you supplied; every populated optional block raises it. |
confidence.breakdown.model_certainty | number | Yes | 0–1. Aggregated per-factor certainty — the analyses' own read of how much reliable information they had. |
factors | object | Yes | The two full assessments, keyed work_relatedness and exceptions. |
factors.<factor>.likelihood | number | Yes | 0–1 likelihood of the factor's question. |
factors.<factor>.leaning | enum | Yes | yes | no | unsure. |
factors.<factor>.reasoning | string | Yes | The cited analysis narrative — several paragraphs in production. |
factors.<factor>.citations | array | Yes | 1–12 entries; every passage the analysis relied on. |
factors.<factor>.citations[].source_type | enum | Yes | regulation | faq | interpretation | preamble. |
factors.<factor>.citations[].ref | string | Yes | The cited reference (e.g. "1904.5(b)(2)(vii)", FAQ "5-11"). |
factors.<factor>.citations[].quote | string | null | No | The quoted passage, when one was quoted. |
factors.<factor>.items | array | null | No | Per-item determinations: the six presumption dimensions on work_relatedness, the nine 1904.5(b)(2) exceptions on exceptions. |
factors.<factor>.items[].key | string | Yes | The dimension name or exception reference. |
factors.<factor>.items[].determination | enum | Yes | yes | no | unsure. |
factors.<factor>.items[].note | string | null | No | One-row rationale. |
factors.<factor>.missing_information | array of string | Yes | Up to 10 facts that would sharpen this factor. May be empty. |
factors.<factor>.certainty | number | Yes | 0–1. The analysis's own read of how much reliable information it had — distinct from likelihood. |
missing_information | array of string | Yes | Merged, deduplicated union of both factors' lists — an investigation checklist for the case. |
catalog_version | string | Yes | Version of the stored regulation-and-guidance catalog the citations were drawn from. |
request_id | string | Yes | Correlation ID. Echo it in support tickets. |
timestamp | string | Yes | ISO 8601, UTC. |
Status codes
| Code | Meaning | When |
|---|---|---|
200 | OK | Both analyses completed and were combined. |
400 | ValidationError | Body shape, enum violation, over-length field, or an unrecognized field. field names the offender when known. |
400 | DeIdentificationViolation | The body carries an identifier-shaped value — including a precise date outside the four exempt event-date fields. |
401 | Unauthenticated | Missing or invalid API key. |
413 | PayloadTooLarge | Body exceeds 512 KB. |
415 | UnsupportedMediaType | Content-Type is not application/json. |
429 | RateLimited | Per-consumer rate limit exceeded. Respect Retry-After. |
500 | InternalError | Unexpected failure. Report the request_id. |
502 | UpstreamError | An AI analysis failed, or its output failed the outbound safety scan. Safe to retry once. |
504 | UpstreamTimeout | An AI analysis exceeded the engine's time budget. |
Error envelope
All non-2xx responses use the uniform envelope:
{
"timestamp": "2026-07-01T17:32:10.812Z",
"error": "ValidationError",
"message": "Field 'case.injury.onset_type' must be one of: acute, gradual, unknown",
"request_id": "8f2c3b1d-5e4a-4a9c-9b1e-2a7f1d3e4c5b",
"field": "case.injury.onset_type"
}
See errors.md for the full code taxonomy and extras.
Examples
curl
curl -sS -X POST "https://engine.tripod-health.com/api/work_relatedness/analyze" \
--max-time 120 \
-H "apikey: $ENGINE_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"case": {
"incident": {
"description": "Employee slipped on ice in the company parking lot while walking from their parked car to the building entrance at the start of their shift, landing on their right side.",
"incident_date": "2026-06-22",
"reported_date": "2026-06-24",
"location_context": "parking_lot",
"activity_at_time": "walking from personal vehicle to the building entrance before clocking in",
"during_assigned_hours": false
},
"injury": {
"description": "Right shoulder pain and limited range of motion, worsening over two days after the fall.",
"body_part": "right shoulder",
"diagnosis": "rotator cuff strain",
"symptom_onset_date": "2026-06-22",
"onset_type": "acute"
},
"employee": {
"job_title": "warehouse associate",
"job_duties": "Repetitive overhead lifting of boxes up to 50 lbs, pallet loading, operating a manual pallet jack across an 8-hour shift.",
"tenure_bracket": "1-3 years"
},
"treatment": {
"provided": [
"ice pack applied on site",
"prescription naproxen",
"referral to physical therapy"
],
"provider_type": "occupational medicine clinic",
"prescription_issued": true
},
"prior_condition": {
"exists": true,
"description": "Prior right shoulder impingement treated with physical therapy, resolved eight months before this incident.",
"prior_incident_date": "2025-10-15"
},
"statements": [
{
"source": "employee",
"text": "I parked in the employee lot and slipped on a patch of ice near the walkway. I did not think it was serious until the shoulder got worse at work."
},
{
"source": "witness",
"text": "Another employee saw the fall from the entrance and helped the employee up."
}
],
"work_status": {
"days_away": 0,
"restricted_duty": true
}
},
"lens": "safety"
}'
Python (requests)
# Uses the call() helper from quickstart.md; raise its timeout to 120 s
# for this endpoint.
result = call("POST", "/api/work_relatedness/analyze", {
"case": {
"incident": {
"description": "Employee slipped on ice in the company parking lot while walking from their parked car to the building entrance at the start of their shift, landing on their right side.",
"incident_date": "2026-06-22",
"reported_date": "2026-06-24",
"location_context": "parking_lot",
"activity_at_time": "walking from personal vehicle to the building entrance before clocking in",
"during_assigned_hours": False,
},
"injury": {
"description": "Right shoulder pain and limited range of motion, worsening over two days after the fall.",
"body_part": "right shoulder",
"diagnosis": "rotator cuff strain",
"symptom_onset_date": "2026-06-22",
"onset_type": "acute",
},
"employee": {
"job_title": "warehouse associate",
"job_duties": "Repetitive overhead lifting of boxes up to 50 lbs, pallet loading, operating a manual pallet jack across an 8-hour shift.",
"tenure_bracket": "1-3 years",
},
"treatment": {
"provided": [
"ice pack applied on site",
"prescription naproxen",
"referral to physical therapy",
],
"provider_type": "occupational medicine clinic",
"prescription_issued": True,
},
"prior_condition": {
"exists": True,
"description": "Prior right shoulder impingement treated with physical therapy, resolved eight months before this incident.",
"prior_incident_date": "2025-10-15",
},
"statements": [
{
"source": "employee",
"text": "I parked in the employee lot and slipped on a patch of ice near the walkway. I did not think it was serious until the shoulder got worse at work.",
},
{
"source": "witness",
"text": "Another employee saw the fall from the entrance and helped the employee up.",
},
],
"work_status": {
"days_away": 0,
"restricted_duty": True,
},
},
"lens": "safety",
})
print(f"score: {result['work_relatedness_score']}")
print(f"presumption: {result['components']['presumption_likelihood']}")
print(f"exceptions: {result['components']['exceptions_likelihood']}")
for item in result["factors"]["work_relatedness"]["items"]:
print(f"- {item['key']}: {item['determination']}")
Node.js (native fetch) — gradual-onset triage case
A cumulative condition carries no single incident date; set
onset_type: "gradual" and the timing dimension weighs the condition
against the cumulative exposure window instead of demanding an event.
// Uses the call() helper from quickstart.md; raise its timeout to 120 s
// for this endpoint.
const result = await call("POST", "/api/work_relatedness/analyze", {
case: {
incident: {
description:
"Employee reports numbness and tingling in both hands that has built up gradually over several months of assembly-line work; no single triggering event identified.",
reported_date: "2026-06-24",
location_context: "on_premises",
},
injury: {
description:
"Bilateral hand numbness and tingling, worse at night, progressing over roughly three months.",
body_part: "hands and wrists",
onset_type: "gradual",
},
employee: {
job_title: "assembly technician",
job_duties:
"Repetitive small-part assembly with pinch-grip and wrist flexion across an 8-hour shift, approximately 40 cycles per hour.",
},
},
});
console.log("score:", result.work_relatedness_score);
console.log("components:", result.components);
console.log("investigate next:", result.missing_information);
Intended use
- Incident triage: an early work-related / not-work-related signal with cited reasoning, before anyone commits investigation time.
- Claims-intake decision support — the per-dimension breakdown and exception rulings give an intake reviewer a structured starting point with the regulation text one click away.
- Screening which incidents warrant a full recordability run:
triage every incident here, and send the cases that look
work-related to
POST /api/recordability/analyze. - Getting the merged
missing_informationlist as an investigation checklist — run early with what you have, collect what the response names, and re-run richer.
Mistaken use
- Answering the full recordability question. Work-relatedness is one
branch of the 1904.4 tree — recordability also needs the new-case
analysis and the recording criteria. Use
POST /api/recordability/analyzeinstead. - Treating
work_relatedness_scoreas a final or legal determination. It never is. The score is weighted, cited decision support; a qualified professional makes the work-relatedness call. - Reading a low
corroborationortiming_correlationdetermination as "not work-related." A single weak dimension weighs on the evidence — a reporting delay in particular is never disqualifying by itself. Read the score, the reasoning, and the citations together. - Sending
lensexpecting a different answer.lenschanges the reasoning's framing for its reader, never the determination.
De-identification contract
This endpoint enforces both directions of the engine's de-id contract:
- Inbound: the case must describe the person structurally.
Free-text fields (
description,activity_at_time,job_duties,statements[].text, ...) must never contain names, initials, SSN-shaped values, email addresses, or phone numbers — refer to people by role. Precise dates are normally rejected as potential dates of birth; the named event-date fields (incident_date,reported_date,symptom_onset_date,prior_incident_date) are exempt, because an event date does not identify a person — and the gaps between them are exactly what the timing analysis needs. Failures return400 DeIdentificationViolationwithfieldnaming the offender. See conventions.md. - Outbound: every generated
reasoning,note, andmissing_informationstring is scanned for identifier shapes before the response returns. A match fails the call with502 UpstreamError; the engine never silently scrubs.
Debugging
Checklist when a call fails:
- Capture the
request_idfrom the response body (success or error). Every support ticket starts here. 400 DeIdentificationViolation— thefieldextra names the offending path. Check free text for names or initials, and check for precise dates outside the four exempt event-date fields.400 ValidationError— check enum values (location_context,onset_type,statements[].source,lens), field lengths, and for unrecognized fields — the body schema is strict.401 Unauthenticated— confirm theapikeyheader is present and the key is active.429 RateLimited— respect theRetry-Afterheader; back off.502 UpstreamError— an analysis failed or its output failed the outbound safety scan. Safe to retry once; if it persists, file a ticket with therequest_id.504 UpstreamTimeoutor a client-side timeout — this endpoint runs tens of seconds. Confirm your client timeout is at least 90 seconds before assuming the engine failed.
Rate limits
Per-consumer limits are managed at the gateway. See rate-limits.md. See credits.md for how this endpoint is metered.
Related
POST /api/recordability/analyze— the full five-factor recordability composite; same case body.- recordability-factor.md — the single-factor endpoints; same case body, one factor's assessment.
GET /api/regulations/search— search the regulation-and-guidance catalog the citations point into.GET /api/regulations/get— fetch a cited passage by reference to render alongside the reasoning.- conventions.md — de-identification contract, request IDs, timestamp shape.
- errors.md — error envelope and code list.
Change history
| Date | Change |
|---|---|
| 2026-07-01 | Initial publication. |