feat: dispatch spend permissions to SpendRouter when onchain spender matches#686
Open
amiecorso wants to merge 3 commits into
Open
feat: dispatch spend permissions to SpendRouter when onchain spender matches#686amiecorso wants to merge 3 commits into
amiecorso wants to merge 3 commits into
Conversation
🟡 Heimdall Review Status
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Implements the SDK-side half of the SpendRouter integration.
useSpendPermissionnow automatically detects whether a permission's onchain spender is the SpendRouter contract and dispatches toSpendRouter.spendAndRouteinstead ofSpendPermissionManager.spendaccordingly.Cross-version compatibility
Dispatch is driven entirely by
permission.spender, with no API-version negotiation, no response-field dependency, and no SDK release coordination required. This means:spendcall to the router contract, which doesn't expose that selector), but legacy permissions still work fine. Encouraging SDK upgrades is the right migration path; no API-side gating needed.permission.spenderand dispatch manually if needed.Changes
TypeScript (24/24 tests pass; lint + format + type-check clean):
SPEND_ROUTER_ADDRESSand minimalSPEND_ROUTER_ABI(justspendAndRoute) intypescript/src/spend-permissions/constants.ts.isSpendRouterPermissionandbuildSpendCalldatahelpers intypescript/src/spend-permissions/utils.ts— single dispatch decision shared by both hooks.account.use.tsandsmartAccount.use.tsnow delegate calldata construction tobuildSpendCalldata. Each hook is ~10 lines smaller and contains zero hardcoded contract references.Python (14/14 tests pass; ruff lint + format clean):
python/cdp/spend_permissions/constants.py.is_spend_router_permissionandbuild_spend_callhelpers inpython/cdp/spend_permissions/utils.py.account_use.pyandsmart_account_use.pynow delegate calldata construction tobuild_spend_call. Each ~25 lines smaller.build_spend_call) instead of patchingWeb3on the action module. Added 2 dispatch tests (router path on each hook).Java/Go/Rust: No changes. These SDK languages do not yet expose spend-permission actions.
Verification
pnpm vitest run src/actions/evm/spend-permissions src/spend-permissions— 24 passnpx tsc --noEmit -p tsconfig.jsoncleanpnpm lintandpnpm format:checkcleanuv run pytest cdp/test/spend_permissions cdp/test/actions/evm/spend_permissions— 14 passmake lintandmake format-checkcleanEnd-to-end verified on Base Sepolia
A real successful tx where the SDK's dispatch logic targets
SpendRouter.spendAndRoute()(notSpendPermissionManager.spend()) against a permission produced by cdp-service:Tx 0x6025f0bf... —
to = SpendRouter (0x1a672dE4...),function = spendAndRouteReproducible test harness: coinbase/spend-permissions#84 (lands at
examples/cdp-integration-test/once merged). Coinbase-internal methodology writeup linked from the harness README.