闪电贷简介
uniswap 中提供了闪电贷功能,大概的意思是用户可以无担保地先借钱,然后用钱,最后再还钱。可以无担保地放心借钱,是因为借钱和还钱都是在同一笔交易中,借贷合约会在最后的逻辑中校验是否归还借款及手续费,如果没有,则回滚整个事务。而用户使用闪电贷的动机可以是 去借贷协议如 AAVE中清算资产或者MEV获利。
Uniswap 核心函数解析
1: 第20行是闪电贷的核心,uniswap的借款合约会根据data是否为空来判断是否是需要回调用户自己的闪电贷合约的逻辑。
2: 31~33行,是还款验证的逻辑,通过验证恒定乘积来确认用户在该笔交易中最终还款了。
用户合约逻辑
(合约的全部代码可见 uniswapFlashLoan)
上面的例子中,举例是只借款 USDTETH 交易池中的 usdt (金额由用户输入)。通过在调用交易池的参数中输入非空的 _data字段, 指示 Uniswap的池子合约回调本合约。
以上代码是用户合约的回调函数,就是用户真正用借来的钱要干的事情。为了方便演示,这里举例用户用借来的 usdt 兑换 usdc, 然后用usdc 兑换 weth, 最后用weth 来偿还从 USDTETH 池子中借的贷款usdt。因为整个流程会产生swap 费用,所以兑换的weth肯定是不够偿还 借的usdt的,因此为了保证整个交易的成功,必须在触发 flashLoan 函数前通过 调用 deposit()函数给该合约充点 weth(该函数逻辑可见 GitHub整个项目)。
运行
整个测试逻辑是借助于 hardhat+ ganache(fork Ethereum 主网)的方式完成的。测试脚本如下
上述的测试流程也可以采用 remix的方式进行,但是remix 没有脚本灵活。测试逻辑主要分两步,充值weth 和 触发 flashLoan. 测试结果如下,可以看见 weth在整个过程中是有耗损的。