creation_sourcecode: {{
    "language": "Solidity",
    "sources": {
      "LiquidityManager.sol": {
        "content": "// SPDX-License-Identifier: -- BCOM --\n\npragma solidity =0.8.25;\n\nimport \"./IERC20.sol\";\nimport \"./ISwapsPair.sol\";\nimport \"./ISwapsRouter.sol\";\n\ncontract LiquidityManager {\n\n    address public owner;\n    address public worker;\n\n    ISwapsPair public pair;\n    ISwapsRouter public router;\n\n    address public token0;\n    address public token1;\n\n    modifier onlyOwner() {\n        require(\n            msg.sender == owner,\n            \"Caller is not the owner\"\n        );\n        _;\n    }\n\n    modifier onlyWorker() {\n        require(\n            msg.sender == worker,\n            \"Caller is not the worker\"\n        );\n        _;\n    }\n\n    event LogQuote(\n        uint256 requiredWethForSwap,\n        uint256 minAmountVerseToBuy,\n        uint256 reserve0,\n        uint256 reserve1\n    );\n\n    event LogOut(\n        uint256 amountWeth,\n        uint256 amountVerse\n    );\n\n    event LogAdded(\n        uint256 addedVerse,\n        uint256 addedWeth,\n        uint256 liquidity\n    );\n\n    constructor() {\n\n        owner = msg.sender;\n        worker = msg.sender;\n\n        router = ISwapsRouter(\n            0xB4B0ea46Fe0E9e8EAB4aFb765b527739F2718671\n        );\n\n        token0 = 0x249cA82617eC3DfB2589c4c17ab7EC9765350a18;\n        token1 = 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2;\n\n        IERC20(token0).approve(\n            address(router),\n            type(uint256).max\n        );\n\n        IERC20(token1).approve(\n            address(router),\n            type(uint256).max\n        );\n\n        pair = ISwapsPair(\n            router.pairFor(\n                router.FACTORY(),\n                token0,\n                token1\n            )\n        );\n\n        pair.approve(\n            address(router),\n            type(uint256).max\n        );\n    }\n\n    function buyBackVerseToken(\n        uint256 _liquidityAmountToUse,\n        uint256 _expectMinVerseRemoved,\n        uint256 _expectMinWethRemoved,\n        uint256 _minAmountVerseToBuy,\n        uint256 _maxAmountWethForSwap,\n        uint256 _desiredVerseToAddBack,\n        uint256 _desiredWethToAddBack,\n        uint256 _expectMinVerseToAddBack,\n        uint256 _expectMinWethToAddBack\n    )\n        external\n        onlyWorker\n    {\n        pair.approve(\n            address(router),\n            _liquidityAmountToUse\n        );\n\n        (\n            uint256 _amountVerse,\n            uint256 _amountWeth\n        ) = router.removeLiquidity(\n            token0,\n            token1,\n            _liquidityAmountToUse,\n            _expectMinVerseRemoved,\n            _expectMinWethRemoved,\n            address(this),\n            block.timestamp\n        );\n\n        emit LogOut(\n            _amountWeth,\n            _amountVerse\n        );\n\n        (\n            uint256 reserve0,\n            uint256 reserve1,\n        ) = pair.getReserves();\n\n        uint256 requiredWethForSwap = router.quote(\n            _minAmountVerseToBuy,\n            reserve0,\n            reserve1\n        );\n\n        emit LogQuote(\n            requiredWethForSwap,\n            _minAmountVerseToBuy,\n            reserve0,\n            reserve1\n        );\n\n        if (requiredWethForSwap > _maxAmountWethForSwap) {\n            revert(\"LiquidityManager: TOO_EXPENSIVE\");\n        }\n\n        router.swapExactTokensForTokens(\n            _maxAmountWethForSwap,\n            _minAmountVerseToBuy,\n            _getSwapPathFromWethToVerse(),\n            address(this),\n            block.timestamp\n        );\n\n        IERC20(token0).approve(\n            address(router),\n            _desiredVerseToAddBack\n        );\n\n        IERC20(token1).approve(\n            address(router),\n            _desiredWethToAddBack\n        );\n\n        (\n            uint256 addedVerse,\n            uint256 addedWeth,\n            uint256 liquidity\n        ) = router.addLiquidity(\n            token0,\n            token1,\n            _desiredVerseToAddBack,\n            _desiredWethToAddBack,\n            _expectMinVerseToAddBack,\n            _expectMinWethToAddBack,\n            address(this),\n            block.timestamp\n        );\n\n        emit LogAdded(\n            addedVerse,\n            addedWeth,\n            liquidity\n        );\n    }\n\n    function buyBackVerseTokenSimple(\n        uint256 _liquidityAmountToUse,\n        uint256 _expectMinVerseRemoved,\n        uint256 _expectMinWethRemoved,\n        uint256 _minAmountVerseToBuy,\n        uint256 _maxAmountWethForSwap,\n        uint256 _expectMinVerseToAddBack,\n        uint256 _expectMinWethToAddBack\n    )\n        external\n        onlyWorker\n    {\n        (\n            uint256 _amountVerse,\n            uint256 _amountWeth\n        ) = router.removeLiquidity(\n            token0,\n            token1,\n            _liquidityAmountToUse,\n            _expectMinVerseRemoved,\n            _expectMinWethRemoved,\n            address(this),\n            block.timestamp\n        );\n\n        emit LogOut(\n            _amountWeth,\n            _amountVerse\n        );\n\n        (\n            uint256 reserve0,\n            uint256 reserve1,\n        ) = pair.getReserves();\n\n        uint256 requiredWethForSwap = router.quote(\n            _minAmountVerseToBuy,\n            reserve0,\n            reserve1\n        );\n\n        emit LogQuote(\n            requiredWethForSwap,\n            _minAmountVerseToBuy,\n            reserve0,\n            reserve1\n        );\n\n        if (requiredWethForSwap > _maxAmountWethForSwap) {\n            revert(\"LiquidityManager: TOO_EXPENSIVE\");\n        }\n\n        router.swapExactTokensForTokens(\n            _maxAmountWethForSwap,\n            _minAmountVerseToBuy,\n            _getSwapPathFromWethToVerse(),\n            address(this),\n            block.timestamp\n        );\n\n        (\n            uint256 addedVerse,\n            uint256 addedWeth,\n            uint256 liquidity\n        ) = router.addLiquidity(\n            token0,\n            token1,\n            IERC20(token0).balanceOf(address(this)),\n            IERC20(token1).balanceOf(address(this)),\n            _expectMinVerseToAddBack,\n            _expectMinWethToAddBack,\n            address(this),\n            block.timestamp\n        );\n\n        emit LogAdded(\n            addedVerse,\n            addedWeth,\n            liquidity\n        );\n    }\n\n    function withdrawTokens(\n        address _token,\n        address _to,\n        uint256 _amount\n    )\n        external\n        onlyOwner\n    {\n        IERC20(_token).transfer(\n            _to,\n            _amount\n        );\n    }\n\n    function withdrawETH(\n        address _to,\n        uint256 _amount\n    )\n        external\n        onlyOwner\n    {\n        payable(_to).transfer(\n            _amount\n        );\n    }\n\n    function setWorker(\n        address _worker\n    )\n        external\n        onlyOwner\n    {\n        worker = _worker;\n    }\n\n    function setOwner(\n        address _owner\n    )\n        external\n        onlyOwner\n    {\n        owner = _owner;\n    }\n\n    function getVerseBalanceSelf()\n        public\n        view\n        returns (uint256)\n    {\n        return IERC20(token0).balanceOf(\n            address(this)\n        );\n    }\n\n    function getWethBalanceSelf()\n        public\n        view\n        returns (uint256)\n    {\n        return IERC20(token1).balanceOf(\n            address(this)\n        );\n    }\n\n    function _getSwapPathFromWethToVerse()\n        private\n        view\n        returns (address[] memory path)\n    {\n        path = new address[](2);\n        path[0] = token1; // WETH\n        path[1] = token0; // VERSE\n    }\n}\n"
      },
      "ISwapsRouter.sol": {
        "content": "// SPDX-License-Identifier: -- BCOM --\n\npragma solidity =0.8.25;\n\ninterface ISwapsRouter {\n\n    function WETH()\n        external\n        returns (address);\n\n    function addLiquidity(\n        address tokenA,\n        address tokenB,\n        uint256 amountADesired,\n        uint256 amountBDesired,\n        uint256 amountAMin,\n        uint256 amountBMin,\n        address to,\n        uint256 deadline\n    )\n        external\n        returns (\n            uint256 amountA,\n            uint256 amountB,\n            uint256 liquidity\n        );\n\n    function swapExactTokensForTokens(\n        uint256 amountIn,\n        uint256 amountOutMin,\n        address[] calldata path,\n        address to,\n        uint256 deadline\n    )\n        external\n        returns (\n            uint[] memory amounts\n        );\n\n    function removeLiquidity(\n        address tokenA,\n        address tokenB,\n        uint256 liquidity,\n        uint256 amountAMin,\n        uint256 amountBMin,\n        address to,\n        uint256 deadline\n    )\n        external\n        returns (\n            uint256 amountA,\n            uint256 amountB\n        );\n\n    function getReserves(\n        address factory,\n        address tokenA,\n        address tokenB\n    )\n        external\n        view\n        returns (\n            uint112 reserveA,\n            uint112 reserveB,\n            uint32 blockTimestampLast\n        );\n\n    function FACTORY()\n        external\n        view\n        returns (address);\n\n    function quote(\n        uint256 amountA,\n        uint256 reserveA,\n        uint256 reserveB\n    )\n        external\n        pure\n        returns (uint256 amountB);\n\n    function pairFor(\n        address factory,\n        address tokenA,\n        address tokenB\n    )\n        external\n        pure\n        returns (address);\n}\n"
      },
      "ISwapsPair.sol": {
        "content": "// SPDX-License-Identifier: BCOM\n\npragma solidity =0.8.25;\n\nimport \"./ISwapsERC20.sol\";\n\ninterface ISwapsPair is ISwapsERC20 {\n\n    function MINIMUM_LIQUIDITY()\n        external\n        pure\n        returns (uint256);\n\n    function factory()\n        external\n        view\n        returns (address);\n\n    function token0()\n        external\n        view\n        returns (address);\n\n    function token1()\n        external\n        view\n        returns (address);\n\n    function getReserves()\n        external\n        view\n        returns (\n            uint112 reserve0,\n            uint112 reserve1,\n            uint32 blockTimestampLast\n        );\n\n    function price0CumulativeLast()\n        external\n        view\n        returns (uint256);\n\n    function price1CumulativeLast()\n        external\n        view\n        returns (uint256);\n\n    function kLast()\n        external\n        view\n        returns (uint256);\n\n    function mint(\n        address _to\n    )\n        external\n        returns (uint256 liquidity);\n\n    function burn(\n        address _to\n    )\n        external\n        returns (\n            uint256 amount0,\n            uint256 amount1\n        );\n\n    function swap(\n        uint256 _amount0Out,\n        uint256 _amount1Out,\n        address _to,\n        bytes calldata _data\n    )\n        external;\n\n    function skim()\n        external;\n\n    function initialize(\n        address,\n        address\n    )\n        external;\n}\n"
      },
      "IERC20.sol": {
        "content": "// SPDX-License-Identifier: -- BCOM --\n\npragma solidity =0.8.25;\n\ninterface IERC20 {\n\n    function balanceOf(\n        address _owner\n    )\n        external\n        view\n        returns (uint256);\n\n    function transfer(\n        address _to,\n        uint256 _value\n    )\n        external\n        returns (bool);\n\n    function transferFrom(\n        address _from,\n        address _to,\n        uint256 _value\n    )\n        external\n        returns (bool);\n\n    function approve(\n        address _spender,\n        uint256 _value\n    )\n        external\n        returns (bool);\n}\n"
      },
      "ISwapsERC20.sol": {
        "content": "// SPDX-License-Identifier: BCOM\n\npragma solidity =0.8.25;\n\ninterface ISwapsERC20 {\n\n    function name()\n        external\n        pure\n        returns (string memory);\n\n    function symbol()\n        external\n        pure\n        returns (string memory);\n\n    function decimals()\n        external\n        pure\n        returns (uint8);\n\n    function totalSupply()\n        external\n        view\n        returns (uint256);\n\n    function balanceOf(\n        address _owner\n    )\n        external\n        view\n        returns (uint256);\n\n    function allowance(\n        address _owner,\n        address _spender\n    )\n        external\n        view\n        returns (uint256);\n\n    function approve(\n        address _spender,\n        uint256 _value\n    )\n        external\n        returns (bool);\n\n    function transfer(\n        address _to,\n        uint256 _value\n    )\n        external\n        returns (bool);\n\n    function transferFrom(\n        address _from,\n        address _to,\n        uint256 _value\n    )\n        external\n        returns (bool);\n\n    function DOMAIN_SEPARATOR()\n        external\n        view\n        returns (bytes32);\n\n    function PERMIT_TYPEHASH()\n        external\n        pure\n        returns (bytes32);\n\n    function nonces(\n        address _owner\n    )\n        external\n        view\n        returns (uint256);\n\n    function permit(\n        address _owner,\n        address _spender,\n        uint256 _value,\n        uint256 _deadline,\n        uint8 _v,\n        bytes32 _r,\n        bytes32 _s\n    )\n        external;\n}\n"
      }
    },
    "settings": {
      "optimizer": {
        "enabled": true,
        "runs": 200
      },
      "outputSelection": {
        "*": {
          "*": [
            "evm.bytecode",
            "evm.deployedBytecode",
            "devdoc",
            "userdoc",
            "metadata",
            "abi"
          ]
        }
      }
    }
  }}