mcpField
P
polybaskets-skills

polybaskets-skills

github.com/adityaakrその他223 回インストール
リポジトリ

polybaskets-skills について

polybaskets-skillsは、Vara Network上の予測市場アグリゲーターPolyBasketsを操作するAIエージェント向けスキルパックです。CHIPの請求、バスケットの作成とベット、ポジション照会、ネイティブVARAフリーベットの手順と安全上の注意をまとめています。

主な機能

  1. 01CHIP請求とベットの手順ガイド
  2. 02予測市場からのバスケット作成
  3. 03ポジション照会と払戻請求
  4. 04ネイティブVARAフリーベットの個別フロー
  5. 05ウォレット、バウチャー、取引の安全策

活用シーン

  1. 01エージェントのCHIPによるベット手順の実行
  2. 02複数市場のバスケット作成とベット
  3. 03ポジション確認と決済済み払戻の請求
  4. 04明示的な要望に応じたネイティブVARAフリーベット

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/adityaakr/polybaskets --skill polybaskets-skills

インストール後、Claude Code で/polybaskets-skillsを入力して読み込まれたか確認します。

同梱ファイル

SKILL.md と一緒にインストールされる参考資料やスクリプト。

README.md
STARTER_PROMPT.md
.claude-plugin/
marketplace.json
plugin.json
idl/
bet_lane_client.idl
bet_token_client.idl
freebet-ledger.idl
polymarket-mirror.idl
references/
contract-interfaces.md
error-codes.md
index-math.md
program-ids.md

詳細

前文(最初に実行)

if ! command -v vara-wallet &>/dev/null; then
  echo "MISSING_DEPENDENCY: vara-wallet not found. Install with: npm install -g vara-wallet"
else
  _VW_VER=$(vara-wallet --version 2>/dev/null)
  echo "vara-wallet version: $_VW_VER"
  # 0.10+ required for hex→bytes auto-conversion in PlaceBet args
  if [ "$(printf '%s\n' "0.10.0" "$_VW_VER" | sort -V | head -1)" != "0.10.0" ]; then
    echo "UPDATE REQUIRED: vara-wallet 0.10+ needed. Run: npm install -g vara-wallet@latest"
  fi
fi

# Check for vara-skills (provides wallet management, Sails interaction, and network utilities)
_VS_FOUND="no"
for _vs in "$HOME/.claude/skills/vara-skills" ".claude/skills/vara-skills" ".agents/skills/vara-skills"; do
  if [ -d "$_vs" ] && [ -f "$_vs/SKILL.md" ]; then _VS_FOUND="yes"; break; fi
done
if [ "$_VS_FOUND" = "no" ]; then
  echo "RECOMMENDED: Install vara-skills for full Vara Network support: npx skills add gear-foundation/vara-skills"
fi

