Skip to content
This repository was archived by the owner on Nov 17, 2025. It is now read-only.

Commit 6424d56

Browse files
authored
Merge pull request #547 from bancorprotocol/release-candidate
Release candidate - Linea support and static data
2 parents fc5325b + c7ad17e commit 6424d56

33 files changed

+393535
-309595
lines changed

.env.example

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@ export WEB3_ALCHEMY_PROJECT_ID="0-USE-YOUR-OWN-ALCHEMY-PROJECT-ID-HERE"
22
export ETH_PRIVATE_KEY_BE_CAREFUL="0x123-USE-YOUR-OWN-PRIVATE-KEY-HERE"
33
export WEB3_FANTOM="FANTOM-API-KEY-HERE" // "public" can be used in place of a paid API key
44
export WEB3_MANTLE="MANTLE-API-KEY-HERE"
5+
export WEB3_LINEA="LINEA-API-KEY-HERE" //
6+
57
#******** For Development - not required to run bot ********#
68
export ETHERSCAN_TOKEN="ONLY_REQUIRED_IN_DEV"
79
export TENDERLY_FORK_ID=

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,7 @@ export ETH_PRIVATE_KEY_BE_CAREFUL="0x9c..."
112112
export WEB3_ALCHEMY_BASE="api_key_here"
113113
export WEB3_FANTOM="api_key_here"
114114
export WEB3_MANTLE="api_key_here"
115-
115+
export WEB3_LINEA="api_key_here"
116116
```
117117
**Note:** To use the Fantom public RPC, write "public" in place of the API key.
118118

fastlane_bot/config/connect.py

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
from eth_typing import HexStr
1212
from hexbytes import HexBytes
1313
from web3 import Web3, AsyncWeb3
14+
from web3.middleware import geth_poa_middleware
1415
from web3.types import TxReceipt
1516

1617
import os
@@ -155,7 +156,7 @@ def increment_nonce(self) -> None:
155156
"""
156157
self.nonce += 1
157158

158-
def connect_network(self):
159+
def connect_network(self, inject_poa_middleware):
159160
"""
160161
Connect to the network
161162
"""
@@ -167,5 +168,9 @@ def connect_network(self):
167168
self.web3 = Web3(Web3.HTTPProvider(self.provider_url, request_kwargs={'timeout': 60}))
168169
self.w3_async = AsyncWeb3(AsyncWeb3.AsyncHTTPProvider(self.provider_url))
169170

171+
if inject_poa_middleware:
172+
self.web3.middleware_onion.inject(geth_poa_middleware, layer=0)
173+
self.w3_async.middleware_onion.inject(geth_poa_middleware, layer=0)
174+
170175
logger.info(f"Connected to {self.network_id} network")
171176
logger.info(f"Connected to {self.web3.provider.endpoint_uri} network")

fastlane_bot/config/constants.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,3 +22,6 @@
2222
CARBON_V1_NAME = "carbon_v1"
2323
VELOCIMETER_V2_NAME = "velocimeter_v2"
2424
SOLIDLY_V2_NAME = "solidly_v2"
25+
ECHODEX_V3_NAME = "echodex_v3"
26+
SECTA_V3_NAME = "secta_v3"
27+
METAVAULT_V3_NAME = "metavault_v3"

fastlane_bot/config/network.py

Lines changed: 42 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -197,7 +197,7 @@ class ConfigNetwork(ConfigBase):
197197
# ACCOUNTS SECTION
198198
#######################################################################################
199199
BINANCE8_WALLET_ADDRESS = "0xF977814e90dA44bFA03b6295A0616a897441aceC"
200-
BINANCE14_WALLET_ADDRESS = "0x28c6c06298d514db089934071355e5743bf21d60"
200+
BINANCE14_WALLET_ADDRESS = "0x28C6c06298d514Db089934071355E5743bf21d60"
201201

202202
# EXCHANGE IDENTIFIERS SECTION
203203
#######################################################################################
@@ -256,7 +256,7 @@ class ConfigNetwork(ConfigBase):
256256

257257
# DEFAULT VALUES SECTION
258258
#######################################################################################
259-
UNIV3_FEE_LIST = [80, 100, 250, 450, 500, 2500, 3000, 10000]
259+
UNIV3_FEE_LIST = [8, 10, 40, 80, 100, 250, 300, 450, 500, 1000, 2500, 3000, 10000]
260260
MIN_BNT_LIQUIDITY = 2_000_000_000_000_000_000
261261
DEFAULT_GAS = 950_000
262262
DEFAULT_GAS_PRICE = 0
@@ -278,6 +278,7 @@ class ConfigNetwork(ConfigBase):
278278
LIMIT_BANCOR3_FLASHLOAN_TOKENS = True
279279
DEFAULT_MIN_PROFIT_GAS_TOKEN = Decimal("0.02")
280280

281+
IS_INJECT_POA_MIDDLEWARE = False
281282
# SUNDRY SECTION
282283
#######################################################################################
283284
COINGECKO_URL = "https://tokens.coingecko.com/uniswap/all.json"
@@ -292,6 +293,7 @@ class ConfigNetwork(ConfigBase):
292293
NETWORK_OPTIMISM = S.NETWORK_OPTIMISM
293294
NETWORK_FANTOM = S.NETWORK_FANTOM
294295
NETWORK_MANTLE = S.NETWORK_MANTLE
296+
NETWORK_LINEA = S.NETWORK_LINEA
295297

296298
# FLAGS
297299
#######################################################################################
@@ -321,6 +323,8 @@ def new(cls, network=None):
321323
return _ConfigNetworkFantom(_direct=False)
322324
elif network == cls.NETWORK_MANTLE:
323325
return _ConfigNetworkMantle(_direct=False)
326+
elif network == cls.NETWORK_LINEA:
327+
return _ConfigNetworkLinea(_direct=False)
324328
elif network == cls.NETWORK_TENDERLY:
325329
return _ConfigNetworkTenderly(_direct=False)
326330
else:
@@ -729,6 +733,42 @@ class _ConfigNetworkMantle(ConfigNetwork):
729733
# Add any exchanges unique to the chain here
730734
CHAIN_SPECIFIC_EXCHANGES = []
731735

736+
class _ConfigNetworkLinea(ConfigNetwork):
737+
"""
738+
Fastlane bot config -- network [Base Mainnet]
739+
"""
740+
741+
NETWORK = S.NETWORK_LINEA
742+
NETWORK_ID = "59144"
743+
NETWORK_NAME = "linea"
744+
DEFAULT_PROVIDER = S.PROVIDER_ALCHEMY
745+
RPC_ENDPOINT = "https://linea.blockpi.network/v1/rpc/"
746+
WEB3_ALCHEMY_PROJECT_ID = os.environ.get("WEB3_LINEA")
747+
748+
network_df = get_multichain_addresses(network=NETWORK_NAME)
749+
FASTLANE_CONTRACT_ADDRESS = "0xC7Dd38e64822108446872c5C2105308058c5C55C"
750+
MULTICALL_CONTRACT_ADDRESS = "0xcA11bde05977b3631167028862bE2a173976CA11"
751+
752+
CARBON_CONTROLLER_ADDRESS = "0x0000000000000000000000000000000000000000" #TODO - UPDATE WITH ACTUAL DEPLOYMENT WHEN THERE IS ONE
753+
CARBON_CONTROLLER_VOUCHER = "0x0000000000000000000000000000000000000000" #TODO - UPDATE WITH ACTUAL DEPLOYMENT WHEN THERE IS ONE
754+
755+
NATIVE_GAS_TOKEN_ADDRESS = "0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE"
756+
WRAPPED_GAS_TOKEN_ADDRESS = "0xe5D7C2a44FfDDf6b295A15c148167daaAf5Cf34f"
757+
NATIVE_GAS_TOKEN_SYMBOL = "ETH"
758+
WRAPPED_GAS_TOKEN_SYMBOL = "WETH"
759+
STABLECOIN_ADDRESS = "0x176211869ca2b568f2a7d4ee941e073a821ee1ff"
760+
761+
IS_INJECT_POA_MIDDLEWARE = True
762+
# Balancer
763+
BALANCER_VAULT_ADDRESS = "0x1d0188c4B276A09366D05d6Be06aF61a73bC7535" # velocore
764+
765+
CHAIN_FLASHLOAN_TOKENS = {
766+
"0xe5D7C2a44FfDDf6b295A15c148167daaAf5Cf34f": "WETH",
767+
"0x176211869ca2b568f2a7d4ee941e073a821ee1ff": "USDC",
768+
}
769+
# Add any exchanges unique to the chain here
770+
CHAIN_SPECIFIC_EXCHANGES = []
771+
732772
class _ConfigNetworkTenderly(ConfigNetwork):
733773
"""
734774
Fastlane bot config -- network [Ethereum Tenderly]

fastlane_bot/config/provider.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -101,13 +101,13 @@ def __init__(self, network: ConfigNetwork, **kwargs):
101101
provider_url=self.RPC_URL,
102102
provider_name="alchemy",
103103
)
104-
self.connection.connect_network()
104+
self.connection.connect_network(network.IS_INJECT_POA_MIDDLEWARE)
105105
self.w3 = self.connection.web3
106106
self.w3_async = self.connection.w3_async
107107
self.LOCAL_ACCOUNT = self.w3.eth.account.from_key(ETH_PRIVATE_KEY_BE_CAREFUL)
108108

109109

110-
if network.NETWORK in [N.NETWORK_BASE, N.NETWORK_ETHEREUM, N.NETWORK_FANTOM, N.NETWORK_MANTLE]:
110+
if network.NETWORK in [N.NETWORK_BASE, N.NETWORK_ETHEREUM, N.NETWORK_FANTOM, N.NETWORK_MANTLE, N.NETWORK_LINEA]:
111111
self.CARBON_CONTROLLER_CONTRACT = self.w3.eth.contract(
112112
address=network.CARBON_CONTROLLER_ADDRESS,
113113
abi=CARBON_CONTROLLER_ABI,

fastlane_bot/config/selectors.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
NETWORK_OPTIMISM = "optimism"
1111
NETWORK_CANTO = "canto"
1212
NETWORK_FANTOM = "fantom"
13+
NETWORK_LINEA = "linea"
1314
NETWORK_MANTLE = "mantle"
1415
NETWORK_SCROLL = "scroll"
1516
NETWORK_BSC = "binance_smart_chain"

fastlane_bot/data/abi.py

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,38 @@
5656
"""
5757
)
5858

59+
LYNEX_V2_FACTORY_ABI = [
60+
{
61+
"type": "event",
62+
"name": "PairCreated",
63+
"anonymous": False,
64+
"inputs": [{"indexed": True, "internalType": "address", "name": "token0", "type": "address"}, {"indexed": True, "internalType": "address", "name": "token1", "type": "address"}, {"indexed": False, "internalType": "bool", "name": "stable", "type": "bool"}, {"indexed": False, "internalType": "address", "name": "pair", "type": "address"}, {"indexed": False, "internalType": "uint256", "name": "", "type": "uint256"}]
65+
},
66+
{
67+
"type": "function",
68+
"name": "getFee",
69+
"stateMutability": "view",
70+
"inputs": [{"internalType": "bool", "name": "_stable", "type": "bool"}],
71+
"outputs": [{"internalType": "uint256", "name": "", "type": "uint256"}]
72+
}
73+
]
74+
75+
NILE_V2_FACTORY_ABI = [
76+
{
77+
"type": "event",
78+
"name": "PairCreated",
79+
"anonymous": False,
80+
"inputs": [{"indexed": True, "internalType": "address", "name": "token0", "type": "address"}, {"indexed": True, "internalType": "address", "name": "token1", "type": "address"}, {"indexed": False, "internalType": "bool", "name": "stable", "type": "bool"}, {"indexed": False, "internalType": "address", "name": "pair", "type": "address"}, {"indexed": False, "internalType": "uint256", "name": "", "type": "uint256"}]
81+
},
82+
{
83+
"type": "function",
84+
"name": "pairFee",
85+
"stateMutability": "view",
86+
"inputs": [{"internalType": "address", "name": "_pool", "type": "address"}],
87+
"outputs": [{"internalType": "uint256", "name": "fee", "type": "uint256"}]
88+
}
89+
]
90+
5991
PANCAKESWAP_V2_FACTORY_ABI = json.loads(
6092
"""
6193
[{"inputs":[{"internalType":"address","name":"_feeToSetter","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"token0","type":"address"},{"indexed":true,"internalType":"address","name":"token1","type":"address"},{"indexed":false,"internalType":"address","name":"pair","type":"address"},{"indexed":false,"internalType":"uint256","name":"","type":"uint256"}],"name":"PairCreated","type":"event"},{"constant":true,"inputs":[],"name":"INIT_CODE_PAIR_HASH","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"allPairs","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"allPairsLength","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"tokenA","type":"address"},{"internalType":"address","name":"tokenB","type":"address"}],"name":"createPair","outputs":[{"internalType":"address","name":"pair","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"feeTo","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"feeToSetter","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"address","name":"","type":"address"}],"name":"getPair","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"_feeTo","type":"address"}],"name":"setFeeTo","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"_feeToSetter","type":"address"}],"name":"setFeeToSetter","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"}]

0 commit comments

Comments
 (0)