Rebalance engine

The rebalance engine sits on top of the priceless-synth contracts. Where the position manager, optimistic oracle, and liquidation keep a single synth solvent against one reference, the rebalance engine adjusts the collateral mix of an event-triggered synth when its referenced event resolves.

Event reference

Each synth commits an optimistic-oracle price identifier and ancillary data that encodes the event question and its resolution source. The pair is set once at registration and is immutable.

bytes32 priceIdentifier;   // e.g. "TRANT_EVENT_V1"
bytes   ancillaryData;     // "q:Will the FOMC cut at the Sep 2026 meeting?,src:federalreserve.gov"

A keeper's initiateRebalance call turns this into a live price request. A proposer answers it, a liveness window opens, and a disputer can escalate. The engine only ever reads a settled value.

Bounded, pre-committed weight formula

Registration also commits the entire rebalancing policy:

On execution the engine clamps the committed target into each asset's window and renormalises so the basket sums to one:

max(floor_i, w_i − Δ)  ≤  applied_i  ≤  min(ceil_i, w_i + Δ)
          Σ applied_i  =  1e18
Invariant

The applied mix is bounded regardless of what the schedule says and regardless of how far the basket has drifted. If the bands genuinely can't host a basket that sums to one this round, the call reverts and the keeper retries after the interval.

Rebalance lifecycle

One rebalance can be in flight per synth at a time. Only completed rebalances are rate-limited by the minimum interval; a cancelled one can be retried immediately. Every state-changing entrypoint is non-reentrant.

CallCallerEffect
registerSynthGovernorOnce per synth. Commits the event reference, asset bands, outcome schedule, bond and interval parameters. Immutable after.
fundRewardsAnyoneTops up the synth's keeper-reward pool in the bond currency.
initiateRebalanceKeeperPulls the oracle reward, final fee, and rebalance bond; opens a price request for the event; the engine holds the bond.
executeRebalanceAnyoneSettles the oracle value, selects the step, clamps against the bands and max delta, pushes the bounded target to the vault, returns the bond, and pays the keeper reward.
cancelRebalanceAnyoneAfter the resolve window with no settlement: unwinds the pending state and refunds the held bond.

Keeper incentive

Triggering a rebalance costs capital up front and returns it once the oracle validates the outcome, the same shape as an EMP liquidation bond.

FlowOn initiateOn executeOn cancel
Oracle reward + final feekeeper → oracle, , (not reclaimed in the scaffold)
Rebalance bondkeeper → engineengine → keeperengine → keeper
Keeper reward, pool → keeper,

Net keeper result on a completed rebalance = keeper reward − oracle reward − final fee − gas. The reward has to be set above the oracle cost or keepers won't call; executeRebalance reverts if the pool can't cover it.

Guards

Status

The engine is a Solidity scaffold (Foundry, solc 0.8.19) with an end-to-end test suite. It has not been audited or deployed. Token-decimal normalisation, oracle-reward reclaim on cancel, a production swap executor, and an emergency pause are still open.