111 lines
3.2 KiB
Solidity
111 lines
3.2 KiB
Solidity
// SPDX-License-Identifier: MIT
|
|
pragma solidity ^0.8.20;
|
|
|
|
import "../interfaces/IAavePool.sol";
|
|
import "../interfaces/IERC20.sol";
|
|
|
|
/**
|
|
* @title AaveFlashLoanReceiver
|
|
* @notice Example flash loan receiver for Aave v3
|
|
* @dev This contract receives flash loans and must repay them in executeOperation
|
|
*/
|
|
contract AaveFlashLoanReceiver is IFlashLoanReceiver {
|
|
IAavePool public immutable pool;
|
|
address public owner;
|
|
|
|
modifier onlyOwner() {
|
|
require(msg.sender == owner, "Not owner");
|
|
_;
|
|
}
|
|
|
|
constructor(address pool_) {
|
|
pool = IAavePool(pool_);
|
|
owner = msg.sender;
|
|
}
|
|
|
|
/**
|
|
* @notice Execute flash loan operation
|
|
* @param asset The flash loaned asset
|
|
* @param amount The flash loaned amount
|
|
* @param premium The premium to repay
|
|
* @param initiator The initiator of the flash loan
|
|
* @param params Additional parameters (can encode arbitrage data, etc.)
|
|
* @return true if successful
|
|
*/
|
|
function executeOperation(
|
|
address asset,
|
|
uint256 amount,
|
|
uint256 premium,
|
|
address initiator,
|
|
bytes calldata params
|
|
) external override returns (bool) {
|
|
// Verify this was called by the pool
|
|
require(msg.sender == address(pool), "Invalid caller");
|
|
require(initiator == address(this), "Invalid initiator");
|
|
|
|
// Your logic here (e.g., arbitrage, liquidation, etc.)
|
|
// Example: swap on DEX, arbitrage, etc.
|
|
|
|
// Calculate total amount to repay (loan + premium)
|
|
uint256 amountOwed = amount + premium;
|
|
|
|
// Approve pool to take repayment
|
|
IERC20(asset).approve(address(pool), amountOwed);
|
|
|
|
// Return true to indicate successful operation
|
|
return true;
|
|
}
|
|
|
|
/**
|
|
* @notice Execute flash loan (single asset)
|
|
* @param asset The asset to flash loan
|
|
* @param amount The amount to flash loan
|
|
* @param params Additional parameters for executeOperation
|
|
*/
|
|
function flashLoanSimple(
|
|
address asset,
|
|
uint256 amount,
|
|
bytes calldata params
|
|
) external onlyOwner {
|
|
pool.flashLoanSimple(
|
|
address(this),
|
|
asset,
|
|
amount,
|
|
params,
|
|
0 // referral code
|
|
);
|
|
}
|
|
|
|
/**
|
|
* @notice Execute flash loan (multiple assets)
|
|
* @param assets The assets to flash loan
|
|
* @param amounts The amounts to flash loan
|
|
* @param modes The flash loan modes (0 = no debt, 2 = variable debt)
|
|
* @param params Additional parameters for executeOperation
|
|
*/
|
|
function flashLoan(
|
|
address[] calldata assets,
|
|
uint256[] calldata amounts,
|
|
uint256[] calldata modes,
|
|
bytes calldata params
|
|
) external onlyOwner {
|
|
pool.flashLoan(
|
|
address(this),
|
|
assets,
|
|
amounts,
|
|
modes,
|
|
address(this),
|
|
params,
|
|
0 // referral code
|
|
);
|
|
}
|
|
|
|
/**
|
|
* @notice Withdraw tokens (emergency)
|
|
*/
|
|
function withdrawToken(address token, uint256 amount) external onlyOwner {
|
|
IERC20(token).transfer(owner, amount);
|
|
}
|
|
}
|
|
|