Files
mini_code/polymarket 抓取价格.py
2025-12-30 13:06:58 +08:00

79 lines
2.6 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import requests
import json
GAMMA = "https://gamma-api.polymarket.com"
CLOB = "https://clob.polymarket.com"
def parse_jsonish_list(v):
if v is None:
return []
if isinstance(v, list):
return v
if isinstance(v, str):
return json.loads(v)
return []
def get_market_by_slug(slug: str):
r = requests.get(f"{GAMMA}/markets/slug/{slug}", timeout=20)
r.raise_for_status()
return r.json()
def get_best_price(token_id: str, side: str) -> float | None:
# side: "buy" => best bid, "sell" => best ask
r = requests.get(f"{CLOB}/price", params={"token_id": token_id, "side": side}, timeout=20)
r.raise_for_status()
p = r.json().get("price")
return float(p) if p is not None else None
def get_mid_or_fallback(token_id: str):
bid = get_best_price(token_id, "buy")
ask = get_best_price(token_id, "sell")
if bid is None and ask is None:
return None, bid, ask, None
# 如果只拿到一侧,就退化
if bid is None:
return ask, bid, ask, None
if ask is None:
return bid, bid, ask, None
spread = ask - bid
mid = (bid + ask) / 2
return mid, bid, ask, spread
def web_like_up_down(slug: str, decimals=0):
m = get_market_by_slug(slug)
outcomes = [str(x) for x in parse_jsonish_list(m.get("outcomes"))]
token_ids = [str(x) for x in parse_jsonish_list(m.get("clobTokenIds"))]
token_map = dict(zip(outcomes, token_ids))
up_id = token_map.get("Up") or token_map.get("Yes") or token_ids[0]
down_id = token_map.get("Down") or token_map.get("No") or token_ids[1]
up_mid, up_bid, up_ask, up_spread = get_mid_or_fallback(up_id)
dn_mid, dn_bid, dn_ask, dn_spread = get_mid_or_fallback(down_id)
if up_mid is None or dn_mid is None:
return {"error": "missing price", "up": (up_mid, up_bid, up_ask), "down": (dn_mid, dn_bid, dn_ask)}
# 归一化(避免因为点差导致 up+down != 1
s = up_mid + dn_mid
up_pct = round(up_mid / s * 100, decimals)
dn_pct = round(dn_mid / s * 100, decimals)
return {
"question": m.get("question"),
"market_id": m.get("id"),
"slug": m.get("slug"),
"up_pct": up_pct,
"down_pct": dn_pct,
"debug": {
"up": {"token_id": up_id, "bid": up_bid, "ask": up_ask, "mid_used": up_mid, "spread": up_spread},
"down":{"token_id": down_id, "bid": dn_bid, "ask": dn_ask, "mid_used": dn_mid, "spread": dn_spread},
"note": "网页通常用 mid若点差>0.10 则可能改用 last trade price。"
}
}
if __name__ == "__main__":
print(web_like_up_down("eth-updown-15m-1767069900", decimals=0))