Polymarket Bot Tutorial · Rozdział 20 z 32
Śledź whale wallets Polymarket i programowo kopiuj najlepszych traderów: identyfikuj rentowne wallets przez leaderboard i analizę on-chain, odzwierciedlaj ich transakcje z zasadami dotyczącymi size i timing.
Co obejmuje ten rozdział
Kopiowanie wygrywających walletów Polymarket to popularny pomysł, ale prawdziwe whale na Polymarket w większości robią late-window arb na resolved markets, a nie directional bets. Ten rozdział to uczciwy research oparty na analizie on-chain: które wallets faktycznie warto kopiować, dlaczego większość nie jest tego warta i jak wygląda matematyka position sizing.
To jest rozdział 20 z naszej 32-częściowej serii o budowie Polymarket trading bota. Omawiamy temat szczegółowo w sekcjach poniżej. Treść główna dla każdej sekcji jest pisana i publikowana rozdział po rozdziale; odpowiedzi FAQ i references są już kompletne i odzwierciedlają production experience z uruchamiania naszego własnego tradera.
- Identyfikacja rentownych wallets
- Detekcja transakcji on-chain
- Position sizing względem whale
- Latency: jak późno to już za późno
- Filtry: follow only wallets z potwierdzonym edge
- Code: wykryj whale buy event, wykonaj sized copy
Identifying profitable wallets
Założenie whale-copying polega na tym, że niektóre wallets są konsekwentnie rentowne, a kopiowanie ich wejść przechwytuje część ich edge. Analiza on-chain top wallets Polymarket z lat 2025-26 dała trzeźwiący wynik: większość widocznych whale robi late-window arbitrage na resolved markets, a nie directional trading.
Profil, który zmierzyliśmy na trzech kandydackich whale wallets:
- "hhhhhh6" (98.5% win rate, $n M volume) — 88% wejść po cenach ≥0.95, mediana timestamp wejścia 226 s z 300 s okna. Czysty tail-yield arb, nie directional.
- "anonymous" (20% win rate) — degenerate gambler. Kopiowanie traci pieniądze.
- "Jkim123" (53.5% win rate) — coin-flip. To nie jest sygnał wart kopiowania.
0% transakcji tych whale miało miejsce w pierwszych 120 s dowolnego 5-minutowego okna. Sygnał predykcyjny (jeśli w ogóle istnieje) pochodziłby z EARLY-window dużych wejść — ale to nie są wallets z góry leaderboard, bo są trudne.
On-chain trade detection
Wykrywanie transakcji docelowego walleta wymaga albo polling Polymarket data-api, albo subskrypcji eventów on-chain CTF transfer. Opcja data-api jest prostsza.
def watch_wallet(wallet_addr, last_seen_ts=0):
while True:
url = f"https://data-api.polymarket.com/activity?user={wallet_addr}&limit=100"
events = requests.get(url).json()
for ev in events:
ts = int(ev.get("timestamp", 0))
if ts <= last_seen_ts: continue
if ev["type"] == "TRADE":
process_whale_trade(ev)
last_seen_ts = max(last_seen_ts, ts)
time.sleep(5)
Polling co pięć sekund to praktyczne minimum dla data-api. Poniżej tego trafisz na rate limits. Do wykrywania poniżej sekundy subskrybuj on-chain events ERC-1155 TransferSingle z kontraktu CTF, filtrowane po proxy address whale.
Position sizing relative to the whale
Jeśli size dla kopiowanej transakcji ustawisz jako stały fraction trade whale, dziedziczysz ich risk profile. Dwie praktyczne alternatywy.
- Cap-based: size każdą kopię na stałą kwotę w dolarach ($10-50) niezależnie od size whale. Wolniej się compounding, ale strata na transakcję jest ograniczona.
- Win-rate-weighted: size copy jako funkcję recent win rate whale. 60%+ WR → full-size copy; 40-60% → half-size; poniżej 40% → skip.
Cap-based approach to bezpieczniejsze pierwsze wdrożenie. Przejdź do win-rate-weighted dopiero po zmierzeniu rzeczywistego win rate whale na TWOICH kopiach (który zwykle jest gorszy niż ich headline number, bo przychodzisz późno).
Latency: jak późno to za późno
Trade whale jest publicznie widoczny w ciągu 1-2 sekund od execution. Kopiowanie wymaga szybszej latency niż to po stronie odczytu, plus własnej latency składania orderu.
End-to-end dla typowego copy bota: polling 5-10 sekund + 200 ms order placement = łącznie 5-15 sekund. Zanim twoja kopia się wykona, sygnał whale jest już w price.
Dla 99% kopii to na wąskich markets Polymarket jest już za późno. Wejście whale przesunęło mid o 1-2 centy; płacisz tę premię 1-2 centy względem ceny, po której oni weszli. Jeśli ich edge wynosił 3c, połowa już zniknęła, zanim dotrzesz.
Copy boty, które działają, albo (a) targetują wolno poruszające się markets, gdzie latency 30 s nie ma znaczenia, albo (b) używają event subscription on-chain, by reagować w sub-second timeframes.
Filters: tylko follow wallets z potwierdzonym edge
Trzy filtry przed dodaniem jakiegokolwiek walleta do listy copy.
- 30+ closed trades w historii walleta. Mniejsze próbki to szum.
- Lifetime win rate > 60% albo dodatni expected value na transakcję na podstawie entry prices. Wystarczy jeden warunek; oba są lepsze.
- Wzorzec NIE jest late-window arb. Sprawdź median seconds-to-resolution przy wejściu; jeśli jest blisko 0, wallet robi tail-yield arb, którego nie da się odtworzyć.
Większość kandydackich whale nie przechodzi jednego z tych trzech testów. Pula naprawdę kopiowalnych wallets jest mała. Utrzymanie listy wymaga okresowych ponownych sprawdzeń — wallets, które były rentowne w zeszłym miesiącu, nie muszą być rentowne teraz.
Code: detect whale buy event, place sized copy
Reference: wykryj event CTF TransferSingle dla obserwowanego whale i wykonaj sized copy buy.
from web3 import Web3
w3 = Web3(Web3.WebsocketProvider(POLYGON_WSS))
ctf = w3.eth.contract(address=CTF_ADDR, abi=CTF_ABI)
WHALES = {"0xabc...": {"fraction": 0.05, "cap": 50}}
def on_transfer(event):
to = event.args["to"].lower()
if to not in WHALES: return
cfg = WHALES[to]
token_id = event.args.id
whale_size = event.args.value / 1e6
copy_size = min(cfg["cap"], whale_size * cfg["fraction"])
if copy_size < 5: return # not worth fees
book = fetch_book(str(token_id))
if book.best_ask:
place_fok(str(token_id), "BUY", book.best_ask + 0.01, copy_size)
# subscribe to ERC-1155 TransferSingle events from CTF
filt = ctf.events.TransferSingle.create_filter(fromBlock="latest")
while True:
for ev in filt.get_new_entries(): on_transfer(ev)
time.sleep(0.5)
Odróżnij buy od sell, sprawdzając from (zero address = mint = whale bought) vs to (zero address = burn = sold).











