Skip to content

Instantly share code, notes, and snippets.

@jeongseup
Created February 6, 2026 00:11
Show Gist options
  • Select an option

  • Save jeongseup/1551b6281ae3bbd9e8acb286f3696175 to your computer and use it in GitHub Desktop.

Select an option

Save jeongseup/1551b6281ae3bbd9e8acb286f3696175 to your computer and use it in GitHub Desktop.
Polymarket Trading Guide

Polymarket 15m Up/Down Trading Bot - 개발 가이드

개요

이 문서는 Polymarket 15분 Up/Down 마켓에서 자동 거래를 실행하는 방법을 설명합니다.

Note: 이 가이드는 거래 실행 자동화에 집중합니다.
매매 전략(시그널 생성 로직)은 별도로 커스터마이징하세요.


사전 요구사항

  • Python 3.10+
  • Polygon 지갑 (USDC 보유)
  • Polymarket 계정 (지갑 연동 완료)

환경 변수

# ===== 필수 (지갑) =====
PRIVATE_KEY=0x...           # EOA 개인키 (Polygon)
SIGNATURE_TYPE=2            # EOA=0, POLY_PROXY=1, POLY_GNOSIS=2
FUNDER_ADDRESS=0x...        # 지갑 주소

# ===== 거래 설정 =====
TRADE_AMOUNT=1              # 거래당 금액 ($)
DRY_RUN=false               # true = 모의 거래
MAX_DAILY_TRADES=500        # 일일 최대 거래 수

# ===== 텔레그램 알림 (선택) =====
TELEGRAM_BOT_TOKEN=
TELEGRAM_CHAT_ID=

Polymarket CLOB API

Base URL

https://clob.polymarket.com

1. 15분 마켓 조회

GET /markets?tag=crypto-15m-up-down&closed=false

Response:

{
  "data": [{
    "condition_id": "0xabc123...",
    "question": "Bitcoin Up or Down - February 5, 6:00AM-6:15AM ET",
    "market_slug": "btc-updown-15m-1707127200",
    "tokens": [
      {"token_id": "111...", "outcome": "Up", "price": 0.51},
      {"token_id": "222...", "outcome": "Down", "price": 0.49}
    ],
    "end_date_iso": "2024-02-05T11:15:00Z"
  }]
}

핵심 필드:

필드 설명
condition_id 마켓 고유 ID
market_slug 슬러그 (타임스탬프 포함)
tokens[].token_id Up/Down 토큰 ID
tokens[].price 현재 가격 (0.0-1.0)
end_date_iso 마켓 종료 시간

2. 주문 실행

POST /order
Content-Type: application/json

Headers:
  POLY-ADDRESS: {지갑주소}
  POLY-SIGNATURE: {서명}
  POLY-TIMESTAMP: {타임스탬프}
  POLY-NONCE: {논스}

Request Body:

{
  "order": {
    "tokenID": "111...",
    "price": "0.51",
    "size": "2",
    "side": "BUY",
    "feeRateBps": "0",
    "nonce": "0",
    "expiration": "0",
    "signatureType": 2
  },
  "signature": "0x..."
}

Response (성공):

{
  "success": true,
  "orderID": "0xdef456...",
  "status": "matched",
  "takingAmount": "2",
  "makingAmount": "1",
  "transactionsHashes": ["0x..."]
}

3. 서명 생성

Polymarket은 EIP-712 서명을 사용합니다.

from eth_account import Account
from eth_account.messages import encode_typed_data

def sign_order(order_data: dict, private_key: str) -> str:
    """
    EIP-712 타입 데이터 서명
    """
    domain = {
        "name": "Polymarket CTF Exchange",
        "version": "1",
        "chainId": 137,  # Polygon
    }
    
    types = {
        "Order": [
            {"name": "tokenId", "type": "uint256"},
            {"name": "price", "type": "uint256"},
            {"name": "size", "type": "uint256"},
            {"name": "side", "type": "uint8"},
            # ... 추가 필드
        ]
    }
    
    message = encode_typed_data(domain, types, order_data)
    signed = Account.sign_message(message, private_key)
    
    return signed.signature.hex()

