// SPDX-License-Identifier: MIT pragma solidity ^0.8.20; import {Test, console} from "forge-std/Test.sol"; import {AtomicExecutor} from "../AtomicExecutor.sol"; // Mock target contract for testing contract MockTarget { bool public testCalled = false; uint256 public value; function test() external { testCalled = true; } function setValue(uint256 _value) external { value = _value; } function revertTest() external pure { revert("Test revert"); } } contract AtomicExecutorTest is Test { AtomicExecutor executor; MockTarget target; address owner = address(1); address user = address(2); function setUp() public { vm.prank(owner); executor = new AtomicExecutor(owner); target = new MockTarget(); vm.prank(owner); executor.setAllowedTarget(address(target), true); } function testBatchExecute() public { address[] memory targets = new address[](1); bytes[] memory calldatas = new bytes[](1); targets[0] = address(target); calldatas[0] = abi.encodeWithSignature("test()"); vm.prank(user); executor.executeBatch(targets, calldatas); assertTrue(target.testCalled()); } function testBatchExecuteMultiple() public { address[] memory targets = new address[](2); bytes[] memory calldatas = new bytes[](2); targets[0] = address(target); calldatas[0] = abi.encodeWithSignature("setValue(uint256)", 100); targets[1] = address(target); calldatas[1] = abi.encodeWithSignature("setValue(uint256)", 200); vm.prank(user); executor.executeBatch(targets, calldatas); assertEq(target.value(), 200); } function testAllowListEnforcement() public { address newTarget = address(3); address[] memory targets = new address[](1); bytes[] memory calldatas = new bytes[](1); targets[0] = newTarget; calldatas[0] = abi.encodeWithSignature("test()"); vm.prank(user); vm.expectRevert("Target not allowed"); executor.executeBatch(targets, calldatas); } function testAllowListDisabled() public { address newTarget = address(3); vm.prank(owner); executor.setAllowListEnabled(false); address[] memory targets = new address[](1); bytes[] memory calldatas = new bytes[](1); targets[0] = newTarget; calldatas[0] = abi.encodeWithSignature("test()"); vm.prank(user); executor.executeBatch(targets, calldatas); // Should succeed } function testPause() public { vm.prank(owner); executor.pause(); address[] memory targets = new address[](1); bytes[] memory calldatas = new bytes[](1); targets[0] = address(target); calldatas[0] = abi.encodeWithSignature("test()"); vm.prank(user); vm.expectRevert(); executor.executeBatch(targets, calldatas); } function testUnpause() public { vm.prank(owner); executor.pause(); vm.prank(owner); executor.unpause(); address[] memory targets = new address[](1); bytes[] memory calldatas = new bytes[](1); targets[0] = address(target); calldatas[0] = abi.encodeWithSignature("test()"); vm.prank(user); executor.executeBatch(targets, calldatas); // Should succeed } function testRevertPropagation() public { address[] memory targets = new address[](1); bytes[] memory calldatas = new bytes[](1); targets[0] = address(target); calldatas[0] = abi.encodeWithSignature("revertTest()"); vm.prank(user); vm.expectRevert("Test revert"); executor.executeBatch(targets, calldatas); } function testSetAllowedPool() public { address pool = address(0x123); vm.prank(owner); executor.setAllowedPool(pool, true); assertTrue(executor.allowedPools(pool)); } function testOnlyOwnerCanSetPool() public { address pool = address(0x123); vm.prank(user); vm.expectRevert(); executor.setAllowedPool(pool, true); } }