Skip to content

Commit 2e4ea42

Browse files
authored
fix: Ensure staking-payouts depth integrates with the relay chain post AHM (#1718)
* Add backwards era calculating * Start and end of migration for relay on westend * Get the logic working * Update docs
1 parent 38e4d3f commit 2e4ea42

4 files changed

Lines changed: 354 additions & 29 deletions

File tree

docs/dist/app.bundle.js

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

docs/src/openapi-v1.yaml

Lines changed: 16 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -554,14 +554,16 @@ paths:
554554
tags:
555555
- staking
556556
summary: Get payout information for a _Stash_ account.
557-
description: Returns payout information for the last specified eras. If
558-
specifying both the depth and era query params, this endpoint will
559-
return information for (era - depth) through era. (i.e. if depth=5 and
560-
era=20 information will be returned for eras 16 through 20). N.B. You
561-
cannot query eras less then `current_era - HISTORY_DEPTH`. N.B. The
562-
`nominator*` fields correspond to the address being queried, even if it
563-
is a validator's _Stash_ address. This is because a validator is technically
564-
nominating itself.
557+
description: |
558+
Returns payout information for the last specified eras. If specifying both the depth and era query params, this endpoint will return information for (era - depth) through era. (i.e. if depth=5 and era=20 information will be returned for eras 16 through 20).
559+
560+
**Asset Hub Migration Support:**
561+
For Asset Hub chains that have migrated staking from the relay chain, this endpoint automatically handles era query routing:
562+
- **Pre-migration eras**: Queries historical data from the relay chain
563+
- **Post-migration eras**: Queries current data from Asset Hub
564+
- **Cross-migration queries**: Automatically splits the era range and combines results from both chains
565+
566+
**Note:** The `nominator*` fields correspond to the address being queried, even if it is a validator's _Stash_ address. This is because a validator is technically nominating itself.
565567
operationId: getStakingPayoutsByAccountId
566568
parameters:
567569
- name: accountId
@@ -624,7 +626,12 @@ paths:
624626
- type: array
625627
items:
626628
$ref: '#/components/schemas/AccountStakingPayouts'
627-
description: Returns a single object when using standard parameters. Returns an array when using 'useRcBlock' parameter (array contains one object per Asset Hub block found, or empty array if none found).
629+
description: |
630+
**Standard Mode**: Returns a single object when using standard parameters (without useRcBlock).
631+
632+
**Relay Chain Block Mode**: Returns an array when using 'useRcBlock' parameter (array contains one object per Asset Hub block found, or empty array if none found).
633+
634+
**Asset Hub Migration**: For both modes, when querying eras that span the Asset Hub migration boundary, the endpoint automatically fetches and combines data from both relay chain (pre-migration eras) and Asset Hub (post-migration eras). The migration handling is transparent to the user - you get complete payout information regardless of which chain originally held the data.
628635
"400":
629636
description: invalid blockId supplied for at query param, or invalid parameter combination
630637
content:

src/controllers/accounts/AccountsStakingPayoutsController.ts

Lines changed: 46 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import BN from 'bn.js';
2020
import { RequestHandler } from 'express';
2121
import { BadRequest, InternalServerError } from 'http-errors';
2222

23+
import { ApiPromiseRegistry } from '../../apiRegistry';
2324
import { validateAddress, validateBoolean, validateUseRcBlock } from '../../middleware';
2425
import { AccountsStakingPayoutsService } from '../../services';
2526
import { IEarlyErasBlockInfo } from '../../services/accounts/AccountsStakingPayoutsService';
@@ -118,6 +119,7 @@ export default class AccountsStakingPayoutsController extends AbstractController
118119
): Promise<void> => {
119120
const { specName } = this;
120121
const isKusama = specName.toString().toLowerCase() === 'kusama';
122+
const { isAssetHubMigrated } = ApiPromiseRegistry.assetHubInfo;
121123

122124
if (useRcBlock === 'true') {
123125
const rcAtResults = await this.getHashFromRcAt(at);
@@ -154,15 +156,28 @@ export default class AccountsStakingPayoutsController extends AbstractController
154156
throw new BadRequest('Staking pallet not found for queried runtime');
155157
}
156158

157-
const result = await this.service.fetchAccountStakingPayout(
158-
hash,
159-
address,
160-
this.verifyAndCastOr('depth', sanitizedDepth, 1) as number,
161-
eraArg,
162-
unclaimedOnly === 'false' ? false : true,
163-
currentEra,
164-
apiAt,
165-
);
159+
let result;
160+
if (isAssetHubMigrated) {
161+
result = await this.service.fetchAccountStakingPayoutAssetHub(
162+
hash,
163+
address,
164+
this.verifyAndCastOr('depth', sanitizedDepth, 1) as number,
165+
eraArg,
166+
unclaimedOnly === 'false' ? false : true,
167+
currentEra,
168+
apiAt,
169+
);
170+
} else {
171+
result = await this.service.fetchAccountStakingPayout(
172+
hash,
173+
address,
174+
this.verifyAndCastOr('depth', sanitizedDepth, 1) as number,
175+
eraArg,
176+
unclaimedOnly === 'false' ? false : true,
177+
currentEra,
178+
apiAt,
179+
);
180+
}
166181

167182
const finalApiAt = await this.api.at(hash);
168183
const ahTimestamp = await finalApiAt.query.timestamp.now();
@@ -201,15 +216,28 @@ export default class AccountsStakingPayoutsController extends AbstractController
201216
throw new BadRequest('Staking pallet not found for queried runtime');
202217
}
203218

204-
const result = await this.service.fetchAccountStakingPayout(
205-
hash,
206-
address,
207-
this.verifyAndCastOr('depth', sanitizedDepth, 1) as number,
208-
eraArg,
209-
unclaimedOnly === 'false' ? false : true,
210-
currentEra,
211-
apiAt,
212-
);
219+
let result;
220+
if (isAssetHubMigrated) {
221+
result = await this.service.fetchAccountStakingPayoutAssetHub(
222+
hash,
223+
address,
224+
this.verifyAndCastOr('depth', sanitizedDepth, 1) as number,
225+
eraArg,
226+
unclaimedOnly === 'false' ? false : true,
227+
currentEra,
228+
apiAt,
229+
);
230+
} else {
231+
result = await this.service.fetchAccountStakingPayout(
232+
hash,
233+
address,
234+
this.verifyAndCastOr('depth', sanitizedDepth, 1) as number,
235+
eraArg,
236+
unclaimedOnly === 'false' ? false : true,
237+
currentEra,
238+
apiAt,
239+
);
240+
}
213241

214242
AccountsStakingPayoutsController.sanitizedSend(res, result);
215243
}

0 commit comments

Comments
 (0)