거래 실행 흐름

┌─────────────────────────────────────────────────────────────┐
│  1. 마켓 조회                                                │
│     GET /markets?tag=crypto-15m-up-down&closed=false        │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│  2. 거래 결정 (YOUR STRATEGY)                                │
│     - 방향: "up" or "down"                                  │
│     - 토큰 선택: tokens[0] (Up) or tokens[1] (Down)         │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│  3. 주문 생성                                                │
│     - size = TRADE_AMOUNT / price                           │
│     - 최소 5 shares 이상 (Polymarket 최소 단위)              │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│  4. 서명 (EIP-712)                                           │
│     - PRIVATE_KEY로 주문 데이터 서명                         │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│  5. 주문 제출                                                │
│     POST /order                                              │
│     - Headers: POLY-ADDRESS, POLY-SIGNATURE, ...            │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│  6. 결과 확인                                                │
│     - success: true → 체결 완료                              │
│     - transactionsHashes로 Polygonscan 확인 가능            │
└─────────────────────────────────────────────────────────────┘

최소 실행 코드 예시

import asyncio
import aiohttp
from eth_account import Account

CLOB_URL = "https://clob.polymarket.com"
PRIVATE_KEY = "0x..."
WALLET = "0x..."

async def get_markets():
    """15분 마켓 조회"""
    async with aiohttp.ClientSession() as session:
        url = f"{CLOB_URL}/markets?tag=crypto-15m-up-down&closed=false"
        async with session.get(url) as resp:
            data = await resp.json()
            return data.get("data", [])

async def execute_trade(token_id: str, price: float, amount: float):
    """
    거래 실행
    
    Args:
        token_id: Up 또는 Down 토큰 ID
        price: 현재 가격 (0.0-1.0)
        amount: 거래 금액 ($)
    """
    size = amount / price  # shares 계산
    
    order = {
        "tokenID": token_id,
        "price": str(int(price * 1e6)),  # 6 decimals
        "size": str(int(size * 1e6)),
        "side": "BUY",
        "feeRateBps": "0",
        "nonce": "0",
        "expiration": "0",
        "signatureType": 2
    }
    
    # 서명 생성 (실제로는 EIP-712 필요)
    signature = sign_order(order, PRIVATE_KEY)
    
    headers = {
        "POLY-ADDRESS": WALLET,
        "POLY-SIGNATURE": signature,
        "POLY-TIMESTAMP": str(int(time.time())),
        "POLY-NONCE": "0"
    }
    
    async with aiohttp.ClientSession() as session:
        async with session.post(
            f"{CLOB_URL}/order",
            json={"order": order, "signature": signature},
            headers=headers
        ) as resp:
            return await resp.json()

async def main():
    # 1. 마켓 조회
    markets = await get_markets()
    
    for market in markets:
        # 2. BTC 마켓 찾기
        if "Bitcoin" not in market["question"]:
            continue
        
        up_token = market["tokens"][0]
        down_token = market["tokens"][1]
        
        # 3. 거래 결정 (YOUR STRATEGY HERE)
        direction = "up"  # 또는 "down"
        
        # 4. 토큰 선택
        token = up_token if direction == "up" else down_token
        
        # 5. 거래 실행
        result = await execute_trade(
            token_id=token["token_id"],
            price=float(token["price"]),
            amount=1.0  # $1
        )
        
        print(f"Trade result: {result}")

if __name__ == "__main__":
    asyncio.run(main())

중요 제약사항

항목 설명
최소 거래 ~$1 5+ shares 필요
수수료 0% Maker 수수료 없음
체인 Polygon USDC 필요
Rate Limit 50 req/sec API 호출 제한

참고 문서

Polymarket

Polygon


트러블슈팅

"insufficient balance"

→ Polygon 지갑에 USDC 충전

"invalid signature"

→ SIGNATURE_TYPE 확인 (EOA=0, POLY_GNOSIS=2)

"order too small"

→ 최소 5 shares 이상 필요 ($1 at 20¢ = 5 shares)


Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment