get

/v4/reallocations/report/{campaignId}

Retrace a campaign's reallocations (BETA)

Reallocation Report

Retraces every reallocation ever applied to a campaign, from its latest merkle tree — the newest root whose tree the tree service holds, named in atRoot. The distribution chain is inferred from the campaign ID.


A reallocation is a two-step protocol recorded in the tree, and it never changes a campaign's total. Step 1 shrinks the original recipient's leaves to what it had already claimed and stages a marker at the zero address (tmp_reallocation_{from}_{to}). Step 2 drains that marker and either credits the destination (reallocation for a creator request, unclaimedRewards for a wipe sweep) or returns the reward to the original recipient (fail_reallocation / fail_wipe) when it claimed in between.


Drained markers survive at amount zero, so the senders roster and the inFlight, returned and per-destination settled amounts are exact.


Not available here: per-sender settled and stagedAt (walk is null). A destination's leaf aggregates every sender and a drained marker has no amount left, so recovering those means one tree read per root — see POST /v4/reallocations/report/{campaignId}/walk.


Authentication: Requires either a valid x-api-key header or the back-office bearer secret.


⚠️ Beta: this endpoint is in beta. The behavior, response shape and data format may change at any time without notice.

Path parameters

campaignIdstring
required

Responses

200
Response for status 200
Schema
object
campaignIdstring
required
Onchain campaign ID the report covers
distributionChainIdnumber
required
Distribution chain inferred from the campaign ID
rewardTokenobject
required
addressstring
required
symbolstring
required
decimalsnumber
required
atRootobject
required
rootstring
required
Merkle root the report describes — the chain's newest one the tree service can read.
timestampstring
required
Unix timestamp (seconds) of that root
totalsobject
required
inFlightstring
required
Sum of every marker still staged, in raw token units
settledstring
required
Sum held at every destination under a reallocation reason, in raw token units
returnedstring
required
Sum returned to senders by a failed settle, in raw token units
stagedstringSum of every step-1 wave the walk observed, in raw token units. Only present on a walk-job result.
destinationsobject[]
required
tostringAddress credited with the reallocated rewards
kindenum`creator-request` — the creator staged an on-chain reallocation (`reason = reallocation`). `wipe` — the wipe job swept unclaimed rewards older than a year to the Merkl dumper (`reason = unclaimedRewards`).creator-requestwipe
settledstringAmount held at this address under the reallocation reason, in raw token units. Aggregated over every sender — per-sender attribution needs the walk job.
sendersobject[]
required
Every original recipient ever reallocated for this campaign, sorted by amount moved descending.
fromstringOriginal recipient the rewards were taken from
tostring[]Destination(s) this sender's rewards were staged toward, parsed from its `tmp_reallocation_{from}_{to}` marker(s). More than one means the sender was reallocated in separate waves to different addresses.
inFlightstringAmount staged at step 1 but not yet settled, in raw token units.
returnedstringAmount returned because the sender claimed between step 1 and step 2 (`fail_reallocation` / `fail_wipe`), in raw token units. The sender kept these rewards.
settledstringAmount taken from this sender that actually reached its destination, in raw token units. Only present on a walk-job result, and only when the walk covered every wave.
stagedAtobject[]Each step-1 wave that staged rewards from this sender, oldest first. Only present on a walk-job result.
rootstringMerkle root of the tree the marker first carried this amount in
timestampstringUnix timestamp (seconds) of that root
amountstringAmount staged in this wave, in raw token units
tostringDestination this wave was staged toward
walkobject | null
required
completeboolean`true` when every step-1 wave was accounted for, so each sender's `settled` is exact. `false` means the walk hit its snapshot budget, or the tree service no longer holds the trees the earliest waves are in, or markers disagreed with the staged total — and the amounts are lower bounds.
incompleteReasonstringWhy the walk could not close
rootsScannednumberRoots read — far fewer than the roots covered
oldestRootstringOldest root covered — the campaign's first, or the oldest whose tree the tree service still holds
newestRootstringNewest root covered — the chain's latest readable one
Example
{
  "campaignId": "string",
  "distributionChainId": 0,
  "rewardToken": {
    "address": "string",
    "symbol": "string",
    "decimals": 0
  },
  "atRoot": {
    "root": "string",
    "timestamp": "string"
  },
  "totals": {
    "inFlight": "string",
    "settled": "string",
    "returned": "string",
    "staged": "string"
  },
  "destinations": [
    {
      "to": "string",
      "kind": "creator-request",
      "settled": "string"
    }
  ],
  "senders": [
    {
      "from": "string",
      "to": [
        "string"
      ],
      "inFlight": "string",
      "returned": "string",
      "settled": "string",
      "stagedAt": [
        {
          "root": "string",
          "timestamp": "string",
          "amount": "string",
          "to": "string"
        }
      ]
    }
  ],
  "walk": {
    "complete": false,
    "incompleteReason": "string",
    "rootsScanned": 0,
    "oldestRoot": "string",
    "newestRoot": "string"
  }
}
get
https://api.merkl.xyz/v4/reallocations/report/{campaignId}
Merkl API
curl -X GET "https://api.merkl.xyz/v4/reallocations/report/{campaignId}"
Fill the required path parameter campaignId to send.