package main import ( "context" "fmt" "log" "math/big" "strings" "time" "github.com/ethereum/go-ethereum" "github.com/ethereum/go-ethereum/accounts/abi" "github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/ethclient" ) const uniswapV3PoolABI = `[ {"name":"token0","type":"function","inputs":[],"outputs":[{"name":"","type":"address"}]}, {"name":"token1","type":"function","inputs":[],"outputs":[{"name":"","type":"address"}]}, {"name":"fee","type":"function","inputs":[],"outputs":[{"name":"","type":"uint24"}]}, {"name":"liquidity","type":"function","inputs":[],"outputs":[{"name":"","type":"uint128"}]}, {"name":"slot0","type":"function","inputs":[],"outputs":[{"name":"sqrtPriceX96","type":"uint160"},{"name":"tick","type":"int24"},{"name":"observationIndex","type":"uint16"},{"name":"observationCardinality","type":"uint16"},{"name":"observationCardinalityNext","type":"uint16"},{"name":"feeProtocol","type":"uint8"},{"name":"unlocked","type":"bool"}]} ]` func main() { // Connect to Arbitrum client, err := ethclient.Dial("https://arb1.arbitrum.io/rpc") if err != nil { log.Fatal("Failed to connect:", err) } // Parse the ABI poolABI, err := abi.JSON(strings.NewReader(uniswapV3PoolABI)) if err != nil { log.Fatal("Failed to parse ABI:", err) } fmt.Println("Testing UniswapV3 Pool Calls") fmt.Println("============================") fmt.Println() // Test known good pools goodPools := []struct { address string name string }{ {"0xC31E54c7a869B9FcBEcc14363CF510d1c41fa443", "WETH/USDC.e 0.05%"}, {"0x641C00A822e8b671738d32a431a4Fb6074E5c79d", "USDT/WETH 0.05%"}, {"0x2f5e87C9312fa29aed5c179E456625D79015299c", "WBTC/WETH 0.05%"}, {"0x6f38e884725a116C9C7fBF208e79FE8828a2595F", "WETH/USDC 0.05%"}, } fmt.Println("Testing Known Good UniswapV3 Pools:") fmt.Println("-----------------------------------") for _, pool := range goodPools { testPool(client, poolABI, pool.address, pool.name) } // Test problematic pools from blacklist blacklistedPools := []string{ "0x7760cfd39f8fc36239c7299851d8b334cc5acbed", "0xe0571fecab07216cae82a0af3f44e7ea7aff8426", "0x8d17b1ce5132b327981dcea21cb183b9a3e1c177", } fmt.Println("\nTesting Blacklisted Pools:") fmt.Println("--------------------------") for _, pool := range blacklistedPools { testPool(client, poolABI, pool, "Blacklisted") } } func testPool(client *ethclient.Client, poolABI abi.ABI, poolHex string, name string) { poolAddress := common.HexToAddress(poolHex) fmt.Printf("\nPool: %s (%s)\n", poolHex[:10]+"...", name) ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second) defer cancel() // Check if contract exists code, err := client.CodeAt(ctx, poolAddress, nil) if err != nil || len(code) == 0 { fmt.Println(" ❌ No contract at this address") return } fmt.Printf(" ✅ Contract exists (%d bytes)\n", len(code)) // Test token0() token0Data, err := poolABI.Pack("token0") if err != nil { fmt.Printf(" ❌ Failed to pack token0: %v\n", err) return } result, err := client.CallContract(ctx, ethereum.CallMsg{ To: &poolAddress, Data: token0Data, }, nil) if err != nil { fmt.Printf(" ❌ token0() failed: %v\n", err) } else { var token0 common.Address err = poolABI.UnpackIntoInterface(&token0, "token0", result) if err != nil { fmt.Printf(" ❌ Failed to unpack token0: %v\n", err) } else { fmt.Printf(" ✅ token0: %s\n", token0.Hex()) } } // Test token1() token1Data, err := poolABI.Pack("token1") if err != nil { fmt.Printf(" ❌ Failed to pack token1: %v\n", err) return } result, err = client.CallContract(ctx, ethereum.CallMsg{ To: &poolAddress, Data: token1Data, }, nil) if err != nil { fmt.Printf(" ❌ token1() failed: %v\n", err) } else { var token1 common.Address err = poolABI.UnpackIntoInterface(&token1, "token1", result) if err != nil { fmt.Printf(" ❌ Failed to unpack token1: %v\n", err) } else { fmt.Printf(" ✅ token1: %s\n", token1.Hex()) } } // Test fee() feeData, err := poolABI.Pack("fee") if err != nil { fmt.Printf(" ❌ Failed to pack fee: %v\n", err) return } result, err = client.CallContract(ctx, ethereum.CallMsg{ To: &poolAddress, Data: feeData, }, nil) if err != nil { fmt.Printf(" ❌ fee() failed: %v\n", err) } else { var fee *big.Int err = poolABI.UnpackIntoInterface(&fee, "fee", result) if err != nil { fmt.Printf(" ❌ Failed to unpack fee: %v\n", err) } else { fmt.Printf(" ✅ fee: %d (%.2f%%)\n", fee, float64(fee.Int64())/10000) } } // Test using raw selectors fmt.Println(" Testing with raw selectors:") token0Selector := []byte{0x0d, 0xfe, 0x16, 0x81} result, err = client.CallContract(ctx, ethereum.CallMsg{ To: &poolAddress, Data: token0Selector, }, nil) if err != nil { fmt.Printf(" ❌ Raw token0() failed: %v\n", err) } else if len(result) >= 32 { fmt.Printf(" ✅ Raw token0(): 0x%x\n", result[12:32]) } }