PMXT Python SDK
A unified Python SDK for supported prediction markets. Hosted services are the default, with local sidecar access for self-hosted venue integrations.
Note: Use with a PMXT API key (hosted, recommended) or run a local PMXT service. Get a key at pmxt.dev/dashboard.
Installation
pip install pmxt
Requirements: Python >= 3.8. The local PMXT service is bundled automatically via the pmxt-core dependency — only needed when self-hosting.
Quick Start
Get your API key at pmxt.dev/dashboard. For reads, only pmxt_api_key and wallet_address are required.
import pmxt
# Reads — pmxt_api_key + wallet_address only
client = pmxt.Polymarket(
pmxt_api_key="pmxt_live_...",
wallet_address="0xYourWalletAddress",
)
# Search for markets
markets = client.fetch_markets(query="Trump")
print(markets[0].title)
# Get outcome details
outcome = markets[0].outcomes[0]
print(f"{outcome.label}: {outcome.price * 100:.1f}%")
# Fetch historical data (use outcome.outcome_id!)
candles = client.fetch_ohlcv(
outcome.outcome_id,
resolution="1d",
limit=30,
)
# Get current order book
order_book = client.fetch_order_book(outcome.outcome_id)
spread = order_book.asks[0].price - order_book.bids[0].price
print(f"Spread: {spread * 100:.2f}%")
# Account reads
positions = client.fetch_positions()
balance = client.fetch_balance()
How it works (hosted)
When you pass pmxt_api_key, the SDK talks to the PMXT hosted services:
- Catalog requests go to
api.pmxt.dev(markets, events, order books, OHLCV, trades). - Trading requests go to
trade.pmxt.dev(orders, positions, balances). - The SDK does not spawn a local process.
- For Polymarket, Opinion, and Limitless, PMXT's PreFundedEscrow handles custody — you sign orders with your own key, PMXT settles on-chain.
How it works (self-hosted)
When you omit pmxt_api_key, the Python SDK manages the local PMXT service for you:
- First API call: Checks if server is running
- Auto-start: Starts server if needed (takes ~1-2 seconds)
- Reuse: Multiple Python processes share the same server
- Zero config: Just import and use!
Manual server control (optional)
If you prefer to manage the server yourself:
import pmxt
# Disable auto-start
poly = pmxt.Polymarket(auto_start_server=False)
# Or start the server manually in a separate terminal
# $ pmxt-server
Trading
Hosted trading (recommended)
With a PMXT API key, pass pmxt_api_key, wallet_address, and private_key. The SDK auto-wraps your key into an EIP-712 signer and PMXT settles the order on-chain.
Polymarket
import pmxt
trader = pmxt.Polymarket(
pmxt_api_key="pmxt_live_...",
wallet_address="0xYourWalletAddress",
private_key="0xYourPrivateKey",
)
balance = trader.fetch_balance()
print(f"Available: ${balance[0].available}")
order = trader.create_order(
market_id="market-uuid",
outcome_id="outcome-uuid",
side="buy",
order_type="market",
amount=5.0,
denom="usdc",
slippage_pct=30.0,
)
print(f"Order status: {order.status}")
Opinion
import pmxt
trader = pmxt.Opinion(
pmxt_api_key="pmxt_live_...",
wallet_address="0xYourWalletAddress",
private_key="0xYourPrivateKey",
)
See the full hosted trading guide for venue support, custody model, and limits.
Self-hosted trading (advanced)
When self-hosting, you supply venue credentials directly — no pmxt_api_key. The SDK spawns a local PMXT service.
Polymarket
Requires your Polygon Private Key:
import os
import pmxt
poly = pmxt.Polymarket(
private_key=os.getenv("POLYMARKET_PRIVATE_KEY"),
proxy_address=os.getenv("POLYMARKET_PROXY_ADDRESS"), # Optional
# signature_type='gnosis-safe' (default)
)
# Check balance
balances = poly.fetch_balance()
print(f"Available: ${balances[0].available}")
# Place order (using outcome shorthand)
markets = poly.fetch_markets(query="Trump")
order = poly.create_order(
outcome=markets[0].yes,
side="buy",
type="limit",
amount=10,
price=0.55
)
Kalshi
Requires API Key and Private Key:
import os
import pmxt
kalshi = pmxt.Kalshi(
api_key=os.getenv("KALSHI_API_KEY"),
private_key=os.getenv("KALSHI_PRIVATE_KEY"),
)
# Check positions
positions = kalshi.fetch_positions()
for pos in positions:
print(f"{pos.outcome_label}: ${pos.unrealized_pnl:.2f}")
Limitless
Requires Private Key:
import os
import pmxt
limitless = pmxt.Limitless(
private_key=os.getenv("LIMITLESS_PRIVATE_KEY")
)
# Check balance
balances = limitless.fetch_balance()
print(f"Available: ${balances[0].available}")
API Reference
Market Data Methods
fetch_markets(params?)- Get active markets# Fetch recent markets poly.fetch_markets(limit=20, sort='volume') # Search by text poly.fetch_markets(query='Fed rates', limit=10) # Fetch by slug/ticker poly.fetch_markets(slug='who-will-trump-nominate-as-fed-chair')
filter_markets(markets, query)- Filter markets by keywordfetch_ohlcv(outcome_id, params)- Get historical price candlesfetch_order_book(outcome_id)- Get current order bookfetch_trades(outcome_id, params)- Get trade historyget_execution_price(order_book, side, amount)- Get execution priceget_execution_price_detailed(order_book, side, amount)- Get detailed execution info
Trading Methods (require authentication)
create_order(params)- Place a new ordercancel_order(order_id)- Cancel an open orderfetch_order(order_id)- Get order detailsfetch_open_orders(market_id?)- Get all open orders
Account Methods (require authentication)
fetch_balance()- Get account balancefetch_positions()- Get current positions
Data Models
All methods return clean Python dataclasses:
@dataclass
class UnifiedMarket:
market_id: str # Use this for create_order
title: str
outcomes: List[MarketOutcome]
volume_24h: float
liquidity: float
url: str
# ... more fields
@dataclass
class MarketOutcome:
outcome_id: str # Use this for fetch_ohlcv/fetch_order_book/fetch_trades
label: str # "Trump", "Yes", etc.
price: float # 0.0 to 1.0 (probability)
# ... more fields
See the full API reference for complete documentation.
Important Notes
Use outcome.outcome_id, not market.market_id
For deep-dive methods like fetch_ohlcv(), fetch_order_book(), and fetch_trades(), you must use the outcome ID, not the market ID:
markets = poly.fetch_markets(query="Trump")
outcome_id = markets[0].outcomes[0].outcome_id # Correct
candles = poly.fetch_ohlcv(outcome_id, ...) # Works
candles = poly.fetch_ohlcv(markets[0].market_id, ...) # Wrong!
Prices are 0.0 to 1.0
All prices represent probabilities (0.0 to 1.0). Multiply by 100 for percentages:
outcome = markets[0].outcomes[0]
print(f"Price: {outcome.price * 100:.1f}%") # "Price: 55.3%"
Timestamps are Unix milliseconds
from datetime import datetime
candle = candles[0]
dt = datetime.fromtimestamp(candle.timestamp / 1000)
print(dt)
Development
# Clone the repo
git clone https://github.com/pmxt-dev/pmxt.git
cd pmxt/sdks/python
# Install in development mode
pip install -e ".[dev]"
# Run tests
pytest
License
MIT
Metadata
Release files for pmxt 2.54.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| pmxt-2.54.0.tar.gz | 2.3 MB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| pmxt-2.54.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 4.7 MB
Release files / pmxt-2.54.0.tar.gz
| Download URL | pmxt-2.54.0.tar.gz |
|---|---|
| Size | 2.3 MB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
2839e4c591368b492cecf42b9b019e6fe14dddfc1a836dd58f36e2b9ad9f8bd1
|
|
BLAKE2b-256 checksum How to use checksums |
dc5f58fd7872e3c0c523d5fd0149091cf457f4e206588b41b510f04c869dd766
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.14.6
|
Release files / pmxt-2.54.0-py3-none-any.whl
| Download URL | pmxt-2.54.0-py3-none-any.whl |
|---|---|
| Size | 2.4 MB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
cd1cacc074537c7a640ed00b7ad1952e32bcd180f583a95ac9b6795c256b4c0c
|
|
BLAKE2b-256 checksum How to use checksums |
961e85d014b6a38474f43ccfd2983f825aa4325c8aff7420491038f68e0d603c
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.14.6
|