Skip to main content
The risk engine watches the health of your yield sources and reacts when a source crosses a limit you define. A risk rule is a single condition on a yield-source metric plus the outcome that fires when that condition is met. Each rule belongs to one portfolio wallet and one yield source. When a new metric reading for that source crosses the rule, the engine opens an alert and, depending on the outcome, may create an action.

Rule anatomy

FieldRequiredDescription
portfolioWalletIdYesThe wallet the rule applies to
yieldSourceIdYesThe yield source to watch (UUID or public id, e.g. morpho-gauntlet-usdc)
metricYesThe metric to evaluate (see Metrics)
ruleKindYesabsolute or relative_change_bps (see Rule kinds)
comparatorYeslt, lte, gt, or gte
thresholdValueYesThe value to compare against
windowSecondsFor velocityLookback window, required for relative_change_bps, omitted for absolute
outcomeNoalert (default), prevent_additional_allocation, or exit_position
approvalModeFor non-alertautomatic or approval_required
nameNoA human label
statusNoactive (default) or paused

Metrics

Rules can be written against these per-source metrics:
MetricMeaningUnits
available_withdrawal_liquidity_usdLiquidity currently available to withdraw from the sourceUSD
tvl_usdTotal value locked in the sourceUSD
apy_bpsCurrent annualized yieldBasis points (100 bps = 1%)
Metrics are ingested on a poll cadence per source. You can read the latest readings with GET /v2/wallets/risk/metrics.

Rule kinds

Absolute (ruleKind: "absolute") compares the current reading directly against thresholdValue. thresholdValue must be non-negative and windowSeconds is omitted.
Alert when available withdrawal liquidity drops below $100,000,000: metric: available_withdrawal_liquidity_usd, comparator: lt, thresholdValue: 100000000.
Velocity (ruleKind: "relative_change_bps") compares the change in the metric over windowSeconds against thresholdValue, expressed in basis points. Here thresholdValue is a signed bps change and windowSeconds is required.
Alert when TVL falls 15% or more over 24h: metric: tvl_usd, ruleKind: relative_change_bps, comparator: lte, thresholdValue: -1500, windowSeconds: 86400.
For velocity rules, thresholdValue may be negative (a drop). For absolute rules it must be non-negative.

Comparators

lt (below), lte (at or below), gt (above), gte (at or above). A rule breaches when the reading satisfies the comparator against the threshold.

Outcome and approval mode

The outcome decides what happens when the rule breaches:
  • alert: notify only. No approvalMode.
  • prevent_additional_allocation: block new allocation into the source while the alert is open.
  • exit_position: exit the position when the rule breaches.
Non-alert outcomes require an approvalMode of automatic (acts on its own) or approval_required (waits for you to approve). See Outcomes and Actions for the full behavior of each.

Create a rule

curl -X POST "$BASE_URL/v2/wallets/risk/rules" \
  -H "Authorization: Bearer $API_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "portfolioWalletId": "388f4859-36a0-47ca-9f80-abb73aa56fe9",
    "yieldSourceId": "morpho-gauntlet-usdc",
    "name": "Gauntlet liquidity floor",
    "metric": "available_withdrawal_liquidity_usd",
    "ruleKind": "absolute",
    "comparator": "lt",
    "thresholdValue": 100000000,
    "outcome": "alert"
  }'
Rules back-evaluate on creation. If the source is already breaching the threshold when you create the rule, the alert opens immediately instead of waiting for the next metric reading. The same happens when you re-enable a paused rule.

Edit a rule

Patch any subset of fields. The wallet and yield source are fixed at creation and cannot be changed. To watch a different source, create a new rule.
curl -X PATCH "$BASE_URL/v2/wallets/risk/rules/$RISK_RULE_ID" \
  -H "Authorization: Bearer $API_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "thresholdValue": 50000000 }'
Changing a rule’s threshold or other execution fields re-checks it against the latest reading, and rejects any of its actions that were still pending.

Pause and resume a rule

Set status to paused to turn a rule off, or active to turn it back on.
curl -X PATCH "$BASE_URL/v2/wallets/risk/rules/$RISK_RULE_ID" \
  -H "Authorization: Bearer $API_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "status": "paused" }'
While paused, a rule is not evaluated against new readings: it raises no new alerts, takes no automatic action, and any of its pending approvals or auto-executions are rejected. If it was preventing allocation into a source, that block is lifted. Alerts and history it already created are kept. Resuming re-checks the rule against the latest reading.

Delete a rule

curl -X DELETE "$BASE_URL/v2/wallets/risk/rules/$RISK_RULE_ID" \
  -H "Authorization: Bearer $API_TOKEN"
Deleting a rule first resolves any ongoing alert for it and rejects any pending actions (emitting the corresponding webhooks), then removes the rule. This is permanent.

Next steps