/v4/analytics/positions/by-identifier/{chainId}/{identifier}
Get positions by opportunity identifierFetch the latest position for every user in a given opportunity.
Response:
- data[indexingId]: Wrapped positions keyed by indexingId. Each positionGroup carries shared metadata (protocol, action, stateType, globalStates, tokens) and a positions map keyed by positionId. Each position entry carries its user field; multiple users may share the same indexingId positionGroup.
- latest is reported as of the indexing checkpoint: its (blockNumber, blockTimestamp) are advanced to how far indexing has completed (state unchanged through there), never beyond it — so the state is never presented as more current than what's indexed.
- globalStates: at the positionGroup level it holds series descriptors only (type, indexingId) — fetch the values from GET /v4/analytics/global-states. This route returns raw states; it runs no global-state enrichment.
- display.unpricedReason (when valueUsd is absent): which step gave up — no_price (the token mapped but has no daily close at or before that day), no_token_mapped (no declared token denominates the amount, e.g. a market-keyed identifier), unresolved_amount (global-state enrichment produced none), unsupported_state (no valuation rule for the stateType). A price gap and an unsupported shape both read as "no value" without it.
- debt: present and true when the group's amounts are owed, not held (a borrow) — sum values across groups by subtracting these. Set once per group: it follows from the processor.
- positions[positionId].params: position-invariant fields hoisted out of the snapshots, emitted once per position. Shape follows stateType; CLAMM carries tickLower/tickUpper (and salt when the persisted state has one), which is why they are no longer inside each snapshot's state. poolId and tokenId are not emitted at all: poolId is the positionGroup's identifier, and tokenId is the last segment of the positionId key.
- pagination.positionCount: Total number of position entries returned
- pagination.recipientsCount: Number of distinct user addresses across all positions
Examples:
- Latest positions: GET /v4/analytics/positions/by-identifier/1/0xPoolAddress
Path parameters
chainIdnumber | stringidentifierstringQuery parameters
includeDisplaybooleanResponses
200Response for status 200
Schema
object
dataobjectpaginationobjectrequired
positionCountnumberrecipientsCountnumberExample
{
"data": {},
"pagination": {
"positionCount": 0,
"recipientsCount": 0
}
}https://analytics.merkl.xyz/v4/analytics/positions/by-identifier/{chainId}/{identifier}curl -X GET "https://analytics.merkl.xyz/v4/analytics/positions/by-identifier/{chainId}/{identifier}"