Development of an Automatic Health Factor Management System
A user opens a position in Aave: deposits 10 ETH, borrows 8000 USDC. Health factor with ETH = $2000 is 1.56 — comfortable zone. ETH drops to $1400 over two days. Health factor = 1.09. The liquidation threshold is passed at 1.0 — only 9% buffer remaining. Without automation, the user has three options: keep a hand on the pulse 24/7, lose the position to liquidation (5–15% penalty depending on asset), or overpay in advance for excess collateral. An automatic health factor management system enables a fourth option — an autonomous rebalancer that keeps the position in the safe zone without user participation.
Liquidation Mathematics in Aave V3
What is Health Factor Technically
HF = (∑ collateral_i × price_i × liquidationThreshold_i) / totalDebt
Each asset in Aave V3 has its own liquidationThreshold (expressed in basis points, e.g., ETH = 8250 = 82.5%). When HF < 1.0, the position is liquidatable. A liquidator calls liquidationCall(), receiving liquidationBonus (for ETH = 10500 = 105% — 5% premium over debt).
In practice, liquidations happen before 1.0 — MEV bots monitor the mempool and include the transaction in the same block as oracle price update. The real safe threshold is HF > 1.15–1.20 for volatile assets.
Chainlink Oracle Latency Risk
Aave V3 uses Chainlink aggregators with 1-hour heartbeat for most pairs. During rapid price movement (flash crash), the oracle can lag 30–60 minutes. During this time, on-chain ETH price in Aave differs from real exchange price by 5–10%. This creates a situation where our system sees HF = 1.25, but after the next oracle update HF instantly becomes 0.95 and the position is liquidated.
Handling this scenario is one of the key engineering challenges. Our system accounts for delta between current Chainlink price and Uniswap TWAP price (30-minute) as an indirect indicator of latency risk.
Health Factor Management System Architecture
Three Rebalancing Strategies
Strategy 1: Repay Debt. When HF drops below target threshold, the system takes funds from a user's reserve buffer (pre-deposited on the contract) and partially repays debt via repay(). Simple, predictable, no complex operations. Downside: requires reserve capital.
Strategy 2: Add Collateral. Deposit additional collateral via supply(). Also requires reserves, but does not reduce user's leverage. Suitable when the goal is to keep the loan size unchanged.
Strategy 3: Deleverage via Flash Loan. Most complex and capital-efficient. Take a flash loan (Aave V3 flashLoan or Uniswap V3 flash), repay part of debt, withdraw part of collateral, return flash loan. User pays only fee (~0.05% Aave, 0.05% Uniswap V3), without need to hold reserve capital.
// Simplified deleverage via Aave flash loan
function executeOperation(
address[] calldata assets,
uint256[] calldata amounts,
uint256[] calldata premiums,
address initiator,
bytes calldata params
) external returns (bool) {
// assets[0] = debt token (USDC)
// amounts[0] = repayment amount
// 1. Repay debt in Aave
IPool(aavePool).repay(assets[0], amounts[0], 2, userAddress);
// 2. Withdraw equivalent collateral
IPool(aavePool).withdraw(collateralAsset, collateralAmount, address(this));
// 3. Swap collateral → debt token via Uniswap V3
swapExactOutputSingle(collateralAsset, assets[0], amounts[0] + premiums[0]);
// 4. Return flash loan + premium
IERC20(assets[0]).approve(aavePool, amounts[0] + premiums[0]);
return true;
}
Trigger Mechanism: Chainlink Automation
To monitor HF, we use Chainlink Automation (formerly Keeper Network). checkUpkeep() reads current HF via IPool.getUserAccountData(), compares with target threshold. If HF < threshold — performUpkeep() calls the appropriate strategy.
Important nuance: checkUpkeep() executes off-chain on Chainlink nodes. This means you can do expensive computations inside without gas. We move all strategy selection logic there, and performUpkeep() receives ready parameters via performData.
Alternative — custom keeper bot. Cheaper at high user volume, but requires infrastructure (VPS, uptime monitoring). For B2C products we recommend Chainlink — no dependency on our server.
Role Model and Security
The contract manages the position on behalf of the user through Aave's delegatecredit mechanism. User grants approveDelegation() to our contract — it can borrow on their behalf, but not withdraw tokens directly. This is important: even if our contract is compromised, the attacker cannot withdraw collateral without an extra step.
// User executes once
IVariableDebtToken(vDebtToken).approveDelegation(
address(autoManager),
type(uint256).max
);
Additional protection: slippage guard on all swaps (max 0.5% deviation from TWAP), cooldown between rebalances (minimum 5 minutes to prevent gas drain attacks), operation amount limit per period.
Multi-protocol Support
| Protocol | HF Data Type | Flash Loan Available | Chains |
|---|---|---|---|
| Aave V3 | getUserAccountData() |
Yes, 0.05% | ETH, Polygon, Arbitrum, Optimism |
| Compound V3 | getBorrowableOf() |
Via Uniswap | ETH, Polygon, Arbitrum |
| Morpho | position per-market | No native | ETH, Base |
The system is built with protocol abstraction: ILendingAdapter interface allows adding new protocols without rewriting core logic.
Development Process
Analytics (2–3 days). Define protocols, assets, target HF threshold, select rebalancing strategy. Model scenarios in Python: ETH -50% over 24 hours, flash crash to -80%, gradual decline. Verify system reacts at realistic Chainlink latency.
Development (5–7 days). Core contract, adapters for Aave V3/Compound, Chainlink Automation integration, fuzz tests on HF boundary values. Fork tests on mainnet with real positions via vm.prank.
Edge Case Testing (2–3 days). Simulate: Chainlink oracle stuck for 2 hours, Aave pool paused, Uniswap V3 pool with low liquidity. Each scenario — separate Foundry test with fork.
Deployment (1–2 days). Goerli/Sepolia with test Aave, then mainnet via multisig.
Basic system with one strategy and one protocol — 1–1.5 weeks. Multi-strategy with multi-protocol support and custom dashboard — 2–3 weeks. Cost calculated after analysis of requirements.







