harb/onchain/test/helpers/UniswapTestBase.sol
giteadmin bb34d0725f feature/simulations (#11)
this pull request:
- creates a unit test that can take any scenario file (default: `out/scenario.json` and play it back on the deployment
- during the playback a debug trace generated in `timeSeries.csv`
- extracts the sentimenter into a separate upgradeable contract

Co-authored-by: JulesCrown <admin@noip.localhost>
Co-authored-by: giteadmin <gite@admin.com>
Reviewed-on: http://gitea.loseyourip.com:4000/dark-meme-society/harb/pulls/11
2024-11-07 15:33:40 +00:00

81 lines
2.3 KiB
Solidity

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.19;
import "forge-std/Test.sol";
import "@uniswap-v3-core/interfaces/IUniswapV3Pool.sol";
import {TickMath} from "@aperture/uni-v3-lib/TickMath.sol";
import "../../src/interfaces/IWETH9.sol";
import {Harberg} from "../../src/Harberg.sol";
/**
* @title UniswapTestBase
* @dev Base contract for Uniswap V3 testing, providing reusable swap logic.
*/
abstract contract UniswapTestBase is Test {
address account = makeAddr("alice");
IUniswapV3Pool public pool;
IWETH9 public weth;
Harberg public harberg;
bool public token0isWeth;
/**
* @dev Performs a swap in the Uniswap V3 pool.
* @param amount The amount to swap.
* @param isBuy True if buying WETH, false if selling.
*/
function performSwap(uint256 amount, bool isBuy) internal {
uint160 limit;
// Determine the swap direction
bool zeroForOne = isBuy ? token0isWeth : !token0isWeth;
if (isBuy) {
vm.prank(account);
weth.transfer(address(this), amount);
} else {
vm.prank(account);
harberg.approve(address(this), amount);
}
// Set the sqrtPriceLimitX96 based on the swap direction
if (zeroForOne) {
// Swapping token0 for token1
// sqrtPriceLimitX96 must be less than current price but greater than MIN_SQRT_RATIO
limit = TickMath.MIN_SQRT_RATIO + 1;
} else {
// Swapping token1 for token0
// sqrtPriceLimitX96 must be greater than current price but less than MAX_SQRT_RATIO
limit = TickMath.MAX_SQRT_RATIO - 1;
}
pool.swap(
account,
zeroForOne,
int256(amount),
limit,
abi.encode(account, int256(amount), isBuy)
);
}
/**
* @dev The Uniswap V3 swap callback.
*/
function uniswapV3SwapCallback(
int256 amount0Delta,
int256 amount1Delta,
bytes calldata _data
) external {
require(amount0Delta > 0 || amount1Delta > 0);
(address seller, , bool isBuy) = abi.decode(_data, (address, uint256, bool));
(, uint256 amountToPay) = amount0Delta > 0
? (!token0isWeth, uint256(amount0Delta))
: (token0isWeth, uint256(amount1Delta));
if (isBuy) {
weth.transfer(msg.sender, amountToPay);
} else {
require(harberg.transferFrom(seller, msg.sender, amountToPay), "Transfer failed");
}
}
}