Twinkle HubTwinkle Hub

Docs

10 分鐘接通

Twinkle Hub 是一個 MCP endpoint,任何 MCP client 都能接。下面分兩條路徑 — 看你比較像哪種人。

1. 取得 API key

/login → Google / GitHub OAuth → 自動發 virtual key。Alpha 階段聯繫管理員人工加額度。 所有後續 request 都帶 Authorization: Bearer sk-...

2. curl(streamable-http transport)

Step 1:initialize 拿 session id(在 response header 的 mcp-session-id)

text
curl -i -X POST https://api.twinkleai.tw/mcp/ \
  -H "Authorization: Bearer sk-..." \
  -H "Accept: application/json, text/event-stream" \
  -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2025-03-26","capabilities":{},"clientInfo":{"name":"curl","version":"0"}}}'

Step 2:tools/call

text
curl -X POST https://api.twinkleai.tw/mcp/ \
  -H "Authorization: Bearer sk-..." \
  -H "Accept: application/json, text/event-stream" \
  -H "Content-Type: application/json" \
  -H "mcp-session-id: <from-step-1>" \
  -d '{"jsonrpc":"2.0","id":2,"method":"tools/call","params":{"name":"opendata-list_domains","arguments":{}}}'

Response 是 SSE-style framing — 找 data: 開頭的最後一行解 JSON。

3. Python(fastmcp client)

python
import asyncio
from fastmcp.client import Client
from fastmcp.client.auth import BearerAuth

async def main():
    async with Client(
        "https://api.twinkleai.tw/mcp/",
        auth=BearerAuth("sk-..."),
    ) as client:
        tools = await client.list_tools()
        print([t.name for t in tools])

        r = await client.call_tool(
            "opendata-search_datasets",
            {"query": "AQI", "domain": "environment", "limit": 5},
        )
        # response 在 r.content[0].text — JSON string
        import json
        print(json.loads(r.content[0].text))

asyncio.run(main())

Tool 回的是 CallToolResult.content[0].text, 內容是 JSON string。licence、citation 等 metadata 在 _meta 欄位透傳給你。

4. Tools reference

ToolArgumentsReturns (簡)
opendata-list_domains[{key, name_zh, scope, typical_questions}]
opendata-search_datasets{query, domain?, limit?}[{dataset_id, title, score, license}]
opendata-get_dataset{dataset_id}{schema, columns, license, source_url}
opendata-query_rows{dataset_id, where?, limit?}[row, ...]
opendata-materialize_dataset{dataset_id, format?}全表 CSV / JSON

所有 tool 的完整 schema 可以 call tools/list 拿到, 自動 generate 成 JSON Schema。

5. Authentication

  • Bearer token — header Authorization: Bearer sk-...。 是 LiteLLM virtual key,每個 user 一支。Rotate 從 /dashboard
  • 沒有 OAuth flow — 客戶端不需要 PKCE / refresh token, 就一支 long-lived bearer。
  • Rate limit — 目前無 per-key RPM/TPM 限制, 只有 max_budget 在擋(spend > max_budget LiteLLM 直接 reject)。

6. 計費

Tool每次用途
opendata-list_domains$0.0005列出 19 個 domain(給 Claude 用來規劃)
opendata-search_datasets$0.001在 domain 內找 dataset
opendata-get_dataset$0.001拿一個 dataset 的 metadata + schema
opendata-query_rows$0.005下 SQL-like filter 拿資料列
opendata-materialize_dataset$0.010整個 dataset 物化(大筆)

Spend tracking 有 5–15s async lag(LiteLLM batch DB write)。Quota 即時擋: 下一筆 request 進來時 LiteLLM 會比 spend vs max_budget。