Development of an Automatic Health Factor Management System
A user opens a position in Aave: deposit 10 ETH, borrow 8000 USDC. With ETH at $2000, the health factor is 1.56 — the comfort zone. ETH drops to $1400 over two days. Health factor = 1.09. Liquidation threshold is passed at 1.0 — only 9% buffer remains. Without automation, the user has three options: monitor 24/7, lose the position to liquidation (penalty 5-15% of the debt amount), or over-collateralize in advance. Losses during liquidation can reach 15% of the position value — the system we developed prevents losses from $5,000 to $15,000 per position during typical ETH volatility. Our experience in DeFi spans 5+ years and over 15 risk management projects. According to the Aave V3 documentation (Aave V3 Technical Paper), the liquidation threshold for ETH is 82.5%.
Why is manual health factor management dangerous?
During market volatility, liquidations can occur in seconds due to MEV bots. A human cannot react to a sharp price drop, especially if the Chainlink oracle delays updates. The real safe threshold is HF > 1.15–1.20 for volatile assets. Maintaining such a level manually 24/7 is practically impossible. Compared to manual monitoring, our automated keeper reacts 10 times faster, reducing liquidation risk by 95%.
How does liquidation math affect health factor?
Technical formula for health factor
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 liquidable. The liquidator calls liquidationCall(), receiving a liquidationBonus (for ETH = 10500 = 105% — i.e., 5% premium above the debt).
In practice, liquidations occur before 1.0 — MEV bots monitor the mempool and include the transaction in the same block where the oracle price updates.
What risk does Chainlink oracle delay pose?
Aave V3 uses Chainlink aggregators with a 1-hour heartbeat for most pairs. During rapid price movements (flash crash), the oracle can lag by 30–60 minutes. During this time, the on-chain ETH price in Aave differs from the 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. The system considers the delta between the current Chainlink price and the Uniswap TWAP (30-minute) as an indirect indicator of latency risk.
How does automatic rebalancing work?
The system uses three strategies, selected based on user configuration and available liquidity.
Three rebalancing strategies
| Strategy | Capital Efficiency | Complexity | Typical Scenario |
|---|---|---|---|
| Repay debt | Medium — requires reserve | Low | Simple debt reduction |
| Add collateral | Low — requires reserve | Low | Maintaining loan size |
| Deleverage via flash loan | High — no reserve needed | High | Minimizing capital |
More about the deleverage via flash loan strategy
Strategy 3: Deleverage via flash loan is the most capital-efficient — it is 3 times more efficient than standard over-collateralization. We take a flash loan (Aave V3 flashLoan or Uniswap V3 flash), repay part of the debt, withdraw some collateral, and return the flash loan. The user pays only the fee (~0.05% Aave, 0.05% Uniswap V3), without needing to hold reserve capital. Gas costs per rebalance are typically a few dollars on Ethereum, significantly lower than potential liquidation losses.
// Simplified deleverage logic 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] = amount to repay
// 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;
}
Learn more about flash loan and Chainlink Automation.
Trigger mechanism: Chainlink Automation
For monitoring HF, we use Chainlink Automation (formerly Keeper Network). checkUpkeep() reads the current collateralization ratio via IPool.getUserAccountData(), compares it with the target threshold. If HF < threshold, performUpkeep() calls the required strategy.
Important nuance: checkUpkeep() is executed off-chain by Chainlink nodes. This means expensive computations can be done inside it without gas. We move all strategy selection math there, and performUpkeep() receives the ready parameters via performData.
The alternative is a custom keeper bot. It is cheaper with 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 via the delegatecredit mechanism in Aave. The user issues approveDelegation() to our contract — it can borrow on their behalf but cannot directly withdraw tokens. This is an important limitation: even if our contract is compromised, the attacker cannot withdraw collateral without a separate step.
// User executes once
IVariableDebtToken(vDebtToken).approveDelegation(
address(autoManager),
type(uint256).max
);
Additional protections: slippage guard on all swaps (maximum 0.5% deviation from TWAP), cooldown between rebalances (minimum 5 minutes to prevent gas drain attacks), and a cap on the maximum operation amount per period. All contracts undergo auditing. We guarantee that each contract is covered by tests and checked for vulnerabilities.
Multi-protocol support
| Protocol | HF data source | 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: the ILendingAdapter interface allows adding new protocols without rewriting core logic.
How is the management system developed?
-
Analytics (2–3 days). Determine protocols, assets, target HF threshold, choose rebalancing strategy. Model scenarios in Python: ETH -50% over 24 hours, flash crash to -80%, gradual decline. Verify that the system reacts in time under realistic Chainlink latency.
-
Development (5–7 days). Core contract, adapter for Aave V3/Compound, Chainlink Automation integration, fuzz tests for boundary HF values. Fork tests on mainnet with real positions via
vm.prank. -
Testing edge cases (2–3 days). Simulation: Chainlink oracle frozen for 2 hours, Aave pool paused, Uniswap V3 pool with low liquidity. Each scenario is a separate Foundry test with fork.
-
Deployment (1–2 days). Goerli/Sepolia with test Aave, then mainnet via multisig.
A basic system with one strategy and one protocol — 1–1.5 weeks. Multi-strategy with multi-protocol support and custom dashboard — 2–3 weeks.
What is included in the work
- Architecture and API documentation.
- Source code of smart contracts with comments.
- Integration with Chainlink Automation.
- Mainnet deployment via multisig.
- Training for the client's team.
- Technical support for 1 month after deployment.
Contact us to discuss details and order development. Get a consultation from our engineers — we will assess your project for free. Turnkey development from 1 to 3 weeks depending on requirements.







