import json, urllib.request, time, collections, sys
RPC = "https://rpc.mainnet.chain.robinhood.com"
def call(m, p):
    time.sleep(0.25)
    for i in range(7):
        try:
            rq = urllib.request.Request(RPC, json.dumps({"jsonrpc": "2.0", "id": 1, "method": m, "params": p}).encode(), {"Content-Type": "application/json", "User-Agent": "Mozilla/5.0"})
            r = json.load(urllib.request.urlopen(rq, timeout=30))
            if "error" in r: raise RuntimeError(r["error"])
            return r["result"]
        except Exception as e:
            err = e; time.sleep(2 ** i)
    raise err
from Crypto.Hash import keccak
def k(s): h = keccak.new(digest_bits=256); h.update(s.encode()); return "0x" + h.hexdigest()
INIT = k("Initialize(bytes32,address,address,uint24,int24,address,uint160,int24)")
latest = int(call("eth_blockNumber", []), 16)
tl = int(call("eth_getBlockByNumber", [hex(latest), False])["timestamp"], 16)
start = latest - int((tl - 1791256500) / 0.1013)
print("latest", latest, "ts", tl, "start", start, file=sys.stderr)
out = []; step = 20000; b = start
while b <= latest:
    e = min(b + step - 1, latest)
    try:
        logs = call("eth_getLogs", [{"fromBlock": hex(b), "toBlock": hex(e), "topics": [INIT]}])
    except Exception as ex:
        if step > 1000: step //= 2; continue
        raise
    for l in logs:
        d = l["data"][2:]
        fee = int(d[0:64], 16); sp = int(d[64:128], 16)
        if sp >= 2 ** 255: sp -= 2 ** 256
        hook = "0x" + d[128 + 24:192]
        out.append(dict(pm=l["address"], id=l["topics"][1], c0="0x" + l["topics"][2][26:], c1="0x" + l["topics"][3][26:], fee=fee, sp=sp, hook=hook, b=int(l["blockNumber"], 16), tx=l["transactionHash"]))
    b = e + 1
json.dump(out, open("/root/fwa1/init_since1015.json", "w"))
c = collections.Counter((x["fee"], x["sp"], x["hook"]) for x in out)
print("pools", len(out)); [print(kk, v) for kk, v in c.most_common(15)]
