Rebalancing Mechanics
Rebalancing is ALP's automated position management system that maintains positions within target health ranges. This powerful feature eliminates manual management and optimizes capital efficiency.
Understanding Rebalancing
What is Rebalancing?
Rebalancing is the automatic adjustment of a position's debt to maintain its health factor within a target range. When overcollateralized (HF > maxHealth), the system automatically borrows more. When undercollateralized (HF < minHealth), it automatically repays debt. When in range (minHealth ≤ HF ≤ maxHealth), no action is needed.
The goal is to keep positions at the target health factor (typically 1.3), maximizing capital efficiency while maintaining safety.
_15graph LR_15 subgraph "Health States"_15 A[HF < 1.1<br/>Undercollateralized]_15 B[HF: 1.1 - 1.5<br/>Healthy Range]_15 C[HF > 1.5<br/>Overcollateralized]_15 end_15_15 A -->|Auto-repay debt| Target[Target HF: 1.3]_15 C -->|Auto-borrow more| Target_15 B -.->|No action| B_15_15 style A fill:#fbb_15 style B fill:#bfb_15 style C fill:#bbf_15 style Target fill:#bfb,stroke:#333,stroke-width:3px
Target Health Range
Each position has configurable health bounds:
_10minHealth: 1.1 (minimum before rebalancing up)_10targetHealth: 1.3 (optimal target)_10maxHealth: 1.5 (maximum before rebalancing down)
Visual representation:
_100.0 ---- 1.0 ---- 1.1 ---- 1.3 ---- 1.5 ---- 2.0+_10 | | | |_10 Liquidation Min Target Max_10 (Repay zone) (Borrow zone)
Rebalancing Decision Logic
_24flowchart TD_24 Start[Check Position Health] --> GetHF[Get Current HF]_24 GetHF --> Check{HF vs Range?}_24_24 Check -->|HF < minHealth<br/>1.1| Low[Undercollateralized]_24 Check -->|minHealth ≤ HF ≤ maxHealth<br/>1.1 - 1.5| Good[Healthy]_24 Check -->|HF > maxHealth<br/>1.5| High[Overcollateralized]_24_24 Low --> CalcRepay[Calculate<br/>Required Repayment]_24 CalcRepay --> PullFunds[Pull from<br/>TopUpSource]_24 PullFunds --> Repay[Repay Debt]_24 Repay --> Restored[HF = 1.3 ✓]_24_24 Good --> NoAction[No Action Needed]_24_24 High --> CalcBorrow[Calculate<br/>Additional Borrowable]_24 CalcBorrow --> Borrow[Borrow MOET]_24 Borrow --> PushFunds[Push to<br/>DrawDownSink]_24 PushFunds --> Restored_24_24 style Low fill:#fbb_24 style Good fill:#bfb_24 style High fill:#bbf_24 style Restored fill:#bfb,stroke:#333,stroke-width:3px
When Rebalancing Triggers
Automatic triggers occur when position health moves outside the min/max range, after deposits that cause overcollateralization, following price changes via oracle updates, and through scheduled checks by keepers or the protocol.
Manual triggers include user-forced rebalancing, protocol maintenance calls, and integration with external automation.
Overcollateralized Rebalancing
When It Occurs
Rebalancing down (borrowing more) happens when:
_10Current Health Factor > maxHealth (1.5)
This means you have "excess" collateral that could be used to borrow more.
The Mathematics
The system calculates how much additional debt can be safely taken:
_12Current State:_12- Effective collateral: EC_12- Effective debt: ED_12- Current health: HF = EC / ED_12- Target health: TH = 1.3_12_12Additional borrowable amount:_12additionalBorrow = (EC / TH) - ED_12_12New state after borrowing:_12- New debt: ED + additionalBorrow = EC / TH_12- New health: EC / (EC / TH) = TH ✓
See FCM Mathematical Foundations for detailed formulas and step-by-step derivations.
Overcollateralized Flow
_15sequenceDiagram_15 participant Position_15 participant ALP_15 participant DrawDownSink_15 participant FYV_15_15 Position->>Position: Detect HF = 2.0<br/>(above max 1.5)_15 Position->>ALP: Calculate additional borrow_15 Note over ALP: (EC / 1.3) - ED<br/>= additional amount_15 ALP->>ALP: Borrow 215.38 MOET_15 ALP->>DrawDownSink: Push MOET_15 DrawDownSink->>FYV: Deploy to yield_15 Position->>Position: Health = 1.3 ✓_15_15 Note over Position,FYV: Automatic capital efficiency!
Example:
_14Current State:_14- Collateral: 1000 FLOW @ $1 = $1000, factor 0.8 = $800 effective_14- Debt: 400 MOET @ $1 = $400_14- Health: 800 / 400 = 2.0 (above maxHealth of 1.5)_14_14Calculation:_14- Target debt for HF=1.3: 800 / 1.3 ≈ 615.38 MOET_14- Additional borrow: 615.38 - 400 = 215.38 MOET_14_14After Rebalancing:_14- Collateral: $800 effective (unchanged)_14- Debt: 615.38 MOET_14- Health: 800 / 615.38 = 1.3 ✓_14- User receives: 215.38 MOET via DrawDownSink
DrawDownSink Integration
When borrowing during rebalancing, funds are pushed to the DrawDownSink:
_12graph LR_12 Position[Position<br/>HF > 1.5] --> Calculate[Calculate<br/>Excess Capacity]_12 Calculate --> Borrow[Borrow<br/>MOET]_12 Borrow --> Sink[DrawDownSink]_12_12 Sink --> Wallet[User Wallet]_12 Sink --> FYV[FYV Strategy]_12 Sink --> LP[LP Pool]_12 Sink --> Other[Other DeFi]_12_12 style Position fill:#bbf_12 style Sink fill:#f9f,stroke:#333,stroke-width:2px
Benefits: Funds are automatically deployed to the user's wallet or DeFi strategy without requiring manual claims, ensuring seamless capital efficiency. The system can integrate with yield farms, LP pools, and other DeFi protocols.
Undercollateralized Rebalancing
When It Occurs
Rebalancing up (repaying debt) happens when:
_10Current Health Factor < minHealth (1.1)
This means your position is approaching liquidation risk and needs debt reduction.
The Mathematics
The system calculates how much debt must be repaid:
_12Current State:_12- Effective collateral: EC_12- Effective debt: ED_12- Current health: HF = EC / ED_12- Target health: TH = 1.3_12_12Required repayment:_12requiredPaydown = ED - (EC / TH)_12_12New state after repayment:_12- New debt: EC / TH_12- New health: EC / (EC / TH) = TH ✓
See FCM Mathematical Foundations for detailed formulas and proofs.
Undercollateralized Flow
_19sequenceDiagram_19 participant Price_19 participant Position_19 participant TopUpSource_19 participant FYV_19 participant ALP_19_19 Price->>Position: FLOW drops 20%_19 Position->>Position: HF = 1.04<br/>(below min 1.1!)_19 Position->>ALP: Calculate repayment needed_19 Note over ALP: ED - (EC / 1.3)<br/>= repayment amount_19 ALP->>TopUpSource: Request 123.07 MOET_19 TopUpSource->>FYV: Withdraw from yield_19 FYV->>TopUpSource: Provide MOET_19 TopUpSource->>ALP: Supply MOET_19 ALP->>ALP: Repay debt_19 Position->>Position: Health = 1.3 ✓_19_19 Note over Price,Position: Automatic liquidation prevention!
Example:
_19Initial State:_19- Collateral: 1000 FLOW @ $1 = $1000, factor 0.8 = $800 effective_19- Debt: 615.38 MOET_19- Health: 800 / 615.38 = 1.3_19_19After FLOW Price Drops 20% to $0.80:_19- Collateral: 1000 FLOW @ $0.80 = $800, factor 0.8 = $640 effective_19- Debt: 615.38 MOET (unchanged)_19- Health: 640 / 615.38 = 1.04 (below minHealth of 1.1)_19_19Calculation:_19- Target debt for HF=1.3: 640 / 1.3 ≈ 492.31 MOET_19- Required paydown: 615.38 - 492.31 = 123.07 MOET_19_19After Rebalancing:_19- Collateral: $640 effective (unchanged)_19- Debt: 492.31 MOET_19- Health: 640 / 492.31 = 1.3 ✓_19- User paid: 123.07 MOET via TopUpSource
TopUpSource Integration
When repaying during rebalancing, funds are pulled from the TopUpSource:
_16graph LR_16 Position[Position<br/>HF < 1.1] --> Calculate[Calculate<br/>Repayment Needed]_16 Calculate --> Request[Request<br/>MOET]_16 Request --> Source[TopUpSource]_16_16 Wallet[User Wallet] --> Source_16 FYV[FYV Strategy] --> Source_16 LP[LP Pool] --> Source_16 Other[Other DeFi] --> Source_16_16 Source --> Repay[Repay<br/>Debt]_16 Repay --> Safe[HF = 1.3 ✓]_16_16 style Position fill:#fbb_16 style Source fill:#f9f,stroke:#333,stroke-width:2px_16 style Safe fill:#bfb
Benefits: The TopUpSource integration provides automatic liquidation protection without requiring manual monitoring. Funds are sourced from the user's chosen location and can integrate with yield farms to automatically exit positions when needed.
When TopUpSource is connected to FYV, your yield automatically protects your position from liquidation. This is the core innovation of Flow Credit Market!
Rebalancing Scenarios
Scenario 1: Initial Position with Auto-Borrow
_17sequenceDiagram_17 participant User_17 participant ALP_17 participant Position_17 participant DrawDownSink_17_17 User->>ALP: Deposit 1000 FLOW<br/>pushToDrawDownSink=true_17 ALP->>Position: Create position_17 Position->>Position: Initial HF = ∞<br/>(no debt yet)_17 Position->>Position: Detect HF > max (1.5)_17 Position->>Position: Calculate: 800/1.3 = 615.38_17 Position->>Position: Auto-borrow 615.38 MOET_17 Position->>DrawDownSink: Push MOET_17 DrawDownSink->>User: Funds deployed_17 Position->>Position: Final HF = 1.3 ✓_17_17 Note over User,DrawDownSink: Immediate auto-optimization!
What happens:
- Initial health: Infinite (no debt)
- System detects health > maxHealth
- Calculates borrowable: 800 / 1.3 ≈ 615.38 MOET
- Auto-borrows 615.38 MOET
- Pushes to DrawDownSink
- Final health: 1.3 ✓
Scenario 2: Price Increase Creates Opportunity
_12graph TD_12 Start[Initial State<br/>1000 FLOW @ $1<br/>Debt: 615 MOET<br/>HF: 1.3] --> PriceUp[FLOW → $1.25]_12 PriceUp --> NewState[New Collateral: $1000<br/>Debt: 615 MOET<br/>HF: 1.625]_12 NewState --> Detect[HF > maxHealth!]_12 Detect --> Calc[Target Debt:<br/>1000 / 1.3 = 769 MOET]_12 Calc --> Borrow[Borrow Additional:<br/>769 - 615 = 154 MOET]_12 Borrow --> Push[Push to DrawDownSink]_12 Push --> Final[Final HF: 1.3 ✓]_12_12 style Start fill:#bbf_12 style NewState fill:#bfb_12 style Final fill:#bfb
Example:
_13Initial: 1000 FLOW @ $1, debt 615.38 MOET, health 1.3_13FLOW price increases to $1.25_13_13New state:_13- Collateral: 1000 FLOW @ $1.25 = $1250, factor 0.8 = $1000 effective_13- Debt: 615.38 MOET_13- Health: 1000 / 615.38 = 1.625 (above maxHealth)_13_13Rebalancing triggers:_13- Target debt: 1000 / 1.3 ≈ 769.23 MOET_13- Additional borrow: 769.23 - 615.38 = 153.85 MOET_13- User receives: 153.85 MOET via DrawDownSink_13- New health: 1.3 ✓
Scenario 3: Price Decrease Requires Repayment
_12graph TD_12 Start[Initial State<br/>1000 FLOW @ $1<br/>Debt: 615 MOET<br/>HF: 1.3] --> PriceDown[FLOW → $0.80]_12 PriceDown --> NewState[New Collateral: $640<br/>Debt: 615 MOET<br/>HF: 1.04]_12 NewState --> Detect[HF < minHealth!]_12 Detect --> Calc[Target Debt:<br/>640 / 1.3 = 492 MOET]_12 Calc --> Repay[Repay:<br/>615 - 492 = 123 MOET]_12 Repay --> Pull[Pull from TopUpSource]_12 Pull --> Final[Final HF: 1.3 ✓]_12_12 style Start fill:#bbf_12 style NewState fill:#fbb_12 style Final fill:#bfb
Example:
_13Initial: 1000 FLOW @ $1, debt 615.38 MOET, health 1.3_13FLOW price decreases to $0.80_13_13New state:_13- Collateral: 1000 FLOW @ $0.80 = $800, factor 0.8 = $640 effective_13- Debt: 615.38 MOET_13- Health: 640 / 615.38 = 1.04 (below minHealth)_13_13Rebalancing triggers:_13- Target debt: 640 / 1.3 ≈ 492.31 MOET_13- Required repayment: 615.38 - 492.31 = 123.07 MOET_13- System pulls: 123.07 MOET from TopUpSource_13- New health: 1.3 ✓
Scenario 4: Interest Accrual Over Time
_11graph LR_11 Start[Initial<br/>HF: 1.3] --> Time[6 Months<br/>10% APY]_11 Time --> Interest[Interest Accrues<br/>Debt ↑ 5%]_11 Interest --> Check{HF < 1.1?}_11 Check -->|Yes| Trigger[Trigger<br/>Rebalancing]_11 Check -->|No| Monitor[Continue<br/>Monitoring]_11 Trigger --> Repay[Repay from<br/>TopUpSource]_11 Repay --> Restored[HF = 1.3 ✓]_11_11 style Interest fill:#ffa_11 style Restored fill:#bfb
Example:
_12Initial: 1000 FLOW @ $1, debt 615.38 MOET, health 1.3_12After 6 months at 10% APY:_12_12New state:_12- Collateral: $800 effective (unchanged)_12- Debt: 615.38 * 1.05 ≈ 646.15 MOET (5% accrued interest)_12- Health: 800 / 646.15 = 1.238 (approaching minHealth)_12_12If health drops below 1.1:_12- Rebalancing triggers_12- Repays enough to restore health to 1.3_12- Funds pulled from TopUpSource
Rebalancing Strategies
Strategy Comparison
_17graph TD_17 subgraph Conservative_17 C1[minHealth: 1.2<br/>target: 1.5<br/>maxHealth: 2.0]_17 C2[✅ Stable<br/>✅ Low gas<br/>❌ Low efficiency]_17 end_17_17 subgraph Balanced_17 B1[minHealth: 1.1<br/>target: 1.3<br/>maxHealth: 1.5]_17 B2[✅ Efficient<br/>✅ Reasonable gas<br/>✅ Good safety]_17 end_17_17 subgraph Aggressive_17 A1[minHealth: 1.1<br/>target: 1.2<br/>maxHealth: 1.3]_17 A2[✅ Max efficiency<br/>❌ High gas<br/>❌ Risky]_17 end_17_17 style Balanced fill:#bfb,stroke:#333,stroke-width:3px
Conservative Strategy
Configuration:
_10minHealth: 1.2_10targetHealth: 1.5_10maxHealth: 2.0
Characteristics: Conservative strategy offers less frequent rebalancing, lower gas costs, more stable positions, and a buffer against volatility. However, it results in lower capital efficiency and less borrowed funds.
Best for: Risk-averse users, volatile collateral, learning the system
Balanced Strategy (Recommended)
Configuration:
_10minHealth: 1.1_10targetHealth: 1.3_10maxHealth: 1.5
Characteristics: Balanced strategy provides good capital efficiency, reasonable rebalancing frequency, balanced risk/reward ratios, and serves as the standard configuration.
Best for: Most users, general purpose lending
This is the default and most common configuration.
Aggressive Strategy
Configuration:
_10minHealth: 1.1_10targetHealth: 1.2_10maxHealth: 1.3
Characteristics: Aggressive strategy offers maximum capital efficiency, more borrowed funds, and higher yield potential. However, it requires frequent rebalancing, incurs higher gas costs, is more sensitive to volatility, and requires a reliable TopUpSource.
Best for: Experienced users, stable collateral, maximum leverage
Aggressive strategy requires reliable TopUpSource with sufficient liquidity. If TopUpSource runs dry during a price drop, liquidation risk increases significantly!
Helper Functions for Rebalancing
ALP provides two key functions to check rebalancing status:
Checking Borrowable Amount
Purpose: See how much can be borrowed without triggering rebalancing
Formula: (effectiveCollateral / targetHealth) - effectiveDebt
Returns: Amount that can be borrowed while maintaining target health (0 if already at/below target)
Checking Required Repayment
Purpose: See how much must be repaid to restore health
Formula: effectiveDebt - (effectiveCollateral / targetHealth)
Returns: Amount that must be repaid to reach target health (0 if already at/above target)
_11// Check borrowable amount above target health_11let available = position.fundsAvailableAboveTargetHealth()_11if available > 0.0 {_11 // Can borrow 'available' amount without triggering rebalancing_11}_11_11// Check required repayment for target health_11let required = position.fundsRequiredForTargetHealth()_11if required > 0.0 {_11 // Must repay 'required' amount to restore health_11}
See GitHub for complete API documentation.
Manual vs Automatic Rebalancing
_13graph TB_13 subgraph Automatic_13 A1[DrawDownSink<br/>Configured] --> A2[TopUpSource<br/>Configured]_13 A2 --> A3[✅ Auto-borrow<br/>✅ Auto-repay<br/>✅ Hands-free]_13 end_13_13 subgraph Manual_13 M1[User Monitors<br/>Health] --> M2[User Triggers<br/>Rebalance]_13 M2 --> M3[❌ Manual work<br/>✅ Full control<br/>⚠️ Risk if delayed]_13 end_13_13 style Automatic fill:#bfb_13 style Manual fill:#bbf
Automatic Rebalancing
Advantages: Automatic rebalancing requires no user intervention, maintains optimal capital efficiency, provides protection against liquidation, and enables integration with DeFi strategies.
Requirements: To enable automatic rebalancing, you must configure DrawDownSink for borrowing and TopUpSource for repayment, ensure sufficient funds in TopUpSource, and set up proper automation (keepers or protocol).
Manual Rebalancing
When to use: Manual rebalancing is suitable for testing and learning, conservative management approaches, situations where manual control is preferred, and complex strategy execution.
Process:
- Monitor position health factor regularly
- Detect when health moves outside range
- Manually trigger rebalancing
- Verify new health factor
Rebalancing Best Practices
Setup
- Configure both Sink and Source: Ensures full automation
- Test with small amounts: Verify rebalancing works as expected
- Monitor initial rebalancing: Watch first few cycles
- Fund TopUpSource adequately: Ensure sufficient repayment capacity
Monitoring
- Track rebalancing events: Log when rebalancing occurs
- Monitor gas costs: Frequent rebalancing costs gas
- Watch health factor trends: Identify patterns
- Alert on failures: Know if TopUpSource runs dry
Optimization
- Adjust health ranges: Based on volatility and strategy
- Choose appropriate tokens: Stable collateral = less rebalancing
- Balance efficiency vs stability: Find your risk tolerance
- Consider timing: Some times have better gas prices
Risk Management
- Ensure TopUpSource liquidity: Always have funds available
- Monitor collateral prices: Know when to add collateral manually
- Have backup plans: What if automation fails?
- Regular health checks: Even with automation, monitor positions
Troubleshooting Rebalancing
Rebalancing Not Triggering
_11graph TD_11 Issue[Rebalancing<br/>Not Triggering] --> Check1{Health in<br/>range?}_11 Check1 -->|Yes| OK[Working as<br/>intended]_11 Check1 -->|No| Check2{Sink/Source<br/>configured?}_11 Check2 -->|No| Fix1[Configure<br/>Sink/Source]_11 Check2 -->|Yes| Check3{Funds in<br/>Source?}_11 Check3 -->|No| Fix2[Add funds to<br/>TopUpSource]_11 Check3 -->|Yes| Fix3[Manual trigger<br/>force=true]_11_11 style Issue fill:#fbb_11 style OK fill:#bfb
Possible causes:
- Health within min/max range (working as intended)
- DrawDownSink not configured
- TopUpSource not configured or empty
- Automation not running
Solutions: Verify the health factor is outside the target range, check Sink/Source configuration, ensure sufficient funds in Source, and manually trigger with force: true if needed.
Rebalancing Fails
Possible causes:
- TopUpSource has insufficient funds
- Oracle price stale or unavailable
- Gas limit exceeded
- Smart contract error
Solutions: Add funds to TopUpSource, wait for fresh oracle updates, increase the gas limit, and check contract logs for specific errors.
Excessive Rebalancing
Possible causes:
- Health range too narrow
- Highly volatile collateral
- Oracle price updates too frequent
Solutions: Widen the health range (increase maxHealth - minHealth), use more stable collateral, adjust target health to the middle of the range, and consider switching to a conservative strategy.
Summary
Rebalancing Mechanics:
- 📊 Maintains health factor in target range (1.1 - 1.5)
- 🔄 Automatic borrowing when overcollateralized (HF > 1.5)
- 🛡️ Automatic repayment when undercollateralized (HF < 1.1)
- 🎯 Targets optimal health factor (1.3)
Key Integrations:
- DrawDownSink: Where borrowed funds go (overcollateralized)
- TopUpSource: Where repayment funds come from (undercollateralized)
- DeFi Actions: Framework enabling automated flows
Strategy Selection:
- Conservative: Wide range (1.2-2.0), stable, low efficiency
- Balanced: Moderate range (1.1-1.5), recommended for most
- Aggressive: Narrow range (1.1-1.3), risky, max efficiency
Best Practices:
- Configure both Sink and Source for full automation
- Ensure TopUpSource has sufficient liquidity
- Monitor rebalancing events and health trends
- Choose strategy based on collateral volatility
Mathematical Foundation
For detailed rebalancing formulas and calculations:
- Overcollateralized Math: Overcollateralized Rebalancing
- Undercollateralized Math: Undercollateralized Rebalancing
- Health Factor Formulas: Health Factor Mathematics
- Price Impact on Rebalancing: Price Impact Analysis
Next Steps
- Understand automation: DeFi Actions Integration
- See the big picture: Position Lifecycle
- Explore liquidation protection: Liquidation System
- Learn credit mechanics: Credit Market Mechanics
Rebalancing is ALP's secret weapon for capital efficiency. By automatically adjusting debt based on collateral value changes, it keeps positions optimized while protecting against liquidation. Combined with FYV as TopUpSource, you get truly hands-free DeFi lending!