Request body
The fields of a request, render modes, features and what a request costs.
| Field | Required | Values | Meaning |
|---|---|---|---|
url |
Yes | Public http or https URL |
Page to retrieve |
render_mode |
Yes | static, js, or auto |
Whether JavaScript rendering is needed |
geo |
No | ISO country code such as US |
Requested exit geography |
device |
No | desktop or mobile |
Requested device profile |
features |
No | Array of up to 8 feature names | Request types enabled on your contract, such as serp_100 |
timeout_ms |
No | Contract-bounded integer | Lowers, never raises, your contract’s budget |
metadata |
No | String-to-string object | Your references, stored for tracing and support |
Use static when the page content exists in the initial HTML. Use js when a browser must execute JavaScript. auto tries static first, because it is cheaper and faster, and automatically re-runs the request with JavaScript rendering if the static attempt fails in a way rendering could fix. Both passes share one deadline and one attempt budget, and you are charged once. The X-Render-Mode header tells you which mode produced the result.
device and features are capability requirements. Each feature name is a lowercase identifier (^[a-z0-9_]{1,32}$), such as premium_proxy, and must be enabled on your contract: features are agreed with Struqter during onboarding and priced into your contract. A request that asks for any feature your contract does not enable – including a name Struqter does not offer – is refused with HTTP 400 and error code FEATURE_NOT_ALLOWED before anything is executed or charged, and is not retryable as-is. Among enabled features, only backends that declare support for every requested feature and the requested device are eligible to serve the request; if none remains, the request fails with HTTP 503 and NO_ELIGIBLE_ROUTE, like any other route with no eligible backend.
What a request costs
Section titled “What a request costs”Each successful request is charged a fixed price per request for its request type, as set in your contract. A request type is:
- the target: the most specific named page type the URL’s hostname and path match, such as an Amazon product page (
/dp/...) or Google Scholar (scholar.google.com), whether or not your contract prices it, otherwise the URL’s domain. When your contract has no rate for that page type, the request is charged the rate your contract has for its domain, or else its standard rate; - the render mode:
staticorjs. Anautorequest that is escalated to JavaScript rendering is charged as ajsrequest; - the features you declare in
features, such asserp_100for Google results with up to 100 results. A request is priced and routed as that type only when you declare it.
Query parameters never affect the price: https://www.google.com/search?q=shoes and the same search asking for results 11 to 20 are the same request type. A request type your contract does not name is charged at your contract’s standard rate. The price is the one in force when you submitted the request, even if it completes after a price change.
Your contract sets separate execution budgets for the two modes: synchronous calls get a short budget because they hold a connection open, and queued jobs get a much longer one. timeout_ms can only lower the applicable budget. Within that budget, each provider attempt is itself capped from the route’s own p95 latency, so a single slow or hanging provider no longer consumes the whole budget and leaves nothing for a fallback attempt; the last attempt the orchestrator can plan for – the one it knows nothing else could follow – still receives all the time that remains.