Skip to main content
Use the components in src/protection/vault to build a policy for a specific vault. The example below combines two independent conditions: standard vault operations must not dilute holders, and net underlying-token outflow must stay within a rolling budget.

Example policy

Save the contract as examples/assertions-book/assertions/src/BookVaultPolicy.sol in the reviewed checkout, then compile it with FOUNDRY_PROFILE=assertions-book forge build. Pass the asset explicitly. The constructor cannot read vault.asset() from the isolated assertion deployment runtime. The share-price check validates the configured vault and asset at the operation’s post-call snapshot.

Share-price scenarios

_registerPerCallSharePriceTriggers() covers deposit, mint, withdraw, and redeem. Each comparison uses the triggering call’s pre- and post-state, reads totalAssets() and totalSupply(), and checks the asset-per-share ratio with the library’s ratio helper. Rounding, fees, and loss recognition can justify a nonzero tolerance or a different policy. An increase can also be manipulation, so this check alone does not prevent donation attacks. Custom selectors need explicit triggers.

Outflow behavior

The cumulative component watches the configured asset at the vault address. With a 100,000-token baseline, 10,000 tokens of net outflow reaches the limit; the next unit above it triggers rejection. Opposite-direction flows offset outflow. The supplied callback binds the adopter to the configured vault and always reverts on a breach. It does not validate the vault’s asset getter itself. The share-price component performs that check on its covered calls. A vault that moves funds into external strategies can have low idle custody while retaining substantial managed assets. This watcher measures the vault’s token balance, not its totalAssets(). Do not apply a percentage of idle custody as if it were a percentage of total portfolio value.

Other vault components

The code above registers only call-level share-price checks and cumulative outflow. Inheriting a component does not activate every function it contains.

Validation

The example compiles against the reviewed revision. The library’s protection test suite exercises its vault components:
Local tests do not simulate cumulative window dispatch. Validate that part in the executor-backed environment described in the outflow guide. Before activating a composed policy, test the exact vault implementation and all registered functions together.