Conversation
6de117f to
c6a0634
Compare
e55de25 to
48ef07b
Compare
|
@jribbink @jordanschalm |
| let vaultBalAfter = _executeScript("../scripts/flow-yield-vaults/get_yield_vault_balance.cdc", [wbtcUser.address, wbtcVaultID]) | ||
| Test.expect(vaultBalAfter, Test.beSucceeded()) | ||
| Test.assert(vaultBalAfter.returnValue == nil, message: "WBTC vault should no longer exist after close") | ||
| log("WBTC yield vault closed successfully") |
There was a problem hiding this comment.
Can we also add assertion to check that after closing the yield vault, the debt is reduced.
We might want to assert that after opening and closing the yield vault, the total collateral amount should be very close to the original amount, there should be only a tiny amount loss due to running into the code path of expectedMOET < totalDebtAmount where some collateral has to be sold, right?
| return self.swapper.quoteOut(forProvided: avail, reverse: false).outAmount | ||
| } | ||
| /// Pulls ALL available yield tokens from the source and swaps them to the debt token. | ||
| /// Ignores quoteIn — avoids ERC4626 rounding underestimates that would leave us short. |
| assert(extraCollateral.balance > 0.0, | ||
| message: "Pre-supplement: no collateral available to cover shortfall of \(shortfall) MOET") | ||
| let extraMOET <- collateralToMoetSwapper.swap(quote: quote, inVault: <-extraCollateral) | ||
| assert(extraMOET.balance > 0.0, |
There was a problem hiding this comment.
should we just assert extraMOET.balance > shortfall?
| collateralType: collateralType, | ||
| uniqueID: self.uniqueID! | ||
| ) | ||
| let shortfall = totalDebtAmount - expectedMOET |
There was a problem hiding this comment.
where is the ERC4626 connector?
yieldToMoetSwapper = MultiSwapper containing:
└── SequentialSwapper:
1. yieldToUnderlying ← MorphoERC4626SwapConnectors.Swapper (isReversed: true)
2. underlyingToDebt ← UniV3 swapper
So the flow is:
BufferedSwapSource
├── source: yieldTokenSource (AutoBalancer external source - just pulls yield tokens)
└── swapper: yieldToMoetSwapper
└── yieldToken → [ERC4626 redeem] → underlying → [UniV3] → MOET
The ERC4626 is inside the swapper — specifically yieldToUnderlying which redeems ERC4626 shares (FUSDEV) back to the underlying asset (PYUSD0), then underlyingToDebt swaps that to MOET via Uniswap.
I think the "at least two hops" Alex mentioned is the "yieldToken → [ERC4626 redeem] → underlying → [UniV3] → MOET" swap route, which is previewed with " FUSDEV → [ERC4626 previewRedeem, floor] → PYUSD0 → [UniV3 quote] → MOET"
But I think the shortfall is actually accurate (Meaning shortfall is always slightly bigger than the actual shortfall, rather than smaller). In other words, I think we don't need the 1% buffer. Why? because the expectedMOET is accurate.
The pre-supplyment already paid the shortfall (self.position.deposit(from: <-extraMOET)), which is slightly more than the actual shortfall , so closing the position with yield token wrapped with SwapSource should be enough to receive the remaining MOET after swap.
Note the pre-supplyment is converting to and paying debts with MOET rather than the yield token, so there is no more ERC4626 rounding error to be hit. The ERC4626 rounding error has been covered by the calculation of expectedMOET.
I think we can validate by removing the 1% buffer and add assertion for extraMOET.balance > shortfall. If closePosition didn't revert, then we should be good. Or did I miss something?
|
@zhangchiqing you're right, the 1% buffer is not required any more after all other roundings. |
Codecov Report❌ Patch coverage is
📢 Thoughts on this report? Let us know! |
| // any surplus shares are still held by the AutoBalancer and are recovered here. | ||
| let excessShares <- yieldTokenSource.withdrawAvailable(maxAmount: UFix64.max) | ||
| if excessShares.balance > 0.0 { | ||
| let moetQuote = yieldToMoetSwapper.quoteOut(forProvided: excessShares.balance, reverse: false) |
There was a problem hiding this comment.
Would it be better to build a sequential swapper from yield -> moet -> collateral? That way we only need to do 1 quote (from yield to collateral), and decide whether to swap: if collQuote.outAmount == 0, we could just burn all the yield token without converting them to moet and then burn.
There was a problem hiding this comment.
yes, sequential swapper is definitely way to go, I left it bare for now as we need to rip MOET out of the strategy, and I feel that with this it will be more obvious where it needs to be removed
Co-authored-by: Leo Zhang <zhangchiqing@gmail.com>

Closes: #???
Description
this PR contains bulk changes related only to FUSDEV strategy from #183
so it's easier to review just the strategy itself withoutt the second strategy
For contributor use:
masterbranchFiles changedin the Github PR explorer