# Locate skill pack root for IDL files
_PB_DIR=""
for _d in \
  "${POLYBASKETS_SKILLS_DIR:-}" \
  "./skills" \
  "$HOME/.claude/skills/polybaskets-skills" \
  ".claude/skills/polybaskets-skills" \
  ".agents/skills/polybaskets-skills" \
  "$HOME"/.claude/plugins/cache/polybaskets-skills/polybaskets-skills/*; do
  if [ -n "$_d" ] && [ -d "$_d/idl" ]; then
    _PB_DIR="$_d"; break
  fi
done
if [ -n "$_PB_DIR" ]; then
  export POLYBASKETS_SKILLS_DIR="$_PB_DIR"
  echo "POLYBASKETS_SKILLS_DIR=$_PB_DIR"
else
  # Fallback: check if we're in the polybaskets repo
  if [ -d "skills/idl" ]; then
    echo "IDL files available at skills/idl/"
  else
    echo "WARNING: Could not locate IDL files. Set POLYBASKETS_SKILLS_DIR or run from polybaskets repo."
  fi
fi

PolyBaskets スキル

AI エージェントが PolyBaskets(Vara Network 上の ETF スタイルの予測市場アグリゲーター)を利用するためのスキルパックです。シーズン 2 のエコノミーでは、エージェントは毎時無料の CHIP トークンを受け取り(基本 500、連続利用日数に応じて UTC 日ごとに +10、11 日目に上限の 600)、予測バスケットにベットし、市場の決済時に配当を受け取ります。ネイティブ VARA のフリーベット残高は、FreebetLedger を通じて個別に処理されます。ガスバウチャーには毎時トランシェモデルが採用されています。1 回のバッチ POST で必要なプログラムを登録し、毎時の補充ごとに +500 VARA を追加します(ウォレットあたり、資金提供を受けた POST は 1 時間に 1 回)。

エージェントの手順

次の手順を順番に実行してください。すべてのコマンドはコピーしてそのまま実行できます。

Step 0: Create wallet (one-time)
Step 1: Check / refresh gas voucher (+500 VARA per hour; GET first, batched POST only if needed)
Step 2: Register agent name on-chain (one-time)
Step 3: Claim free CHIP tokens (once per hour)
Step 4: Search Polymarket for interesting markets
Step 5: Build a basket — pick markets, assign % weights (must sum to 100%)
Step 6: Create basket on-chain
Step 7: Approve CHIP spend, get a signed quote, place bet on your basket
Step 8: Wait for Polymarket markets to resolve
Step 9: Check if basket settlement is finalized (settlement status "Finalized"; basket status "Settled")
Step 10: Claim payout
Step 11: Loop back — claim more CHIP in an hour, or bet on someone else's basket

手順 2〜4 を省略して、別のユーザーが作成した既存のバスケットにベットすることもできます。

クイックスタート — フロー全体をコピーして貼り付け

# Setup — copy this entire block at the start of every session
BASKET_MARKET="0xea8373e8b4441ef6e95325c1044d23ebf615b43fdef60a48623836a15ca7a25a"
BET_TOKEN="0x186f6cda18fea13d9fc5969eec5a379220d6726f64c1d5f4b346e89271f917bc"
BET_LANE="0x35848dea0ab64f283497deaff93b12fe4d17649624b2cd5149f253ef372b29dc"
FREEBET_LEDGER="0x6b4ad81d13194f8e27f71f4046c6e489b2af2b0b1ce835f390899941034fd979"
DAILY_CONTEST="0x1f320a71665f990701daf3862aa4cbb98943859a726c2b497bd053e120149a77"
_PB="${POLYBASKETS_SKILLS_DIR:-skills}"
IDL="$_PB/idl/polymarket-mirror.idl"
BET_TOKEN_IDL="$_PB/idl/bet_token_client.idl"
BET_LANE_IDL="$_PB/idl/bet_lane_client.idl"
FREEBET_LEDGER_IDL="$_PB/idl/freebet-ledger.idl"
VOUCHER_URL="https://voucher-backend-production-5a1b.up.railway.app/voucher"
BET_QUOTE_URL="https://bet-quote-service-production.up.railway.app"

# 1. Set network to mainnet + create wallet (one-time)
vara-wallet config set network mainnet
vara-wallet wallet create --name agent

# 2. Get hex address (needed for actor_id args — SS58 won't work)
MY_ADDR=$(vara-wallet balance | jq -r .address)
if [ -z "$MY_ADDR" ] || [ "$MY_ADDR" = "null" ]; then
  echo "Failed to resolve wallet address; aborting before voucher request."
  exit 1
fi
VOUCHER_STATE_URL="$VOUCHER_URL/$MY_ADDR"

# 3. Check / refresh gas voucher (hourly-tranche: 500 VARA per POST, max 1 per hour per wallet)
#    GET first — free, never rate-limited. Only POST when: no voucher yet,
#    missing one of the required programs, OR known balance is below 10 VARA and
#    canTopUpNow=true. Do not top up merely because the hourly window is open.
#    ⚠ `programs` is a JSON ARRAY of CONTRACT IDs (not your wallet address, not a string).
VOUCHER_STATE=$(curl -s "$VOUCHER_STATE_URL")
VOUCHER_ID=$(echo "$VOUCHER_STATE" | jq -r .voucherId)
CAN_TOP_UP=$(echo "$VOUCHER_STATE" | jq -r .canTopUpNow)
HAS_ALL_PROGRAMS=$(echo "$VOUCHER_STATE" | jq -r \
  --arg bm "$BASKET_MARKET" --arg bt "$BET_TOKEN" --arg bl "$BET_LANE" \
  '($bm | ascii_downcase) as $bm | ($bt | ascii_downcase) as $bt | ($bl | ascii_downcase) as $bl | ((.programs // []) | map(ascii_downcase)) as $p | (($p | index($bm)) != null and ($p | index($bt)) != null and ($p | index($bl)) != null)')
VARA_BALANCE=$(echo "$VOUCHER_STATE" | jq -r .varaBalance)
BALANCE_KNOWN=$(echo "$VOUCHER_STATE" | jq -r .balanceKnown)
LOW_VOUCHER_BALANCE="10000000000000" # 10 VARA in planck
NEED_TOP_UP=false
if [ "$BALANCE_KNOWN" = "true" ] && [ "$VARA_BALANCE" -lt "$LOW_VOUCHER_BALANCE" ]; then
  NEED_TOP_UP=true
fi

if [ "$VOUCHER_ID" = "null" ] || [ "$HAS_ALL_PROGRAMS" != "true" ] || { [ "$NEED_TOP_UP" = "true" ] && [ "$CAN_TOP_UP" = "true" ]; }; then
  # Single batched POST — required programs registered + 500 VARA added only
  # when the voucher is missing, incomplete, or nearly drained.
  RESP=$(curl -s -w "\n%{http_code}" -X POST "$VOUCHER_URL" \
    -H 'Content-Type: application/json' \
    -d '{"account":"'"$MY_ADDR"'","programs":["'"$BASKET_MARKET"'","'"$BET_TOKEN"'","'"$BET_LANE"'"]}')
  HTTP_CODE=$(echo "$RESP" | tail -n1)
  BODY=$(echo "$RESP" | sed '$d')
  case "$HTTP_CODE" in
    200) VOUCHER_ID=$(echo "$BODY" | jq -r .voucherId) ;;
    429) echo "Voucher rate-limited (next top-up in $(echo "$BODY" | jq -r .retryAfterSec) s). Reusing existing voucherId." ;;
    *)   echo "Voucher POST failed: HTTP $HTTP_CODE — $BODY" && exit 1 ;;
  esac
fi
echo "Voucher: $VOUCHER_ID (canTopUpNow=$CAN_TOP_UP, balance=$VARA_BALANCE, known=$BALANCE_KNOWN)"

# 4. Claim hourly CHIP tokens (free — once per hour, reward grows with streak)
#    NOTE: --voucher is required on ALL write calls (agent has no VARA for gas)
vara-wallet --account agent call $BET_TOKEN BetToken/Claim \
  --args '[]' --voucher $VOUCHER_ID --idl $BET_TOKEN_IDL

# 5. Browse baskets — find one with status "Active"
#    If no active baskets exist, create one: see basket-create/SKILL.md
vara-wallet call $BASKET_MARKET BasketMarket/GetBasketCount --args '[]' --idl $IDL
vara-wallet call $BASKET_MARKET BasketMarket/GetBasket --args '[0]' --idl $IDL

# 6. Approve CHIP spend for BetLane contract
#    CHIP has 12 decimals. 100 CHIP = "100000000000000" in raw units.
vara-wallet --account agent call $BET_TOKEN BetToken/Approve \
  --args '["'$BET_LANE'", "100000000000000"]' --voucher $VOUCHER_ID --idl $BET_TOKEN_IDL

# 7. Get quote, estimate gas, place bet (30s expiry — run together!)
#    Replace BASKET_ID with a real basket number (0, 1, 2, ...)
#    ⚠ Do NOT manually reconstruct the quote. Pass the raw curl response directly.
QUOTE=$(curl -s -X POST "$BET_QUOTE_URL/api/bet-lane/quote" \
  -H 'Content-Type: application/json' \
  -d '{"user":"'"$MY_ADDR"'","basketId":BASKET_ID,"amount":"100000000000000","targetProgramId":"'"$BET_LANE"'"}') && \
EST=$(vara-wallet --account agent call $BET_LANE BetLane/PlaceBet \
  --args "[BASKET_ID, \"100000000000000\", $QUOTE]" \
  --voucher $VOUCHER_ID --idl $BET_LANE_IDL --estimate) && \
GAS_LIMIT=$(node -e 'const x=JSON.parse(process.argv[1]); const used=BigInt(x.min_limit??x.minLimit??x.gas_for_reply??x.gasForReply??0); const withBuffer=used + used/5n + 5000000000n; console.log(withBuffer.toString())' "$EST") && \
vara-wallet --account agent call $BET_LANE BetLane/PlaceBet \
  --args "[BASKET_ID, \"100000000000000\", $QUOTE]" \
  --voucher $VOUCHER_ID --gas-limit $GAS_LIMIT --idl $BET_LANE_IDL

# 9. Later — check if basket settled
vara-wallet call $BASKET_MARKET BasketMarket/GetSettlement \
  --args '[BASKET_ID]' --idl $IDL
# Look for: "status": "Finalized" in the response

# 10. Claim payout (only after settlement is Finalized)
vara-wallet --account agent call $BET_LANE BetLane/Claim \
  --args '[BASKET_ID]' --voucher $VOUCHER_ID --idl $BET_LANE_IDL

エージェントの目的に応じた手順

全フロー(推奨):

  1. CHIP トークンを受け取ります:basket-bet/SKILL.md(手順 1)
  2. 市場を検索し、バスケットを作成します:basket-create/SKILL.md
  3. 承認して、自分のバスケットにベットします:basket-bet/SKILL.md(手順 4〜5)
  4. バスケットを閲覧し、ポジションと決済状況を確認します:basket-query/SKILL.md
  5. 決済済みバスケットの配当を受け取ります:basket-claim/SKILL.md

別のユーザーが作成した既存のバスケットにベットすることもできます。その場合は手順 1 を省略してください。

ネイティブ VARA フリーベットのフロー:

  • ユーザーが FreebetLedger 内の、出金不可のネイティブ VARA フリーベット残高を指している場合は、basket-freebet/SKILL.md を使用します。
  • これは CHIP のフローではありません。エージェントは FreebetLedger/BalanceOf を確認し、asset_kind: "Vara" のバスケットを検索または作成し、index_at_creation_bps を計算してから、FreebetLedger/SpendFreebet を呼び出します。その後、BasketMarket/GetFreebetPositions で確認し、BasketMarket/Claim を通じて受け取ります。
  • 受け取り時にフリーベットの元本は FreebetLedger に戻り、ウォレットに支払われるのは賭け金を超える利益のみです。

詳細情報:

  • プロトコル、インデックスの計算方法、配当の計算式について:polybaskets-overview/SKILL.md

セトラーの役割のみ:

  • 決済を提案/確定します:basket-settle/SKILL.md

参照情報

  • プログラム ID、ネットワーク設定、IDL のパス:references/program-ids.md
  • コントラクトインターフェース全体(すべてのメソッド、型、イベント):references/contract-interfaces.md
  • インデックスの計算方法と配当の計算式:references/index-math.md
  • エラーコードと復旧方法:references/error-codes.md

ルール(コマンドを実行する前にすべてお読みください)

  1. MAINNET のみ — テストネットには絶対に切り替えないでください。 コントラクトはメインネット(wss://rpc.vara.network)にデプロイされています。テストネットにはコントラクトもバウチャーも何もありません。呼び出しに失敗した場合は、エラーをデバッグしてください。テストネットにはフォールバックしないでください。各セッションの開始時に vara-wallet config set network mainnet を実行してください。
  2. すべての call コマンドに必ず --idl <path> を追加してください。 追加しないと呼び出しは失敗します。
  3. ブロックチェーンに書き込みを行うコマンド(Claim、Approve、PlaceBet、SpendFreebet)では、--account agent --voucher $VOUCHER_ID を使用してください。 ガス代はバウチャーが支払います。読み取り専用のクエリには、--account や --voucher を使用しないでください。
  4. 現在のセッション中にユーザーから明示的な承認を得ていない限り、ウォレットの VARA を絶対に使わないでください。 これは厳守のルールです。バウチャーがない、期限切れ、または残高不足の場合は、ウォレットの個人保有 VARA を使う前に停止して確認してください。
  5. actor_id 引数は 0x で始まる 16 進数形式である必要があります。 (kG... で始まる)SS58 アドレスでは失敗します。次のコマンドで 16 進数形式のアドレスを取得してください:vara-wallet balance | jq -r .address
  6. CHIP の数量は生の単位(小数点以下 12 桁)です。 1 CHIP = "1000000000000"。100 CHIP = "100000000000000"。必ず引用符で囲んだ文字列として渡してください。
  7. ガスバウチャーを確認/更新してください(1 時間単位のトランシェ方式)。 GET $VOUCHER_URL/$MY_ADDR は無料です。必ず最初に確認してください。POST は次の場合に限ります:バウチャーがまだない、バウチャーが必要なセッションのプログラムをカバーしていない、または balanceKnown=true かつ varaBalance < 10 VARA かつ canTopUpNow=true。canTopUpNow=true という理由だけでトップアップしないでください。残高が 10 VARA 以上ある間は現在のバウチャーを再利用してください。CHIP セッションでは programs: [$BASKET_MARKET, $BET_TOKEN, $BET_LANE] を使用します。ネイティブ freebet セッションでは $FREEBET_LEDGER も含めてください。バックエンドはバウチャーに 500 VARA を補充し、有効期間を 24 時間延長します。1 時間以内に 2 回目の POST を行うと、retryAfterSec を含む 429 が返されます。既存の voucherId を再利用して続行し、中止しないでください。programs はコントラクトのプログラム ID の配列であり、ウォレットアドレスではありません。varaBalance を信頼する前に、レスポンスの balanceKnown フィールドを確認してください。balanceKnown=false の場合、バックエンドはチェーンにアクセスできていないため、残高 0 を「枯渇」と見なしたり、canTopUpNow だけを理由にトップアップしたりしないでください。停止するのは、BALANCE_KNOWN=true かつ varaBalance < 10 VARA かつ canTopUpNow=false の場合だけです。その場合は nextTopUpEligibleAt まで待ってください。
  8. エージェント名をオンチェーンに登録してください。 BasketMarket/RegisterAgent を呼び出し、一意の名前(3~20 文字、小文字の英数字とハイフン)を登録すると、リーダーボードとエージェントのプロフィールにアドレスだけでなく名前が表示されます。すでに登録済みの場合は、残りのフローを続行してください。選んだ名前が使用済みの場合は、別の一意の名前を生成し、続行する前に再試行してください。
  9. ベットの前に承認してください。 BetLane/PlaceBet を呼び出す前に、BetLane コントラクトに対して BetToken/Approve を呼び出す必要があります。承認しないと、ベットは BetTokenTransferFromFailed で失敗します。
  10. PlaceBet では明示的に --gas-limit を指定してください。 推奨手順は、見積もりを取得してから送信することです。BetLane/PlaceBet では、デフォルトの手順として、見積もりをリクエストし、同じ呼び出しを --estimate 付きで実行してから、見積もり値に安全マージンを加えた値を --gas-limit に明示して実際のトランザクションを送信してください(推奨値:estimate * 1.2 + 5_000_000_000)。ガス代はバウチャーが支払いますが、Message ran out of gas while executing や Failed to reserve gas for system signal: Ext(Execution(NotEnoughGas)) から保護されるわけではありません。
  11. PlaceBet がガスエラーで失敗した場合は、再試行する前に状態を確認してください。 Message ran out of gas while executing または ...NotEnoughGas の後は、まず (user, basket_id) に対する BetLane/GetPosition をクエリしてください。ポジションが変化していたら、再送信しないでください。何も変わっていなければ、必要に応じて新しい見積もりを取得し、ガスの安全マージンを増やして、明示的な --gas-limit を指定して 1 回だけ再送信してください。確認せずにループで再試行しないでください。
  12. 同じアカウントから PlaceBet を並行して送信しないでください。 ベットは 1 件ずつ送信し、それぞれの結果を待ってから次に進んでください。OperationInProgress が返された場合は、再試行を連続で行うのではなく、状態を確認してください。少し待ってからポジションを再確認し、必要に応じて見積もりを更新し、対象の組み合わせが明らかに再びアイドル状態になっている場合にのみ続行してください。同じ (user, basket_id) で OperationInProgress が繰り返し返される場合は停止して報告してください。
  13. 1 時間ごとに CHIP を請求してください。 1 時間ごとの報酬は 500 + 10 × (streak_days − 1) CHIP、上限は 600 CHIP です。連続日数カウンターは、新しい UTC の暦日に請求するたびに進みます。同じ UTC 日内に複数回請求しても連続日数は増えません。UTC の丸 1 日分を逃すと、連続日数は 1 にリセットされます。1 日目の請求は毎回 500 CHIP、11 日目以降は毎回 600 CHIP です。
  14. settler ロールを持っていない限り、ProposeSettlement を呼び出さないでください。 設定された異議申し立て期限の後は誰でも FinalizeSettlement を実行できますが、既存の提案の確定を意図的に手伝う場合に限り使用してください。
  15. デフォルトの公開エージェントのフローでは CHIP を使用します。 ユーザーがネイティブ VARA の freebet を明示的に要求しない限り、CHIP(BetLane)を使用し、asset_kind: "Bet" のバスケットを作成してください。ネイティブ freebet では asset_kind: "Vara" のバスケットのみを使用し、最初に BasketMarket/IsVaraEnabled=true を確認してください。
  16. poly_market_id は "540816" のような数値文字列です。 16 進数の conditionId ではありません。

コメント