One WebSocket, sub-second
Prices are pushed the moment they change. Subscribe once and receive a snapshot followed by delta-only updates — no polling loop, no wasted quota.
PinnFeed is a Pinnacle odds API built for developers: one normalized WebSocket with server-side filters and delta updates, REST snapshots, decimal and American prices, no-vig fair odds on every market and a closing-line archive.
From $29/mo · free tier, no card · 13 sports · cancel in one click
| Spt | Fixture | 1 | X | 2 | Fair 1 |
|---|---|---|---|---|---|
| SOC | Viktoriya Sumy v Agrobiznes Volochisk● live 1-0 · Ukraine - Persha Liga | 1.11 | 6.13 | 30.59 | 1.22 |
| SOC | Viktoriya Sumy v Agrobiznes Volochisk● live 1-0 · Ukraine - Persha Liga | 1.11 | 6.13 | 30.59 | 1.22 |
| BAS | Kyoto Hannaryz v Levanga Hokkaido● live · Japan - B.League Premier | 3.38 | — | 1.29 | 3.62 |
| BAS | Ibaraki Robots v Ryukyu Golden Kings● live · Japan - B.League Premier | 1.22 | — | 4.44 | 1.27 |
| BAS | Kawasaki Brave Thunders v Altiri Chiba● live · Japan - B.League Premier | 1.92 | — | 1.82 | 2.05 |
| BAS | Shimane Susanoo Magic v Toyama Grouses● live · Japan - B.League Premier | 1.03 | — | 12.09 | 1.09 |
| BAS | Cheongju KB Stars v Woori Bank Woori Won● live · Korea - WKBL | 2.24 | — | 1.61 | 2.39 |
Everything you would otherwise write yourself — reconnection, merge rules, odds conversion, margin removal, kickoff detection — done once on our side and delivered as clean JSON.
Prices are pushed the moment they change. Subscribe once and receive a snapshot followed by delta-only updates — no polling loop, no wasted quota.
Subscribe by sport, league, event, market type and live or prematch. You only receive — and only pay bandwidth for — what you asked for.
Events and markets with stable ids, decimal and American odds, lines, periods, max stake and cut-off time. No raw feed archaeology.
Every market carries its margin plus fair probability and fair decimal price per outcome — the benchmark for +EV and arbitrage work.
The last prematch price of every market is stored at kickoff. Query closing lines by event or day to measure CLV and backtest models.
Create, rename and revoke as many keys as you need, see usage per key, upgrade or cancel from the dashboard. Keys are stored hashed.
Connect with your key, send one subscribe message and you are streaming. Plain WebSocket — any language works, compression optional.
# pip install websockets
import asyncio, json, os, websockets
async def main():
url = "wss://pinnfeed.io/v1/stream"
async with websockets.connect(url, additional_headers={"x-api-key": os.environ["PINNSOCKET_KEY"]}) as ws:
await ws.send(json.dumps({"type": "subscribe", "sports": ["soccer"], "live": True}))
async for raw in ws:
msg = json.loads(raw)
if msg["type"] == "ping": await ws.send('{"type":"pong"}')
elif msg["type"] == "delta":
for c in msg["changes"]:
if c["kind"] == "market" and c["op"] == "upsert":
m = c["market"]; print(m["key"], [(o["name"], o["decimal"], o["fair"]) for o in m["outcomes"]])
asyncio.run(main())// npm install ws
import WebSocket from 'ws';
const ws = new WebSocket('wss://pinnfeed.io/v1/stream', {
headers: { 'x-api-key': process.env.PINNSOCKET_KEY }, perMessageDeflate: true,
});
ws.on('open', () => ws.send(JSON.stringify({ type: 'subscribe', sports: ['tennis', 'basketball'] })));
ws.on('message', (buf) => {
const msg = JSON.parse(buf);
if (msg.type === 'ping') return ws.send('{"type":"pong"}');
if (msg.type === 'delta') for (const c of msg.changes) console.log(c.kind, c.op, c.market?.key ?? c.event?.home);
});# REST snapshot: every live soccer event with main markets
curl -H "x-api-key: $PINNSOCKET_KEY" \
"https://pinnfeed.io/v1/odds?sport=soccer&live=true&main=true"
# Closing lines for yesterday (Builder and above)
curl -H "x-api-key: $PINNSOCKET_KEY" \
"https://pinnfeed.io/v1/closing?date=2026-11-08&sport=tennis"{
"type": "delta", "seq": 48213, "ts": 1762679412093,
"changes": [{
"kind": "market", "op": "upsert",
"market": {
"id": "1640278226:s;0;m", "eventId": 1640278226,
"type": "moneyline", "period": 0, "main": true, "live": true,
"margin": 0.0357, "maxStake": 1500,
"outcomes": [
{ "name": "home", "american": -128, "decimal": 1.781, "fair": 1.845, "fairProb": 0.5421 },
{ "name": "draw", "american": 262, "decimal": 3.62, "fair": 3.750, "fairProb": 0.2667 },
{ "name": "away", "american": 405, "decimal": 5.05, "fair": 5.230, "fairProb": 0.1912 }
]
}
}]
}op: "remove", so your book never shows stale prices.GET /v1/odds for cron jobs and backfills.Typical public figures as of November 2026. Most odds APIs are REST-only or put streaming behind enterprise pricing.
| PinnFeed | Typical odds API | Enterprise feeds | |
|---|---|---|---|
| Delivery | WebSocket push + REST | REST polling | Push |
| WebSocket from | $29/mo | Add-on or 2× plan price | Contract |
| No-vig fair odds | Every market | Rarely | Sometimes |
| Closing-line history | Builder and above | Separate product | Extra |
| Onboarding | Email signup, key in seconds | Signup + card | Sales call |
| Entry price | Free · $29/mo | $30–99/mo | $1,000s/mo |
Something missing? Email support@pinnfeed.io.
Pinnacle closed its public API to most users in July 2025. PinnFeed is an independent service that streams Pinnacle prices to developers over a normalized WebSocket and REST API. You do not need a Pinnacle account.
Most odds APIs poll on a timer and charge extra for push. PinnFeed is push-first: one WebSocket with server-side filters and delta-only updates, plus REST snapshots, decimal and American prices, no-vig fair odds on every market and stored closing lines.
Pinnacle prices include a margin. We remove it with the multiplicative method and return the fair probability and fair decimal price for every outcome, so you can compare any bookmaker against the sharpest line without extra maths.
Thirteen sports: soccer, tennis, basketball, ice hockey, American football, baseball, rugby, MMA, boxing, volleyball and handball, esports, golf and cricket. Moneyline (1X2), spreads/handicaps including quarter lines, totals, team totals, every period, plus props and futures on Builder and above.
Yes. The Free plan gives REST access to two sports with a 30-second delay and 1,000 requests a day, with no card. Paid plans add the real-time WebSocket.
Yes. Plans are monthly through Stripe and you can cancel or switch plans from the dashboard in one click.
Free key, no card. Not a developer? Pinnacle Terminal gives you live screens and drop alerts without code.