Send a scope as data: the structured intake contract
JSON is the canonical payload. XML is a field-for-field mirror of it for shops that think in Xactimate terms. One scope per request, one request per scope. The endpoint answers with a preview by default, builds when you ask it to, and never guesses a code or a price.
The payload
{
"schema_version": "1.0",
"claim": {
"address": "701 Planters Rd", "city": "Tulsa", "state": "OK", "zip": "74101",
"loss_date": "2026-08-14", "loss_type": "hail",
"carrier": "State Farm", "claim_number": "SF-123456"
},
"entries": [
{
"code": "RFG|DRIP",
"description": "Drip edge, painted aluminum",
"qty": 120, "unit": "LF",
"notes": "full perimeter",
"unit_price": 10.00
},
{
"description": "Ridge vent, 4 ft sections",
"qty": 36, "unit": "EA"
}
]
}The same fields as XML, if your system speaks XML. Every field can be an attribute of the claim or entry element, or a child element of it; the parser reads either form and a field sent both ways keeps its attribute value. Grouped blocks (the roof block, the repeated photo reference) stay elements. This example uses attributes:
<scope>
<claim address="701 Planters Rd" city="Tulsa" state="OK" zip="74101" loss_type="hail"/>
<entries>
<entry code="RFG|DRIP" description="Drip edge, painted aluminum" qty="120" unit="LF" unit_price="10.00"/>
<entry description="Ridge vent, 4 ft sections" qty="36" unit="EA"/>
</entries>
</scope>The three rules the endpoint enforces
Quantity is required
A line with no quantity is refused, and the missing field is named on that line. We do not invent a quantity in a payload you sent us.
A price you state is the price
If an entry carries a unit price, that price is used and the row records that it came from the payload. A line with no price is priced from the grounding catalogue and that source is recorded instead.
A code is optional, a guess is never made
An entry can carry a Xactimate code and selector, or just a description. A description is grounded against the reference catalogue; a line that cannot be grounded, or that matches more than one equally well, is flagged for review rather than given a guessed code.
Calling it
POST /api/v1/public/convert/structured # preview of what would be built
POST /api/v1/public/convert/structured?build=1 # 202 + poll_url for the finished ESX
POST /api/v1/public/convert/structured?build=1&sync=1 # the file in the same response
GET /api/v1/public/convert/structured/build/{task_id} # the poll
X-API-Key: <your key>A partner-sandbox key builds inside the request and hands back the file; a production key gets the job to poll (add the sync flag to wait either way). API access is included from the 100-conversion plan up, or with the $49-a-month API and Integrations add-on. The full reference, including error shapes, is at /api/v1/docs. What the conversion does with every line is described on the XML path.
What is not in v1
Batch job sets, webhooks on this route, and an email-in channel are not part of it. Bulk work today runs through the dashboard multi-file upload, and webhooks fire on PDF conversions. Saying so is cheaper than a partner discovering it in production.