Building on Mezo
Things we learned the hard way while building Feasy. They may save you a day.
Precompiles
- 20 calls per transaction. The BTC token and the price oracle are precompiles.
PriceFeed.fetchPrice()costs two calls. The 21st call burns all of its gas. Read the price once per transaction and pass it down. - The cap applies to views too. A multicall of price-reading views inside one
eth_callcosts two calls per view. - The cap survives
try/catch. Past 20 calls, every later call fails, even insidetry. A reverted call still counts. - Forks can’t run Mezo. Test on testnet with real transactions and
eth_callstate overrides.
Gas
- Estimates come in low.
eth_estimateGasundershoots calls that go through the BTC precompile. Mezo bills the larger of gas used and half the limit. So a 1.5x pad costs nothing. Wallet front ends should pad too. - Estimates and
try/catch. The estimator looks for the smallest limit that does not revert. If atryswallows an out-of-gas, that limit is one where the caught call quietly fails. Checkgasleft()before each caught call and give it a fixed budget. - Hints must be deterministic. A sorted-list hint seeded with the block number samples different troves at estimation and at execution. Gas then swings by about 25%. Seed it with something stable, like the target ratio.
MUSD
- Borrowing capacity is frozen at open. A trove’s
maxBorrowingCapacityis set from its collateral when it opens. Adding collateral does not raise it. Add collateral,refinance(), then borrow. - The loan owes MUSD you never received. The 0.1% fee and the interest are added to the debt. Left alone, that gap stays with whoever exits last. Buy it back right after borrowing.
- Mezo refuses closes that hurt the system.
closeTrovereverts if the system ratio would end under 150%. The last trove can never close. - Max views move every second. Interest accrues live, so
maxWithdrawcan drop by a few wei between reading and sending. Leave 0.001% of room.
Savings and the DEX
- sMUSD is not ERC-4626. It is a 1:1 receipt token with a yield index.
withdrawalso pays out all accrued yield. - A paused DEX still quotes. One key can pause the pool factory. Its pools then refuse every swap while
getAmountsOutkeeps quoting. CheckisPaused()before trusting a quote.
Mezo Earn
- The public repo is not what is deployed. tigris on GitHub differs from the verified testnet veBTC, Voter and gauge sources by hundreds of lines. Use the verified explorer source.
- Votes have a window. Votes and resets open an hour after the Thursday 00:00 UTC flip and close an hour before the next.
- Voted locks can’t be withdrawn. Reset the lock first.
- Rebates need a nudge. The weekly rebate can’t be claimed until someone runs the fee splitter’s
updatePeriod(). Anyone can. - The first write pays the catch-up. veBTC’s first write after a flip pays the weekly checkpoint for everyone. Call
checkpoint()first if your claim runs on a tight gas budget.
RPC
eth_getLogsreturnsblockTimestampas0x0. Read times from blocks.- Log queries are capped at 10,000 blocks. Page them.