How market prices moved over the window
const url = 'https://api.flotera.com/api/v1/marketplaces/market/history?days=7';const options = { method: 'GET', headers: {cookie: '__Host-erm_session=<__Host-erm_session>'}};
try { const response = await fetch(url, options); const data = await response.json(); console.log(data);} catch (error) { console.error(error);}curl --request GET \ --url 'https://api.flotera.com/api/v1/marketplaces/market/history?days=7' \ --cookie __Host-erm_session=<__Host-erm_session>Percentile series per GPU model and marketplace, from the shared hourly market history. Answers “is my price still right”, which the current-snapshot overview cannot: a snapshot shows where the market is, never where it was going.
step says what a point averages — hour for windows up to two days,
day beyond that. The choice follows the window, not a setting: a day
plotted hourly is two points, a month plotted hourly is seven hundred.
buckets says how many hourly samples went into a point. A point built
from one sample and a point built from twenty-four describe different
things, and the price alone does not distinguish them.
rented_share is null when the marketplace does not report occupancy —
as on Vast, whose sample is filtered to free machines. Null and zero
are different answers. For such marketplaces reported_usage_share
carries the platform’s own model-wide busy share instead; the two
series measure different populations and are kept in separate fields
so the provenance stays visible.
Read sources[].price_sample before comparing marketplaces on one
chart: a median over free machines and a median over the whole market
are not the same measurement.
Authorizations
Section titled “Authorizations”Parameters
Section titled “Parameters”Query Parameters
Section titled “Query Parameters”Window length in days, inclusive of today.
Narrow the series to one card class from the catalog ∪ fleet set (see getMarketOverview). Spellings are normalized server-side; a model outside the set is a 422.
Responses
Section titled “Responses”Market history.
object
What one point averages. Follows the window, not a setting.
object
Supported marketplace. The database constrains the same two values, so a third one is a migration rather than a new string.
Start of the bucket, UTC.
How many hourly samples this point averages. A point from one sample and a point from twenty-four describe different things.
Decimal string or null when unknown.
Decimal string or null when unknown.
Decimal string or null when unknown.
Decimal string or null when unknown.
Decimal string or null when unknown.
Busy share by the marketplace’s OWN model-wide aggregate, 0..1. A different population than rented_share: that one is our count over the sampled offers, this one is the platform’s figure for its whole market of the model — which is how Vast occupancy enters the series at all, since its offer sample lists free machines only. Null when the marketplace publishes no such aggregate.
At least one hourly sample in this point hit the marketplace’s page limit, so its percentiles describe a slice rather than the market.
Same sampling caveat as the overview: price_sample must be read before two marketplaces are compared on one chart.
object
A market DATA source — a superset of MarketplaceName. Tier-B venues (tensordock, runpod, akash) feed the price index only: no accounts, no listings, no rentals — see infrastructure/26-market-intelligence.md §3. Execution paths (accounts, links, offers) keep MarketplaceName; a tier-B name is never valid there.
RFC 3339 UTC with microsecond precision, or null.
Which population of machines the prices describe. all includes rented machines; available_only means the query filtered to machines free to rent; reported means there is no sample of ours at all — the venue publishes its own aggregate figures (tier-B sources), computed by an unpublished method.
Without this, comparing marketplaces is misleading. Vast is queried with rentable = true, so its median describes what was NOT taken and skews high; Clore returns the whole market including the attractively-priced machines already rented, and skews low. On live data the gap is a consistent 1.8-2.4x across every card, and how much of it is real cannot be stated. A UI that presents that gap as measured pushes a fleet owner off a marketplace on the strength of a sampling artefact.
How the LAST attempt ended, separate from when data was last fresh: an hour-old market looks identical whether the fetcher is healthy (freshness window) or broken (a run of failures).
rate_limited is not folded into failed — hitting a rate limit is normal traffic shaping against someone else’s API, not a fault, and confusing the two sends the operator to reissue a working key.
Example
{ "step": "hour", "points": [ { "marketplace": "vast" } ], "sources": [ { "marketplace": "vast", "price_sample": "all", "last_fetch_status": "ok" } ]}Missing/invalid credentials (code=unauthorized).
RFC 9457 problem document with a stable machine code.
object
Stable machine-readable error code (03 §2.4).
UUID (v7 for new entities; v4 accepted during migration).
object
JSON Pointer to the offending field.
Example
{ "type": "https://ermeon.com/problems/validation", "code": "unauthorized"}Authenticated but not permitted. code=forbidden — role/scope mismatch; code=feature_not_entitled — the plan does not include the capability; code=account_frozen — the account is frozen and this operation is declared x-ermeon-frozen: deny. The three are deliberately distinct: only the last one is fixed by a top-up (13 §5.6).
RFC 9457 problem document with a stable machine code.
object
Stable machine-readable error code (03 §2.4).
UUID (v7 for new entities; v4 accepted during migration).
object
JSON Pointer to the offending field.
Example
{ "type": "https://ermeon.com/problems/validation", "code": "unauthorized"}Request failed validation (code=validation_failed), with per-field errors.
RFC 9457 problem document with a stable machine code.
object
Stable machine-readable error code (03 §2.4).
UUID (v7 for new entities; v4 accepted during migration).
object
JSON Pointer to the offending field.
Example
{ "type": "https://ermeon.com/problems/validation", "code": "unauthorized"}A dependency the endpoint needs is not configured or is temporarily unavailable (code=unavailable). The rest of the API keeps working — an absent external integration must not take the service down.
RFC 9457 problem document with a stable machine code.
object
Stable machine-readable error code (03 §2.4).
UUID (v7 for new entities; v4 accepted during migration).
object
JSON Pointer to the offending field.
Example
{ "type": "https://ermeon.com/problems/validation", "code": "unauthorized"}