Polymarket Bot Tutorial · Bölüm 7 / 32
Polymarket Gamma API derinlemesine inceleme: /events ve /markets endpoints, pagination, tag IDs (864 Tennis, 745 NBA, vb), 24 saatlik volume'a göre filtreleme, rate limits ve Python ile Node kod örnekleri.
Bu bölüm neleri kapsıyor
Gamma, Polymarket'in catalog API'sidir - front-end'in gösterdiği her event'i, her market'i, tag'i, image'ı ve resolved outcome'u listeler. CLOB API trade yapar; Gamma neyin trade edilebilir olduğunu açıklar. Bot hatalarının discovery katmanındaki en yaygın nedeni, bu ikisini karıştırmak ya da pagination contract'ını kaçırmaktır. Bu bölüm, production fetcher'larımızın dayandığı tam parameter davranışlarıyla Gamma'nın ana endpoints'leri için saha referansıdır.
- Gamma vs CLOB: hangisi ne zaman kullanılır
- /events endpoint anatomisi
- /markets endpoint anatomisi
- Tags ve tag IDs (doğrulanmış liste)
- Filtreleme: active, closed, volume24hr sıralaması
- Pagination ve limits
- Rate limits ve caching
- Kod: en yüksek 24 saatlik volume'a sahip market'leri çekme
Gamma vs CLOB: hangisi ne zaman kullanılır
İki farklı iş için iki farklı service.
Gamma (gamma-api.polymarket.com): catalog. Event'leri, market'leri, tag'leri, açıklamaları, image'ları, resolved outcome'ları, 24 saatlik volume'u, toplam volume'u ve bitiş tarihlerini listeler. Read-only HTTP. Çoğu okuma için authentication gerekmez. Sürekli güncellenir ama eventually consistent'tir - yeni kapanan bir market birkaç saniye boyunca hâlâ closed: false görünebilir.
CLOB (clob.polymarket.com): trading + order book. Mevcut en iyi bid/ask, top-N book depth ve recent trades'i listeler. Write endpoints'ler için authenticated'dır (order placement, cancellation). Book updates için real-time WebSocket channel'ları mevcuttur.
Genel kural: neyin trade edileceğini bulmak için Gamma'yı kullanın; trade etmek için CLOB'u kullanın. Fiyatları Gamma'dan okuyan bir bot stale data kullanıyordur - Gamma'nın price fields'ları CLOB'un order book'una göre daha seyrek güncellenir. Market metadata'yı CLOB'dan okuyan bir bot ise gereğinden fazla request atıyordur.
/events endpoint anatomisi
GET /events event seviyesinde data döndürür. Bir "event", Polymarket'te tek bir sayfadır; tek bir event birden fazla market içerebilir (örneğin 2024 Presidential Election event'inde her aday için bir market bulunur).
Ana field'lar:
slug: URL-safe identifier, event'in yaşam süresi boyunca sabittir.title,description: kullanıcıya gösterilen metin.endDate(ISO 8601): event'in ne zaman kapanacağı.active,closed: boolean; canlı event'ler için sorguda?active=true&closed=falseşeklinde birleştirin.volume,volume24hr: USD toplamları.tags: tag object dizisi (aşağıdaki tags bölümüne bakın).markets: child market object dizisi (bkz./marketsanatomisi).
En yaygın discovery pattern'i: GET /events?active=true&closed=false&order=volume24hr&ascending=false&limit=100. Bu, şu anda canlı olan en yüksek volume'lu 100 event'i döndürür.
/markets endpoint anatomisi
GET /markets market seviyesinde data döndürür. Bir market, bir Y/N ya da multi-outcome contract'tır; bir event'in içinde yer alır.
Ana field'lar:
slug: URL-safe identifier.question: trading page'de gösterilen başlık (ör. "Will Trump be president on January 1, 2027?").outcomes: outcome isimlerinin JSON string'i, ör.'["Yes","No"]'. Binary market'lerde her zaman iki eleman vardır; NegRisk için daha fazladır.outcomePrices: mevcut fiyatların decimal olarak JSON string'i, ör.'["0.62","0.38"]'. Her iki tarafın toplamı spread hariç ~1.0 eder.clobTokenIds: outcomes ile hizalanmış ERC-1155 token ID'lerinin JSON string'i. Aslında alıp sattığınız token'lar bunlardır.negRisk: boolean; toplamı 1 olan multi-outcome market'ler içintrue. Order placement için önemlidir (bölüm 11).
outcomes / outcomePrices / clobTokenIds field'ları parsed array olarak değil, JSON string olarak gelir - kullanmadan önce JSON-decode edin.
Tags ve tag IDs (doğrulanmış liste)
Tags, kategorik etiketlerdir (Sports, Crypto, Tennis, NBA, vb.). En çok kullanılan kategoriler için doğrulanmış production tag ID'leri:
| Tag | ID | Tag | ID |
|---|---|---|---|
| Sports | 1 | NBA | 745 |
| Crypto | 21 | NFL | 450 |
| Politics | 2 | Tennis | 864 |
| Bitcoin | 100196 | Esports | 702 |
| Ethereum | 100383 | Soccer | 1059 |
| Election | 3 | EPL | 739 |
| Middle East | 1432 | UCL | 2186 |
Belirli bir tag için ?tag_id=745 ile filtreleyin ya da slug kullanarak ?tag_slug=nba deneyin. Slug tabanlı filtreleme kodda daha okunaklıdır ama biraz daha yavaştır; ID tabanlı kullanım production default'tur.
Filtreleme: active, closed, volume24hr sıralaması
Zamanın %95'inde kullanacağınız dört filtre boyutu.
active=true|false:true, Polymarket ekibinin UI'dan gizlediği market'leri hariç tutar.closed=true|false:false, resolved market'leri hariç tutar.active=true&closed=falsekombinasyonu en yaygın canlı filtredir.order=volume24hr,order=volume,order=endDate: sıralama anahtarı. Canlı market'leri bulmak için en kullanışlı olanvolume24hr'dür.ascending=true|false: çoğu endpoint'te varsayılan olarak true'dur; volume sıralamalarında neredeyse her zamanfalseistersiniz.
Uyarı: tag_id ile filtreleme, order=volume24hr ve ascending=false ile birleştiğinde, tag çok az sayıda canlı market'e sahipse bazen boş bir sayfa döndürebilir. Bunu ele almak için her zaman over-fetch yapın (göstereceğinizden fazlasını isteyin) ve ardından post-filter uygulayın.
Pagination ve limits
limit parametresi çağrı başına 1-500 aralığını kabul eder. Belirtilmezse varsayılan 100'dür. 500'ün üzerinde server sessizce sınırlar - size 500 döner ama response daha fazlası olduğuna dair bir işaret içermez.
Pagination offset tabanlıdır: ikinci sayfa için ?limit=500&offset=500. Cursor tabanlı pagination yoktur, bu nedenle eşzamanlı eklemeler sayfa sınırlarının çağrılar arasında kaymasına neden olabilir. Çoğu bot discovery kullanımında bu kabul edilebilirdir; arşiv scrape'leri için sabit bir field'a göre sıralayın (endDate veya createdAt) ve slug ile örtüşmeyi tespit edin.
"Tüm canlı market'ler" için pratik pattern: limit=500&order=volume24hr&ascending=false ile çekin. Bu, volume'a göre ilk 500'ü kapsar; bu da pratikte anlamlı activity'ye sahip neredeyse tüm market'lerdir. İlk sayfanın ötesine geçmek nadiren faydalıdır - volume dağılımının kuyruğundaki market'ler tanım gereği hareketin olduğu yer değildir.
Rate limits ve caching
Gamma, Cloudflare arkasındadır ve IP başına yumuşak rate limits uygular. Production yükü altında gözlemlenen empirik eşikler:
- Tek bir IP'den sürdürülebilir şekilde ~30 req/sec'e kadar: sorunsuz.
- 100+ req/sec burst'ler: ara sıra 429 alınır, retry başarılı olur.
- ~500 req/sec sürdürülebilir: rate-limit sayfası veya geçici block (10-60 sn).
Yayınlanan response header'ları çoğu endpoint için 30-60 saniyelik Cache-Control değerleri içerir. Bunlara uyun - aynı event'i dakikada 10 kez yeniden çekmenin hiçbir faydası yoktur. Production caching pattern'i: tam URL'ye göre anahtarlanmış, 30 saniye TTL'li in-process LRU. Request sayısını düşürür ve latency'yi azaltır.
Yüksek frekanslı stratejiler için Gamma data'sını tek bir fetcher process tarafından güncellenen local store'a yansıtın; birden fazla consumer bu store'dan okusun. Bir fetcher × çok consumer > çok fetcher × Gamma.
Kod: en yüksek 24 saatlik volume'a sahip market'leri çekme
Üç dilde referans fetcher; 24 saatlik volume'a göre en iyi 50 canlı market'i döndürür.
Python:
import requests
r = requests.get("https://gamma-api.polymarket.com/events",
params={"active":"true","closed":"false",
"order":"volume24hr","ascending":"false","limit":50},
timeout=10)
for ev in r.json()[:50]:
print(ev["slug"], ev.get("volume24hr"))
Node:
const url = "https://gamma-api.polymarket.com/events?active=true&closed=false" +
"&order=volume24hr&ascending=false&limit=50";
const events = await fetch(url).then(r => r.json());
for (const ev of events) console.log(ev.slug, ev.volume24hr);
Curl:
curl -s "https://gamma-api.polymarket.com/events?active=true&closed=false&order=volume24hr&ascending=false&limit=50" \
| jq '.[].slug'
Polymarket gamma /events endpoint'i serbest metin search parametresini DESTEKLEMEZ - ?q=foo veya ?search=foo eklemek sessizce varsayılan sıralamayı döndürür. Bunun yerine slug veya tag ile filtreleyin.










