Overview
Updates config fields (delta, min TVL/liquidity, hide list, name, and
status for pause/resume — only active and paused are accepted).
SignedRequest, action strategy.update; the id rides in the path
and the proof's - path: entry binds it. Only fields present in the
body are written; explicit null writes null.
Hide-list toggles: hide_vault_key / unhide_vault_key merge a single
key server-side, so a toggle cannot clobber concurrent edits. Exactly
one op per request; combining an op with a hidden_vault_keys array
replace is a 400 invalid_request.
A hide op or array replace that would leave fewer than
max_positions + 1 eligible vaults is a 409 hide_floor_violated.
Hiding a never-eligible vault passes; unhide_vault_key is not checked.
Endpoint
PATCH https://earn-api.quicknode.dev/functions/v1/api/v1/strategies/{id}
Authorization
Include the published apikey header and a valid Sign-In with Ethereum (SIWE) proof in the request body. The SIWE message binds the wallet to this action, payload, and request path.
Parameters
| Parameter | Location | Type | Required | Description |
|---|---|---|---|---|
| id | path | string | Yes | Strategy UUID. |
Request body
Any subset of config fields. Only present fields are written; explicit null writes null. status drives pause/resume. hide_vault_key / unhide_vault_key: exactly one per request, never both, never combined with hidden_vault_keys (400 invalid_request otherwise).
| Field | Type | Required | Description |
|---|---|---|---|
| siwe | object | Yes | A Sign-In-With-Ethereum proof binding the wallet to (action, payload, issuedAt, expirationTime). |
| siwe.message | string | Yes | SIWE message for action `strategy.update`, including the payload hash and strategy path resource. |
| siwe.signature | string | Yes | Wallet signature over `siwe.message`. |
| name | string | No | New strategy name, up to 50 characters. |
| capital_usdc | number | No | Decimal dollars. Written verbatim when present; no balance check on update (unlike create). |
| delta_pct | number | No | Same-network APY-gap threshold (percentage points). When either threshold field is present, the effective post-update pair is validated against the floors: delta_pct >= 3 (5 when the strategy's networks include Ethereum). Strategies created below the floors keep running unchanged until a PATCH touches a threshold field. |
| cross_chain_delta_pct | number | No | Cross-chain APY-gap threshold. 0 means inherit delta_pct — send 0 (not null; the column is non-nullable) to reset an explicit bar back to inherit. For a multi-network strategy the EFFECTIVE cross bar (this value when > 0, else delta_pct) must be >= 5, or >= 7 when the networks include Ethereum — validated whenever either threshold field is in the payload. |
| delta_confirmations | integer | No | Number of consecutive qualifying APY observations required before rebalancing. |
| max_positions | integer | No | Maximum number of vault positions. |
| min_tvl_usd | number | No | Minimum vault TVL in decimal US dollars. |
| min_liquidity_usd | number | No | Minimum vault liquidity in decimal US dollars. |
| min_liquidity_entry_multiplier | number | No | Multiplier applied to `min_liquidity_usd` when evaluating a new vault entry. |
| apy_smoothing_minutes | integer | No | APY smoothing window in minutes. |
| hidden_vault_keys | array<string> | No | Full-array REPLACE of the strategy hide list. Cannot be combined with the single-op toggles below. |
| hide_vault_key | string | No | Single-op: add this vault key to the strategy's hide list (lowercased, deduped server-side). |
| unhide_vault_key | string | No | Single-op: remove this vault key from the strategy's hide list. |
| status | string (active | paused) | No | Set `paused` to pause the strategy or `active` to resume it. |
Example request
curl --request PATCH \
--url 'https://earn-api.quicknode.dev/functions/v1/api/v1/strategies/<STRATEGY_ID>' \
--header 'Accept: application/json' \
--header 'apikey: <EARN_PUBLIC_API_KEY>' \
--header 'Content-Type: application/json' \
--data '{
"siwe": {
"message": "<SIWE_MESSAGE>",
"signature": "<SIGNATURE>"
}
}'
Response
The response uses the same stored strategy-row shape documented by Create strategy, with the updated values.
| Field | Type | Required | Description |
|---|---|---|---|
| strategy | object | Yes | The strategy row returned (inside `strategy`) by create and update: config fields plus cycle/gauge fields (`cycle_state`, `swap_signals`, `last_skip`, ...). No computed rollups. |
| strategy.id | string | Yes | Updated strategy UUID. |
| strategy.wallet_address | string | Yes | Strategy owner address. |
| strategy.name | string | Yes | Current strategy name. |
| strategy.status | string | Yes | Current lifecycle status. |
| strategy.updated_at | string | Yes | Timestamp of the update. |
| strategy.cycle_state | string | null | Yes | Current strategy cycle state. |
Example response
{
"strategy": {
"id": "b7c1e2d3-0000-4000-8000-000000000001",
"wallet_address": "0x1234567890abcdef1234567890abcdef12345678",
"name": "My USDC Strategy",
"capital_usdc": 1000,
"delta_pct": 3,
"cross_chain_delta_pct": 5,
"delta_confirmations": 2,
"max_positions": 2,
"chain_ids": "8453,42161",
"status": "active",
"active": true,
"cycle_state": "idle"
}
}
HTTP responses
| Status | Description |
|---|---|
| 200 | The updated strategy, wrapped in a `strategy` object. A missing or unowned strategy returns 500 `internal_error`, not 404. |
| 400 | Malformed request or SIWE block. `code` is one of: `invalid_request`, `siwe_missing` (no `siwe` block), `siwe_shape` (message/signature not strings), `siwe_parse` (message does not match the documented line format). |
| 401 | SIWE verification failed. `code` is one of: `siwe_domain` (message domain not allowlisted), `siwe_action` (statement/action mismatch), `siwe_stale` (expired or validity window out of bounds), `siwe_payload` (payload hash or resource mismatch — canonicalization drift, a re-serialized body, or a `- path:` entry that does not match the request path), `siwe_chain` (bad chain id), `siwe_recover` (signature does not match the claimed address), `siwe_replay` (nonce already used — sign a fresh request). |
| 409 | `hide_floor_violated`: the hide change would shrink the eligible vault pool below `max_positions + 1`. See the description above. |
| 429 | Rate limit exceeded. `Retry-After` (seconds) tells you when to retry. Reads, feedback, and push writes are keyed per IP; create/update/delete are keyed per wallet+IP; deposit/withdraw/claim calldata is keyed per strategy+IP. |
| 500 | Internal server error. |
| 503 | Transient failure, retry: `strategy_read_failed` (hide-list merge read), `hide_lookup_failed` (hide-floor check read), or `siwe_rpc` (smart-wallet signature verification RPC). |
This page is based on operation updateStrategy in the Earn OpenAPI 3.1 specification.