okx-growth-competition

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

OKX Growth Competition — Trading Competition

OKX成长竞赛 — 交易竞赛

Agentic Wallet exclusive trading competitions. Full lifecycle: list → detail → join → trade → rank → claim.
CLI reference:
references/cli-reference.md
Agentic Wallet专属交易竞赛。完整生命周期:列出→详情→参与→交易→排名→领取。
CLI参考文档:
references/cli-reference.md

Facts about every Agentic Wallet competition (always true unless backend confirms otherwise)

所有Agentic Wallet竞赛的通用规则(除非后端确认否则始终生效)

<MUST> Treat the following as **factual ground truth** when the user asks about how a competition works. Do NOT infer otherwise from a single-chain `chainName` in `competition_detail` — that field currently only carries the primary EVM chain; the second chain is a hardcoded product invariant that backend has not yet split into a separate field. </MUST>
  1. Every active competition runs simultaneously on Solana AND the chain returned by the backend (e.g.
    chainName=X Layer
    → activity runs on both X Layer and Solana). Solana is the hardcoded second chain on every activity.
  2. Trades on either chain count toward the same competition standing. A user trading on Solana for an X-Layer-titled competition is participating, not bystanding. Likewise EVM trades count for a Solana-titled competition. (When backend later returns a multi-chain field listing all supported chains, drop this hardcoding.)
  3. myRankInfo.userTotal = 0
    means the user has not yet hit the qualifying threshold or the backend metric pipeline has not picked up their trades yet — it does NOT mean the user's chain is unsupported. Never tell the user "your chain doesn't count" based on a
    userTotal=0
    observation.
  4. The competition
    --wallet
    argument used in
    competition_rank
    is the chain-appropriate address: SOL for Solana-primary activities, EVM for EVM-primary activities. The address you pass is just a query lens — trades on the OTHER chain still count toward the same ranking.
  5. The shape of point 1–4 may change in the future when backend exposes the full supported-chain list. Until then, NEVER answer "Does Solana count for this competition?" with anything other than YES.
When the user asks anything like "Does my Solana trade count for this competition?" or "Which chain should I trade on?", answer based on this section, not from
chainName
alone.
<MUST> 当用户询问竞赛机制时,请将以下内容作为**事实依据**。请勿仅根据`competition_detail`中的单链`chainName`推断规则——该字段目前仅显示主EVM链;第二条链是硬编码的产品固定规则,后端尚未将其拆分为单独字段。 </MUST>
  1. 所有活跃竞赛同时在Solana和后端返回的链上进行(例如
    chainName=X Layer
    →活动同时在X Layer和Solana上进行)。Solana是所有活动默认的第二条链。
  2. 任意一条链上的交易都将计入同一竞赛排名。用户在Solana上进行X Layer主题竞赛的交易,仍属于参与竞赛,而非旁观。同理,EVM链上的交易也可计入Solana主题竞赛的排名。(当后端后续返回包含所有支持链的多链字段时,取消此硬编码规则。)
  3. myRankInfo.userTotal = 0
    意味着用户尚未达到参赛门槛,或后端指标系统尚未抓取到其交易记录——并不代表用户使用的链不被支持。切勿仅根据
    userTotal=0
    就告知用户“你的链不被计入”。
  4. competition_rank
    中使用的竞赛
    --wallet
    参数需匹配对应链的地址:Solana主活动使用SOL地址,EVM主活动使用EVM地址。传入的地址仅作为查询入口——另一条链上的交易仍会计入同一排名。
  5. 当前述1-4条规则的形式可能会在后端公开完整支持链列表后发生变化。在此之前,对于“Solana是否计入本次竞赛?”这类问题,回答必须为YES。
当用户询问类似“我的Solana交易是否计入本次竞赛?”或“我应该在哪个链上交易?”的问题时,请依据本节内容作答,而非仅参考
chainName
字段。

⚠️ Mandatory reading order

⚠️ 强制阅读顺序

<MUST> **Before producing ANY user-facing message about a competition (list / detail / join / claim / rank / status / wallet-export-guard), you MUST first locate the matching `Step N` section below and follow its fixed template structure.** Do NOT improvise the format. Do NOT shorten the templates. Do NOT drop sections or merge them.
The template structure is fixed; the language follows the user — see the
## Output Language
rule above. When the user writes Chinese, translate the template strings to natural Chinese. When the user writes English, use English as written. Placeholders and
Solana
literal stay as-is.
Quick router (user intent → template section):
  • "list competitions / show available competitions" → Step 1 (table, optionally split by Active / Ended)
  • "show details / show rules / show prize pool" → Step 2 (Basic info block + 4 reward sections, with hardcoded
    Solana, {chainName}
    and required participation / Skill copy)
  • "register / join" → Step 3 (registration success fixed template + disclaimer)
  • "trade for me" → Step 4 (delegate to okx-dex-swap)
  • "leaderboard / ranking" → Step 5
  • "claim reward" → Step 6 (use
    competition_claim
    MCP, atomic)
  • "show registered wallet" → Additional Flows / Query Registered Wallet
  • "export wallet" → Additional Flows / Wallet Export Guard
If the user's intent does not clearly map to one of the above, ask which they meant before responding — do not invent a freeform format. </MUST>
<MUST> **在生成任何面向用户的竞赛相关消息(列出/详情/参与/领取/排名/状态/钱包导出确认)之前,必须先找到下方对应的`步骤N`章节并遵循其固定模板结构**。请勿自行调整格式、缩短模板、删减或合并章节。
模板结构固定语言需匹配用户使用的语言——请参考上方的
## 输出语言
规则。当用户使用中文时,将模板字符串翻译成自然中文;当用户使用英文时,保留原英文表述。占位符和
Solana
字面量保持不变。
快速路由(用户意图→模板章节):
  • "列出竞赛/显示可用竞赛" → 步骤1(表格形式,可按活跃/已结束拆分)
  • "显示详情/显示规则/显示奖池" → 步骤2(基本信息块+4个奖励章节,包含硬编码的
    Solana, {chainName}
    及必填的参与/Skill说明)
  • "报名/参与" → 步骤3(固定的报名成功模板+免责声明)
  • "帮我交易" → 步骤4(委托给okx-dex-swap)
  • "排行榜/排名" → 步骤5
  • "领取奖励" → 步骤6(使用
    competition_claim
    MCP工具,原子操作)
  • "显示已注册钱包" → 附加流程 / 查询已注册钱包
  • "导出钱包" → 附加流程 / 钱包导出确认
如果用户意图无法明确匹配上述任一情况,请先询问用户具体需求再作答——切勿自行创建自由格式的内容</MUST>

Pre-flight

前置检查

Read
../okx-agentic-wallet/_shared/preflight.md
. If missing, read
_shared/preflight.md
.
阅读
../okx-agentic-wallet/_shared/preflight.md
。若该文件缺失,请阅读
_shared/preflight.md

Command Index

命令索引

#CommandAuthDescription
1
onchainos competition list [--status 0|1|2] [--page-size N] [--page-num N]
NoneList Agentic Wallet exclusive competitions (default status=0, active only)
2
onchainos competition detail --activity-id <id>
NoneGet rules, prize pool, chain, timeline
3
onchainos competition rank --activity-id <id> --wallet <addr> --sort-type <type> [--limit N]
NoneLeaderboard + user rank. MCP tool
competition_rank
makes
wallet
optional — when omitted it auto-picks the EVM or SOL address of the active account based on the activity's chain. Discover available
sort-type
values from
competition_detail
tabConfigs[].rankFieldConfig[].sortValueMap.descend
(do not hardcode).
4
onchainos competition user-status [--activity-id <id>] --evm-wallet <evm_addr> --sol-wallet <sol_addr>
NoneCheck participation & reward status; uses chain-appropriate address (omit
--activity-id
to check all activities). MCP tool
competition_user_status
makes both wallet args optional — auto-resolves from active account.
5
onchainos competition join --activity-id <id> --evm-wallet <addr> --sol-wallet <addr> --chain-index <chain_id>
Wallet loginRegister for the competition. MCP tool
competition_join
makes both wallet args optional.
6
onchainos competition claim --activity-id <id> --evm-wallet <addr> --sol-wallet <addr>
Wallet loginCLI returns unsigned calldata. MCP tool
competition_claim
is atomic — wallets are optional, signing + broadcast happens inside the tool, returns txHash array.
--status
(request filter):
0
=active,
1
=ended,
2
=all
activityStatus
(response field):
3
=active,
4
=ended
— these are DIFFERENT values from the request filter
sort-type
: dynamic — read from
competition_detail
tabConfigs[].rankFieldConfig[].sortValueMap.descend
. Currently observed values:
1
=PnL% (realized ROI),
7
=PnL (realized profit). Future activities may add more — always trust
tabConfigs
over hardcoding.
序号命令权限要求描述
1`onchainos competition list [--status 0\1\2] [--page-size N] [--page-num N]`
2
onchainos competition detail --activity-id <id>
获取规则、奖池、链信息、时间线
3
onchainos competition rank --activity-id <id> --wallet <addr> --sort-type <type> [--limit N]
排行榜+用户排名。MCP工具
competition_rank
wallet
为可选参数——若省略,将根据活动链自动选择活跃账户的EVM或SOL地址。可从
competition_detail
tabConfigs[].rankFieldConfig[].sortValueMap.descend
中获取可用的
sort-type
值(请勿硬编码)。
4
onchainos competition user-status [--activity-id <id>] --evm-wallet <evm_addr> --sol-wallet <sol_addr>
检查参与状态及奖励状态;使用对应链的地址(省略
--activity-id
可检查所有活动)。MCP工具
competition_user_status
中两个钱包参数均为可选——将自动从活跃账户解析。
5
onchainos competition join --activity-id <id> --evm-wallet <addr> --sol-wallet <addr> --chain-index <chain_id>
钱包登录报名参与竞赛。MCP工具
competition_join
中两个钱包参数均为可选。
6
onchainos competition claim --activity-id <id> --evm-wallet <addr> --sol-wallet <addr>
钱包登录CLI返回未签名的调用数据。MCP工具
competition_claim
原子操作——钱包参数可选,签名+广播均在工具内部完成,返回txHash数组。
--status
(请求筛选条件):
0
=活跃,
1
=已结束,
2
=全部
activityStatus
(响应字段):
3
=活跃,
4
=已结束
——这些值与请求筛选条件不同
sort-type
:动态值——从
competition_detail
tabConfigs[].rankFieldConfig[].sortValueMap.descend
中读取。目前已观测到的值:
1
=已实现回报率(PnL%),
7
=已实现盈亏(PnL)。未来活动可能新增更多值——请始终以
tabConfigs
为准,切勿硬编码。

Output Rules

输出规则

Internal-only IDs vs user-facing display. Internal numeric IDs (
activityId
,
chainIndex
,
accountId
) are returned in tool responses on purpose — they are needed to chain calls between tools (e.g. after
competition_join
, you may need to call
competition_detail
with the activity id to fill the success template). Keep them in the data layer; never render them in user-visible messages.
<NEVER> **Never include any internal id in a message produced for the user — under ANY circumstance, in ANY format.** Identify activities to the user EXCLUSIVELY by `activityName` (or `shortName` if name is unavailable). </NEVER>
Forbidden user-visible patterns (do NOT produce output like this):
  • Agentic Trading Contest (#107)
  • #106 (agenticwallettest1)
  • ❌ A column titled "ID" or "#"
  • ❌ Any reference like "competition 107" or "id 107"
Correct user-visible pattern:
  • Agentic Trading Contest
  • ✅ When disambiguating two activities with the same name, append
    chainName
    (e.g.
    Agentic Trading Contest (Solana)
    ), never the ID.
Behind the scenes (allowed and expected):
  • ✅ Reading
    activityId
    from a
    competition_user_status
    /
    competition_join
    response and passing it to
    competition_detail
    to fetch the data needed by a fixed template.
  • ✅ Any tool-to-tool chaining via numeric ids — as long as the final user-facing message omits them.
When the user asks to act on a specific activity (e.g. "claim Agentic Trading Contest"), the MCP tools
competition_claim
/
competition_join
accept
activity_name
and resolve the id server-side, so you can also use names directly without doing your own lookup.
内部ID与用户可见显示的区别。工具响应中会返回内部数字ID(
activityId
chainIndex
accountId
),这是为了实现工具间的调用链(例如
competition_join
之后,可能需要调用
competition_detail
并传入活动ID来填充成功模板)。请将这些ID保留在数据层,切勿在用户可见的消息中展示。仅通过
activityName
(若名称不可用则使用
shortName
)向用户标识活动。
<NEVER> **切勿在面向用户的消息中包含任何内部ID——无论任何情况、任何格式**。仅通过`activityName`向用户标识活动(若名称不可用则使用`shortName`)。 </NEVER>
禁止出现的用户可见格式(请勿生成如下输出):
  • Agentic Trading Contest (#107)
  • #106 (agenticwallettest1)
  • ❌ 标题为"ID"或"序号"的列
  • ❌ 任何类似"竞赛107"或"ID 107"的表述
正确的用户可见格式
  • Agentic Trading Contest
  • ✅ 当两个活动名称相同时,可追加
    chainName
    以区分(例如
    Agentic Trading Contest (Solana)
    ),切勿使用ID。
后台操作(允许且预期的行为)
  • ✅ 从
    competition_user_status
    /
    competition_join
    响应中读取
    activityId
    ,并将其传入
    competition_detail
    以获取固定模板所需的数据。
  • ✅ 工具间通过数字ID进行调用链操作——只要最终面向用户的消息中不包含这些ID即可。
当用户要求对特定活动执行操作(例如"领取Agentic Trading Contest的奖励")时,MCP工具
competition_claim
/
competition_join
支持传入
activity_name
并在服务器端解析ID,因此你也可以直接使用活动名称,无需自行查询ID。

Output Language

输出语言

<MUST> **Render every fixed template in the user's conversation language.** The template structure (sections, ordering, numbered items, table column count, placeholder positions, hardcoded literal phrases like `Solana, {chainName}` and the `[Disclaimer: ...]` block) is fixed and must NOT change. Only the natural-language text inside is translated to the user's language naturally.
Placeholders are never translated.
{chainName}
,
{rewardUnit}
,
{txHash}
,
{accountName}
, etc. are filled with API values verbatim — do not localize them.
Solana
(the hardcoded second-chain name) also stays as-is in every language. </MUST>
<MUST> **所有固定模板均需使用用户对话时使用的语言呈现**。模板结构(章节、顺序、编号项、表格列数、占位符位置、硬编码字面短语如`Solana, {chainName}`及`[Disclaimer: ...]`块)固定,不得修改。仅需将模板内的自然语言文本翻译成用户使用的语言。
占位符无需翻译
{chainName}
{rewardUnit}
{txHash}
{accountName}
等将直接填充API返回的值——请勿本地化。
Solana
(硬编码的第二条链名称)在所有语言中均保持不变。 </MUST>

Execution Flow

执行流程

Step 1 — Discover Competitions

步骤1 — 发现竞赛

Choosing the status filter

选择状态筛选条件

Decide which
status
to pass based on the user's intent:
User intentPass
status
Returned
activityStatus
values
Generic listing ("show competitions")
2
(all)
mix of 3 (active) and 4 (ended)
Active only ("which can I join now")
0
(active filter)
only 3
Ended only ("winners list")
1
(ended filter)
only 4
When in doubt, prefer
status=2
so the user can see the full picture and pick.
<MUST> **Display the result as markdown tables — one row per competition. Do not use a numbered prose list, do not collapse fields into a single sentence.**
When the result contains BOTH active (
activityStatus=3
) and ended (
activityStatus=4
) entries, split into two separate tables under bold subheadings (
**Active**
/
**Ended**
, translated to the user's language), in that order
. When only one status is present, render a single table without a subheading. </MUST>
根据用户意图决定传入的
status
参数:
用户意图传入的
status
返回的
activityStatus
通用列表("显示竞赛")
2
(全部)
3(活跃)和4(已结束)混合
仅显示活跃竞赛("我现在可以参加哪些竞赛")
0
(活跃筛选)
仅3
仅显示已结束竞赛("获奖者名单")
1
(已结束筛选)
仅4
若不确定,优先选择
status=2
,以便用户查看完整列表并自行选择。
<MUST> **将结果以Markdown表格形式展示——每行代表一个竞赛。请勿使用编号列表,请勿将字段合并为单句**。
当结果同时包含活跃(
activityStatus=3
)和已结束(
activityStatus=4
)的竞赛时,将其拆分为两个独立表格,并分别添加加粗小标题(
**活跃竞赛**
/
**已结束竞赛**
,需翻译成用户使用的语言),顺序为先活跃后已结束
。若仅存在一种状态,则直接渲染单个表格,无需小标题。 </MUST>

Fixed table template (English canonical; translate cells when user is non-English)

固定表格模板(英文标准版;非英文用户需翻译单元格内容)

**Active**

| Name | Chain | Time | Total Prize Pool | Details |
|------|-------|------|------------------|---------|
| {name} | Solana, {chainName} | {startTime} ~ {endTime} | {rewards} | [View](https://web3.okx.com/boost/trading-competition/{shortName}) |
| ... | ... | ... | ... | ... |

**Ended**

| Name | Chain | Time | Total Prize Pool | Details |
|------|-------|------|------------------|---------|
| {name} | Solana, {chainName} | {startTime} ~ {endTime} | {rewards} | [View](https://web3.okx.com/boost/trading-competition/{shortName}) |
| ... | ... | ... | ... | ... |
For non-English users, translate the column headers, section headers, and link text naturally. The structure (column count, ordering,
Solana, {chainName}
literal) does not change.
**活跃竞赛**

| 名称 | 链 | 时间 | 总奖池 | 详情 |
|------|-------|------|------------------|---------|
| {name} | Solana, {chainName} | {startTime} ~ {endTime} | {rewards} | [查看](https://web3.okx.com/boost/trading-competition/{shortName}) |
| ... | ... | ... | ... | ... |

**已结束竞赛**

| 名称 | 链 | 时间 | 总奖池 | 详情 |
|------|-------|------|------------------|---------|
| {name} | Solana, {chainName} | {startTime} ~ {endTime} | {rewards} | [查看](https://web3.okx.com/boost/trading-competition/{shortName}) |
| ... | ... | ... | ... | ... |
对于非英文用户,请将列标题、章节标题和链接文本自然翻译。结构(列数、顺序、
Solana, {chainName}
字面量)保持不变。

Field-mapping rules

字段映射规则

  • Group rows by
    availableCompetitions[].status
    :
    3
    → Active table,
    4
    → Ended table.
  • Name column ←
    name
  • Chain column ← same hardcoding as Step 2: always include Solana plus the backend
    chainName
    .
    • If
      chainName
      is Solana → write just
      Solana
    • Otherwise → write
      Solana, {chainName}
      (e.g.
      Solana, XLayer
      )
    • Temporary until backend returns a full supported-chain list.
  • Time column ←
    startTime
    ~
    endTime
    (human-readable, e.g.
    2025-04-01 ~ 2025-04-30
    )
  • Total Prize Pool column ←
    rewards
    field (already a formatted string like
    50,000 USDC
    )
  • Details column ←
    https://web3.okx.com/boost/trading-competition/<shortName>
    as a markdown link
After the table(s), ask the user (in their language):
  • If only Active has entries:
    Which competition would you like to view in detail, or would you like to register directly?
  • If only Ended has entries:
    Would you like to check your ranking or claim status for any of these?
  • If both: combine —
    Which active competition would you like to register or view, or which ended competition would you like to check your ranking / claim?
  • availableCompetitions[].status
    分组:
    3
    →活跃竞赛表格,
    4
    →已结束竞赛表格。
  • 名称列 ←
    name
  • 链列 ← 与步骤2相同的硬编码规则:始终包含Solana和后端返回的
    chainName
    • chainName
      为Solana → 仅写
      Solana
    • 否则 → 写
      Solana, {chainName}
      (例如
      Solana, XLayer
    • 此规则为临时规则,直到后端返回完整的支持链列表。
  • 时间列 ←
    startTime
    ~
    endTime
    (易读格式,例如
    2025-04-01 ~ 2025-04-30
  • 总奖池列 ←
    rewards
    字段(已为格式化字符串,例如
    50,000 USDC
  • 详情列 ←
    https://web3.okx.com/boost/trading-competition/<shortName>
    作为Markdown链接
表格展示完成后,用用户使用的语言询问:
  • 若仅存在活跃竞赛:"你想查看哪个竞赛的详情,还是直接报名?"
  • 若仅存在已结束竞赛:"你想查看这些竞赛中的哪个排名或领取状态?"
  • 若两者都存在:合并提问——"你想报名或查看哪个活跃竞赛,还是查看哪个已结束竞赛的排名/领取状态?"

Empty-result handling (English canonical; translate to user's language)

空结果处理(英文标准版;翻译成用户使用的语言)

  • All filters returned 0 entries →
    No trading competitions available right now.
  • status=0
    filter returned 0 entries →
    No active trading competitions at the moment.
  • status=1
    filter returned 0 entries →
    No ended trading competitions yet.
  • 所有筛选条件均返回0条结果 → "目前暂无可用的交易竞赛。"
  • status=0
    筛选返回0条结果 → "目前没有活跃的交易竞赛。"
  • status=1
    筛选返回0条结果 → "暂无已结束的交易竞赛。"

CLI equivalent

CLI等效命令

bash
onchainos competition list --status 2   # all
onchainos competition list --status 0   # active only
onchainos competition list --status 1   # ended only
bash
onchainos competition list --status 2   # 全部
onchainos competition list --status 0   # 仅活跃
onchainos competition list --status 1   # 仅已结束

Step 2 — View Details (if requested)

步骤2 — 查看详情(若用户请求)

bash
onchainos competition detail --activity-id <id>
<MUST> **Display competition / reward info using the fixed English template below.** The structure (sections, ordering, numbered list, placeholder positions, the hardcoded `Solana, {chainName}` chain prefix) is fixed. Copy the template character-for-character; only fill in placeholders. Do not paraphrase, abbreviate, or substitute synonyms.
When the user's language is not English, translate the natural-language strings to the user's language while preserving the structure, the placeholders, and every required content invariant listed below. Do not reorder, omit, or merge sections. </MUST>
bash
onchainos competition detail --activity-id <id>
<MUST> **使用下方固定的英文模板展示竞赛/奖励信息**。结构(章节、顺序、编号列表、占位符位置、硬编码的`Solana, {chainName}`链前缀)固定。请严格复制模板,仅填充占位符内容。请勿改写、缩写或替换同义词。
当用户使用非英文时,将自然语言字符串翻译成用户使用的语言,同时保留结构、占位符及以下列出的所有必填内容规则。请勿重新排序、省略或合并章节。 </MUST>

Fixed display template

固定展示模板

Basic info:
Chain: Solana, {chainName}
Time: {startTime} ~ {endTime}
Total prize pool: {totalPrizePool}

Reward categories:
1. Realized ROI Pool ({roiPoolAmount})
Ranked by realized ROI of the wallet account during the competition, high to low
{roiRankTable}

2. Realized PnL Pool ({pnlPoolAmount})
Ranked by realized PnL of the wallet account during the competition, high to low
{pnlRankTable}

3. Participation Reward ({participationPoolAmount})
During the competition, registered users with cumulative trading volume of $100 or more via Agentic Wallet, and wallet total assets maintained at $100 or more throughout, will share the {participationPoolAmount} participation reward pool. We will perform unscheduled asset snapshots during the competition to verify eligibility.

4. Skill Quality Award ({skillPoolAmount})
The Skill Quality Award is an independent judging category. During the competition, participants may submit their own Agent Skills via the activity page, including but not limited to on-chain autonomous yield strategies, trade analysis, and trading signal monitoring.
All submitted Agent Skills will be evaluated through a dual-rating mechanism of AI initial screening and human review. The top {skillTopN} Skill creators by score will each receive {skillPerCreatorReward}.
基本信息:
链: Solana, {chainName}
时间: {startTime} ~ {endTime}
总奖池: {totalPrizePool}

奖励类别:
1. 已实现回报率奖池 ({roiPoolAmount})
按竞赛期间钱包账户的已实现回报率排名,从高到低
{roiRankTable}

2. 已实现盈亏奖池 ({pnlPoolAmount})
按竞赛期间钱包账户的已实现盈亏排名,从高到低
{pnlRankTable}

3. 参与奖励 ({participationPoolAmount})
竞赛期间,通过Agentic Wallet累计交易量达到100美元及以上,且钱包总资产全程维持在100美元及以上的已报名用户,可共同瓜分{participationPoolAmount}的参与奖励池。我们将在竞赛期间不定期进行资产快照以验证资格。

4. Skill质量奖 ({skillPoolAmount})
Skill质量奖为独立评审类别。竞赛期间,参与者可通过活动页面提交自己的Agent Skill,包括但不限于链上自主收益策略、交易分析、交易信号监控等。
所有提交的Agent Skill将通过AI初筛+人工评审的双重评级机制进行评估。得分排名前{skillTopN}的Skill创作者每人将获得{skillPerCreatorReward}奖励。

Field-mapping rules

字段映射规则

  • Chain line ← Solana first, then the backend
    chainName
    . Concretely:
    • If
      chainName
      already is Solana → write just
      Solana
    • Otherwise → write
      Solana, {chainName}
      (e.g.
      Solana, XLayer
      )
    • This is a temporary hardcoding because the backend currently returns only the primary chain. A future backend release will return the full supported-chain list as a separate field; remove this hardcoding then.
  • {startTime}
    /
    {endTime}
    ← human-readable timestamps.
  • {totalPrizePool}
    ← sum of all
    prizePoolDistribution[].totalReward
    plus
    rewardUnit
    (e.g.
    50,000 USDC
    ).
  • {roiPoolAmount}
    ← totalReward of the realized-ROI tab.
  • {pnlPoolAmount}
    ← totalReward of the realized-PnL tab.
  • {participationPoolAmount}
    ← totalReward of the participation prize tab.
  • {skillPoolAmount}
    ← totalReward of the Skill quality prize tab.
  • {skillTopN}
    ← upper bound of the Skill tab's
    rules[].interval
    (e.g.
    "1-10"
    10
    ).
  • {skillPerCreatorReward}
    ← that rule entry's
    reward
    +
    rewardUnit
    (e.g.
    500 USDC
    ).
  • {roiRankTable}
    /
    {pnlRankTable}
    ← markdown table built from the corresponding tab's
    rules[]
    . Format (English canonical; localize headers to user's language):
    | Rank | Reward |
    |------|--------|
    | <interval-formatted> | <reward-formatted> |
    | ...                  | ...                |
    | Total | <totalReward> {rewardUnit} |
    Interval / reward formatting per row:
    • Single rank (
      interval = "1"
      ) → Rank cell
      Rank 1
      , Reward cell
      <reward> <rewardUnit>
      (no
      each
      prefix)
    • Range (
      interval = "2-6"
      ) → Rank cell
      Ranks 2-6
      , Reward cell
      <reward> <rewardUnit> each
    • Always end with a totals row whose Reward cell is the tab's
      totalReward
      +
      rewardUnit
      .
If any of the four pools is absent for a particular activity, omit just that section (keep the others as-is).
  • 链行 ← 先写Solana,再写后端返回的
    chainName
    。具体规则:
    • 若后端
      chainName
      已为Solana → 仅写
      Solana
    • 否则 → 写
      Solana, {chainName}
      (例如
      Solana, XLayer
    • 此为临时硬编码规则,因后端目前仅返回主链。未来后端版本将返回完整的支持链列表作为单独字段,届时取消此硬编码。
  • {startTime}
    /
    {endTime}
    ← 易读时间戳。
  • {totalPrizePool}
    ← 所有
    prizePoolDistribution[].totalReward
    之和加上
    rewardUnit
    (例如
    50,000 USDC
    )。
  • {roiPoolAmount}
    ← 已实现回报率标签页的totalReward。
  • {pnlPoolAmount}
    ← 已实现盈亏标签页的totalReward。
  • {participationPoolAmount}
    ← 参与奖励标签页的totalReward。
  • {skillPoolAmount}
    ← Skill质量奖标签页的totalReward。
  • {skillTopN}
    ← Skill标签页
    rules[].interval
    的上限(例如
    "1-10"
    10
    )。
  • {skillPerCreatorReward}
    ← 该规则条目的
    reward
    +
    rewardUnit
    (例如
    500 USDC
    )。
  • {roiRankTable}
    /
    {pnlRankTable}
    ← 从对应标签页的
    rules[]
    构建的Markdown表格。格式(英文标准版;列标题需本地化到用户使用的语言):
    | 排名 | 奖励 |
    |------|--------|
    | <格式化后的区间> | <格式化后的奖励> |
    | ...                  | ...                |
    | 总计 | <totalReward> {rewardUnit} |
    每行的区间/奖励格式化规则:
    • 单个排名(
      interval = "1"
      )→ 排名单元格为
      第1名
      ,奖励单元格为
      <reward> <rewardUnit>
      (无需前缀“每人”)
    • 排名区间(
      interval = "2-6"
      )→ 排名单元格为
      第2-6名
      ,奖励单元格为
      <reward> <rewardUnit> 每人
    • 始终以总计行结尾,奖励单元格为标签页的
      totalReward
      +
      rewardUnit
若某一活动缺少四个奖池中的任意一个,仅需省略该章节(保留其他章节不变)。

Required content invariants (per section)

各章节必填内容规则

Section 1 — Realized ROI Pool
  • Title MUST be exactly
    Realized ROI Pool
    (or its faithful translation in the user's language). Do NOT substitute with
    PnL% Ranking Award
    /
    ROI Ranking Award
    / similar.
  • Description MUST mention: ranking by realized ROI, high to low, during the competition period.
  • Rank table MUST have headers
    Rank / Reward
    and end with a
    Total
    row.
Section 2 — Realized PnL Pool
  • Title MUST be exactly
    Realized PnL Pool
    . Do NOT substitute with
    PnL Ranking Award
    .
  • Description MUST mention: ranking by realized PnL, high to low.
  • Rank table MUST follow the same format as Section 1.
Section 3 — Participation Reward (PRODUCT-MANDATED COPY)
  • Title MUST be exactly
    Participation Reward
    .
  • The description body MUST include all of these specific terms:
    • Agentic Wallet
    • cumulative trading volume threshold of
      $100
    • wallet total assets maintained at
      $100
      throughout
    • sharing the participation pool
    • asset snapshots to verify eligibility
Section 4 — Skill Quality Award (PRODUCT-MANDATED COPY)
  • Title MUST be exactly
    Skill Quality Award
    .
  • The description body MUST include all of these specific terms:
    • submission of Agent Skill via the activity page
    • examples of skill content (on-chain yield strategies, trade analysis, signal monitoring)
    • dual-rating mechanism of AI initial screening and human review
    • top {skillTopN} Skill creators ... each receive {skillPerCreatorReward}
<NEVER> - ❌ Do NOT drop the trailing `, Solana` from the chain line, even if the backend's `chainName` is already an EVM chain like XLayer / Arbitrum. - ❌ Do NOT reorder or merge the four reward sections — they must appear in the order 1 → 2 → 3 → 4. - ❌ Do NOT add ID columns or expose any internal numeric id (`activityId`, etc.) anywhere in the output. - ❌ Do NOT paraphrase, abbreviate, or substitute synonyms in Sections 3 and 4. These are product-mandated copy. - ❌ Do NOT invent rank-distribution rules from the pool amount. The actual rules come from `prizePoolDistribution[].rules[]` — read them; do not divide. - ❌ Do NOT use bullet markers (`-`) inside the four numbered sections — the structure is `1. Title (amount)\n description text` then the rank table; not a bullet list. </NEVER>
After printing the template, ask:
Would you like me to register you for this competition?
章节1 — 已实现回报率奖池
  • 标题必须为
    已实现回报率奖池
    (或用户语言中的忠实翻译)。请勿替换为
    盈亏率排名奖励
    /
    回报率排名奖励
    等类似表述。
  • 描述必须包含:按已实现回报率排名、从高到低、竞赛期间。
  • 排名表格必须包含
    排名/奖励
    列标题,并以
    总计
    行结尾。
章节2 — 已实现盈亏奖池
  • 标题必须为
    已实现盈亏奖池
    。请勿替换为
    盈亏排名奖励
  • 描述必须包含:按已实现盈亏排名、从高到低。
  • 排名表格必须遵循与章节1相同的格式。
章节3 — 参与奖励(产品强制文案)
  • 标题必须为
    参与奖励
  • 描述正文必须包含以下所有特定术语:
    • Agentic Wallet
    • 累计交易量门槛
      100美元
    • 钱包总资产全程维持在
      100美元
      及以上
    • 瓜分参与奖池
    • 资产快照验证资格
章节4 — Skill质量奖(产品强制文案)
  • 标题必须为
    Skill质量奖
  • 描述正文必须包含以下所有特定术语:
    • 通过活动页面提交Agent Skill
    • Skill内容示例(链上收益策略、交易分析、信号监控)
    • AI初筛+人工评审的双重评级机制
    • 排名前{skillTopN}的Skill创作者……每人获得{skillPerCreatorReward}
<NEVER> - ❌ 即使后端`chainName`为XLayer/Arbitrum等EVM链,也不得省略链行末尾的`Solana`——活动实际上在两条链上同时进行。 - ❌ 不得重新排序或合并四个奖励章节——必须按1→2→3→4的顺序展示。 - ❌ 不得添加ID列或在任何输出中暴露内部数字ID(`activityId`等)。 - ❌ 不得改写、缩写或替换章节3和4中的同义词。这些是产品强制文案。 - ❌ 不得根据奖池金额自行推断排名分配规则。实际规则来自`prizePoolDistribution[].rules[]`——请读取该字段,切勿自行分配。 - ❌ 不得在四个编号章节内使用项目符号(`-`)——结构应为`1. 标题(金额)\ 描述文本`,然后是排名表格;而非项目符号列表。 </NEVER>
模板展示完成后,询问:"你想让我帮你报名参加这个竞赛吗?"

Step 3 — Join (requires wallet login)

步骤3 — 参与竞赛(需钱包登录)

MCP: call
competition_join
with
activity_name
and
chain_index
only —
evm_wallet
and
sol_wallet
are auto-resolved from the active account.
CLI: pass addresses explicitly:
bash
onchainos competition join --activity-id <id> --evm-wallet <evm_addr> --sol-wallet <sol_addr> --chain-index <chain_id>
Get
chainIndex
from
competition_detail
chainIndex
field.
If the user is not logged in, the tool returns
not logged in — please run: onchainos wallet login
. Tell the user verbatim:
Please run
onchainos wallet login <your_email>
in your terminal to log in (it cannot be done from inside this conversation), then ask me to register again.
MCP工具:调用
competition_join
,仅传入
activity_name
chain_index
——
evm_wallet
sol_wallet
将从活跃账户自动解析。
CLI命令:需显式传入地址:
bash
onchainos competition join --activity-id <id> --evm-wallet <evm_addr> --sol-wallet <sol_addr> --chain-index <chain_id>
competition_detail
chainIndex
字段获取
chainIndex
若用户未登录,工具将返回
not logged in — please run: onchainos wallet login
。请直接告知用户:
请在终端中运行
onchainos wallet login <your_email>
进行登录(无法在此对话中完成登录),然后再次请求报名。

Required pre-flight: distinguish duplicate-registration scenarios

必要前置检查:区分重复报名场景

<MUST> **Before calling `competition_join`, you MUST first call `competition_user_status` for the activity to read the current account's `joinStatus`.** This separates the two duplicate-registration cases that have different user-facing messages. </MUST>
Scenario
user_status.joinStatus
(current account)
ActionTemplate
A — current account already joined
1
Do NOT call
competition_join
Scenario A template (below)
B — current account NOT joined
0
Call
competition_join
If success → success template; if
code=11016
→ Scenario B template
<MUST> **调用`competition_join`之前,必须先调用`competition_user_status`获取当前账户的`joinStatus`**。这将区分两种不同的重复报名场景,对应不同的用户消息。 </MUST>
场景当前账户的
user_status.joinStatus
操作模板
场景A — 当前账户已报名
1
请勿调用
competition_join
场景A模板(如下)
场景B — 当前账户未报名
0
调用
competition_join
成功→成功模板;若返回
code=11016
→场景B模板
Scenario A — current wallet already registered
场景A — 当前钱包已注册
Template:
Your current wallet account [accountName] is already registered for [activityName]. No need to register again. Would you like me to walk you through the rules in detail, or start trading directly?
Field-mapping:
  • [accountName]
    accountName
    of the currently selected account (read from
    wallet_store
    /
    wallet status
    , e.g.
    Account 1
    )
  • [activityName]
    activityName
    from the prior
    competition_user_status
    /
    competition_list
    response
模板:
你当前的钱包账户 [accountName] 已报名参加 [activityName],无需重复报名。你想让我详细讲解规则,还是直接开始交易?
字段映射:
  • [accountName]
    ← 当前选中账户的
    accountName
    (从
    wallet_store
    /
    wallet status
    读取,例如
    Account 1
  • [activityName]
    ← 之前
    competition_user_status
    /
    competition_list
    响应中的
    activityName
Scenario B — same login, different account already registered
场景B — 同一登录下的其他账户已注册
Triggered when
competition_join
returns
code=11016 Participation limit reached
.
Template:
Registration failed. Your wallet account [registeredAccountName] is already registered. You cannot register again. Please switch to your registered account to trade.
Field-mapping:
  • [registeredAccountName]
    ← name of the OTHER account in the same login that holds the registration. To find it, iterate every account from
    wallet_store
    other than the current one and call
    competition_user_status
    for the activity, picking the one whose
    joinStatus=1
    . If no account is found (rare race), fall back to a generic phrase like
    another of your wallet accounts is already registered
    and ask the user to check
    onchainos wallet status
    themselves.
competition_join
返回
code=11016 Participation limit reached
时触发。
模板:
报名失败。你的钱包账户 [registeredAccountName] 已报名,无法重复报名。请切换到已报名的账户进行交易。
字段映射:
  • [registeredAccountName]
    ← 同一登录下已报名的其他账户名称。需遍历
    wallet_store
    中除当前账户外的所有账户,调用
    competition_user_status
    获取该活动的状态,找到
    joinStatus=1
    的账户。若未找到(罕见竞争情况),则使用通用表述如
    你的另一个钱包账户已报名
    ,并请用户自行查看
    onchainos wallet status

Successful registration

报名成功

<MUST> **On every successful `competition_join` call (the tool returns `joined: true`), output the fixed template below.** Structure (the lead phrase + the dual-chain sentence + the closing question + the bracketed disclaimer on its own line) is fixed. Solana literal is hardcoded; `{chainName}` and `{totalPrizePool}` are filled from `competition_detail` (call it before formatting if you don't have it cached). Translate the natural-language strings to the user's language while preserving structure, placeholders, and the `Solana` literal. </MUST>
Template:
Registered successfully! This competition runs simultaneously on {chainName} and Solana, with a total prize pool of {totalPrizePool}. The trading contest ranks players by both PnL% and realized PnL, with additional Participation and Skill Quality Awards. Would you like me to walk you through the detailed rules, or help you initiate a trade on {chainName} or Solana?

[Disclaimer: Digital asset trading involves risk. Prices can be highly volatile. Please understand the risks fully and do your own research before trading.]
Field-mapping rules
  • {chainName}
    ← backend
    chainName
    from
    competition_detail
    (e.g.
    XLayer
    ). Special case: if backend
    chainName
    is already Solana, the activity is single-chain — collapse the sentence to
    This competition runs on Solana
    and the trailing question to
    Would you like me to walk you through the detailed rules, or help you initiate a trade on Solana?
    . The disclaimer line still appears at the end either way.
  • {totalPrizePool}
    ← total reward pool (sum of all
    prizePoolDistribution[].totalReward
    +
    rewardUnit
    , e.g.
    500 DJT
    ).
<NEVER> - ❌ Do NOT drop the hardcoded `Solana` mention even when the backend's primary chain is already an EVM chain — the activity actually runs on both chains. - ❌ Do NOT drop or merge the four key phrases of the lead sentence: (1) which two chains it runs on, (2) the total prize pool, (3) the dual-axis PnL%/realized PnL ranking, (4) the existence of Participation and Skill Quality Awards. These are required content; the wording can be localized but the four pieces must all appear. - ❌ Do NOT drop the bracketed disclaimer line — it must appear on its own line at the end of the message, in the user's language. </NEVER>
<MUST> **每次`competition_join`调用成功(工具返回`joined: true`)时,输出下方固定模板**。结构(引导语+双链说明+收尾问题+单独一行的括号内免责声明)固定。Solana字面量为硬编码;`{chainName}`和`{totalPrizePool}`从`competition_detail`填充(若未缓存,请先调用该接口)。将自然语言字符串翻译成用户使用的语言,同时保留结构、占位符及`Solana`字面量。 </MUST>
模板:
报名成功!本次竞赛同时在{chainName}和Solana上进行,总奖池为{totalPrizePool}。交易竞赛将按盈亏率和已实现盈亏进行排名,另有参与奖励和Skill质量奖。你想让我详细讲解规则,还是帮你在{chainName}或Solana上发起交易?

[免责声明:数字资产交易存在风险,价格波动剧烈。请充分了解风险并在交易前自行研究。]
字段映射规则
  • {chainName}
    competition_detail
    中的后端
    chainName
    (例如
    XLayer
    )。特殊情况:若后端
    chainName
    已为Solana,则活动为单链——将句子简化为
    本次竞赛在Solana上进行
    ,收尾问题简化为
    你想让我详细讲解规则,还是帮你在Solana上发起交易?
    。无论哪种情况,免责声明行仍需放在末尾。
  • {totalPrizePool}
    ← 总奖池(所有
    prizePoolDistribution[].totalReward
    之和 +
    rewardUnit
    ,例如
    500 DJT
    )。
<NEVER> - ❌ 即使后端主链为EVM链,也不得省略硬编码的`Solana`提及——活动实际上在两条链上同时进行。 - ❌ 不得省略引导语中的四个关键信息:(1) 活动在哪些链上进行,(2) 总奖池金额,(3) 按盈亏率/已实现盈亏双维度排名,(4) 存在参与奖励和Skill质量奖。这些是必填内容;表述可本地化,但四个信息必须全部包含。 - ❌ 不得省略括号内的免责声明行——必须单独放在消息末尾,使用用户的语言。 </NEVER>

Other errors

其他错误

On error containing
region
/
not available in your region
:
Registration failed: service is not available in your region. Please switch to a supported region and try again.
On any other error:
Operation failed. Please contact customer support.
错误包含
region
/
not available in your region
时:
报名失败:该服务在你的地区不可用,请切换到支持的地区后重试。
其他任何错误:
操作失败,请联系客服。

Step 4 — Trade (delegate to okx-dex-swap)

步骤4 — 交易(委托给okx-dex-swap)

When user asks to trade per competition rules:
Case A — User does NOT provide a CA (only token name/symbol):
  1. Resolve the CA via the
    token_search
    MCP tool (CLI:
    onchainos token search
    ).
  2. Confirm with user before proceeding:
    Just to confirm, the CA for token "{tokenSymbol}" is "{contractAddress}". Is that correct?
  3. Wait for user to confirm. Only proceed after explicit "yes".
  4. Then follow Case B below.
Case B — User provides a CA directly:
  1. Execute swap via the
    swap_swap
    MCP tool (CLI:
    onchainos swap swap
    ); see the
    okx-dex-swap
    skill for parameters.
  2. Report: "Done — your trade has been submitted." + tx hash.
Note: do NOT pre-empt the swap with an extra "token prices are volatile, do you accept the risk?" prompt. The user already requested the trade — additional friction is unwanted. Per-token risk metadata (e.g. honeypot / extreme volatility flags) belongs to
okx-security
and only fires when actually flagged.
Competition constraints per trade:
  • Single-trade min $1 (orders below $1 are not counted)
  • Token pairs must match competition rules from
    detail
    response
当用户要求按竞赛规则进行交易时:
场景A — 用户未提供合约地址(仅提供代币名称/符号):
  1. 通过
    token_search
    MCP工具解析合约地址(CLI命令:
    onchainos token search
    )。
  2. 执行前与用户确认:
    确认一下,代币"{tokenSymbol}"的合约地址是"{contractAddress}",对吗?
  3. 等待用户确认。仅在用户明确回复“是”后继续。
  4. 然后按照场景B操作。
场景B — 用户直接提供合约地址:
  1. 执行兑换:通过
    swap_swap
    MCP工具(CLI命令:
    onchainos swap swap
    );参数请参考
    okx-dex-swap
    技能。
  2. 反馈:"已完成——你的交易已提交。" + 交易哈希。
注意:无需在兑换前额外提示“代币价格波动,你是否接受风险?”。用户已主动请求交易,额外的提示会增加操作摩擦。代币风险元数据(例如蜜罐/极端波动标记)属于
okx-security
,仅在实际触发时展示。
竞赛交易约束:
  • 单笔交易最低1美元(低于1美元的订单不计入)
  • 代币对必须符合
    detail
    响应中的竞赛规则

Step 5 — Check Status & Rank

步骤5 — 查看状态与排名

Check participation status

查看参与状态

bash
onchainos competition user-status --evm-wallet <evm_addr> --sol-wallet <sol_addr>                       # all activities
onchainos competition user-status --activity-id <id> --evm-wallet <evm_addr> --sol-wallet <sol_addr>   # single
Display: join status, join time, reward status, reward amount.
  • If
    rewardStatus=1
    (won, not claimed): proactively ask "You have won a reward. Would you like me to claim it for you?"
  • If
    rewardStatus=3
    (expired): "Your reward has expired and can no longer be claimed."
bash
onchainos competition user-status --evm-wallet <evm_addr> --sol-wallet <sol_addr>                       # 所有活动
onchainos competition user-status --activity-id <id> --evm-wallet <evm_addr> --sol-wallet <sol_addr>   # 单个活动
展示:报名状态、报名时间、奖励状态、奖励金额。
  • rewardStatus=1
    (已获奖但未领取):主动询问"你已获得奖励,是否需要帮你领取?"
  • rewardStatus=3
    (已过期):"你的奖励已过期,无法再领取。"

Check leaderboard (full board)

查看排行榜(完整榜单)

<MUST> When the user says "view leaderboard" without specifying which one, you MUST:
  1. Call
    competition_detail
    for the activity and enumerate
    tabConfigs[].rankFieldConfig[].sortValueMap.descend
    — this is the full set of leaderboards the activity exposes.
  2. Call
    competition_rank
    ONCE PER
    sort_type
    (one HTTP call per leaderboard) so you have data for every leaderboard.
  3. Render ALL of them in the response — one section per leaderboard. Do NOT silently default to a single leaderboard (e.g. only
    sort_type=1
    ) when the activity has more than one.
Only ask the user to pick one when there are clearly too many to fit (≥ 3 leaderboards on a single competition). With 1–2 leaderboards, always show all by default. </MUST>
tabConfigs[].rankFieldConfig[]
fields:
  • title
    — display name (e.g.
    PnL%
    ,
    PnL
    )
  • key
    — internal sort field (e.g.
    pnl
    ,
    realizedProfit
    )
  • sortValueMap.descend
    — the numeric value to pass as
    --sort-type
Per-leaderboard fetch:
bash
onchainos competition rank --activity-id <id> --wallet <addr> --sort-type <descend> --limit 20
Display rules: for each leaderboard render a separate section labeled by its
title
. Each section shows top N entries: rank, nickname (masked), score (
userTotal
formatted by
format
field), estimated reward.
Example response (activity with two leaderboards):
PnL% leaderboard — pool 200 DJT Rank 1, Agentic....sMWP, PnL% +0.17%, estimated reward 100 DJT Rank 2, Agentic....gweD, PnL% +0.03%, estimated reward 20 DJT
PnL leaderboard — pool 200 DJT Rank 1, Agentic....sMWP, PnL $0.1885, estimated reward 100 DJT Rank 2, Agentic....gweD, PnL $0.0006, estimated reward 20 DJT
After the leaderboards, append a "Your rank" section using the CASE 1 / 2 / 3 templates from the next section, since you already have all the data.
<MUST> 当用户说“查看排行榜”但未指定具体榜单时,必须:
  1. 调用
    competition_detail
    获取活动信息,枚举
    tabConfigs[].rankFieldConfig[].sortValueMap.descend
    ——这是活动提供的所有榜单。
  2. 针对每个
    sort_type
    调用一次
    competition_rank
    (每个榜单一次HTTP调用),获取所有榜单的数据。
  3. 在响应中渲染所有榜单——每个榜单一个章节。当活动有多个榜单时,请勿默认仅展示单个榜单(例如仅
    sort_type=1
    )。
仅当榜单数量过多(单个竞赛≥3个)时,才请用户选择其中一个。若榜单数量为1-2个,请默认展示所有榜单。 </MUST>
tabConfigs[].rankFieldConfig[]
字段:
  • title
    — 显示名称(例如
    PnL%
    PnL
  • key
    — 内部排序字段(例如
    pnl
    realizedProfit
  • sortValueMap.descend
    — 需传入
    --sort-type
    的数值
每个榜单的获取命令:
bash
onchainos competition rank --activity-id <id> --wallet <addr> --sort-type <descend> --limit 20
展示规则: 每个榜单单独一个章节,以其
title
为标题。每个章节展示前N条记录:排名、昵称(掩码处理)、得分(
userTotal
format
字段格式化)、预估奖励。
示例响应(含两个榜单的活动):
盈亏率排行榜 — 奖池200 DJT 第1名,Agentic....sMWP,盈亏率 +0.17%,预估奖励100 DJT 第2名,Agentic....gweD,盈亏率 +0.03%,预估奖励20 DJT
盈亏排行榜 — 奖池200 DJT 第1名,Agentic....sMWP,盈亏 $0.1885,预估奖励100 DJT 第2名,Agentic....gweD,盈亏 $0.0006,预估奖励20 DJT
排行榜展示完成后,追加“你的排名”章节,使用下一节中的场景1/2/3模板,因为你已获取所有数据。

Check user's own rank (across ALL leaderboards)

查看用户自身排名(所有榜单)

A user can simultaneously appear on multiple leaderboards (e.g. PnL% AND PnL). When the user asks "what's my rank?", you MUST query every leaderboard the activity exposes, then render one of the three fixed templates below.
Required flow:
  1. Call
    competition_detail
    → enumerate
    tabConfigs[].rankFieldConfig[].sortValueMap.descend
    to get the full set of
    sort_type
    values for this activity.
  2. For EACH
    sort_type
    , call
    competition_rank --sort-type <descend>
    and capture
    myRankInfo
    plus the leaderboard's threshold (lowest
    userTotal
    in
    allRankInfos
    ).
  3. Classify the result:
    • CASE 1 — user has
      currentRank > 0
      on every leaderboard
    • CASE 2 — user has
      currentRank > 0
      on at least one but not all
    • CASE 3 — user has no
      currentRank > 0
      on any leaderboard
  4. Output the matching fixed template, rendered in the user's language (English canonical below; localize for Chinese / other-language users).
<MUST> **Output exactly the matching template structure below — never paraphrase the data fields, never collapse the two-leaderboard sections into one. Localize the natural-language strings to the user's language; keep placeholders, numeric values, and units verbatim.** </MUST>
用户可能同时出现在多个榜单上(例如盈亏率和盈亏榜单)。当用户询问“我的排名是多少?”时,必须查询活动提供的所有榜单,然后渲染以下三个固定模板中的一个。
必要流程:
  1. 调用
    competition_detail
    →枚举
    tabConfigs[].rankFieldConfig[].sortValueMap.descend
    ,获取该活动的所有
    sort_type
    值。
  2. 针对每个
    sort_type
    ,调用
    competition_rank --sort-type <descend>
    ,捕获
    myRankInfo
    及榜单门槛(
    allRankInfos
    中的最低
    userTotal
    )。
  3. 对结果进行分类:
    • 场景1 — 用户在所有榜单上的
      currentRank > 0
    • 场景2 — 用户在至少一个榜单上的
      currentRank > 0
      ,但并非所有榜单
    • 场景3 — 用户在所有榜单上的
      currentRank
      均不大于0
  4. 输出匹配的固定模板,使用用户的语言渲染(下方为英文标准版;中文/其他语言用户需本地化)。
<MUST> **严格输出匹配的模板结构——切勿改写数据字段,切勿将两个榜单的章节合并为一个。将自然语言字符串本地化到用户的语言;占位符、数值和单位保持不变。** </MUST>
CASE 1 — ranked on both PnL and PnL%
场景1 — 同时进入盈亏和盈亏率榜单
Template:
Realized PnL ranking:
You are currently ranked #{pnlRank}, estimated reward {pnlReward} {rewardUnit}!

Realized ROI ranking:
You are currently ranked #{roiRank}, estimated reward {roiReward} {rewardUnit}!

| Leaderboard | My rank | Estimated reward |
|-------------|---------|------------------|
| Realized PnL | #{pnlRank} | {pnlReward} {rewardUnit} |
| Realized ROI | #{roiRank} | {roiReward} {rewardUnit} |

Your total estimated reward across both rankings: {totalReward} {rewardUnit} (sum of the two)
模板:
已实现盈亏排名:
你当前位列第#{pnlRank}名,预估奖励{pnlReward} {rewardUnit}!

已实现回报率排名:
你当前位列第#{roiRank}名,预估奖励{roiReward} {rewardUnit}!

| 榜单 | 我的排名 | 预估奖励 |
|-------------|---------|------------------|
| 已实现盈亏 | 第#{pnlRank}名 | {pnlReward} {rewardUnit} |
| 已实现回报率 | 第#{roiRank}名 | {roiReward} {rewardUnit} |

你在两个榜单上的预估总奖励:{totalReward} {rewardUnit}(两个奖励之和)
CASE 2 — ranked on one leaderboard, off the other
场景2 — 进入一个榜单,未进入另一个榜单
There are two symmetric sub-cases. The structure is identical: the ranked leaderboard goes first ("ranked #N, estimated reward X"), then the unranked one ("not on the leaderboard, current value Y, threshold Z"). Each sub-case has its own pinned template — do NOT improvise the unranked-section unit (
%
for PnL%, currency
$
for PnL).
包含两个对称子场景。结构相同:先展示用户已进入的榜单(“位列第N名,预估奖励X”),再展示未进入的榜单(“未进入排行榜,当前值Y,门槛Z”)。每个子场景有固定模板——请勿自行修改未进入榜单的单位(盈亏率使用
%
,盈亏使用
$
)。
CASE 2-A — on PnL, off PnL% (currentRank for sort_type=7 > 0; sort_type=1 == 0)
场景2-A — 进入盈亏榜单,未进入盈亏率榜单(sort_type=7的currentRank > 0;sort_type=1 == 0)
Template:
Realized PnL ranking:
You are currently ranked #{pnlRank}, estimated reward {pnlReward} {rewardUnit}!

Realized ROI ranking:
Not on the leaderboard yet. Your current realized ROI is {currentRoi}%. You need at least {minRoi}% (the current leaderboard minimum) to qualify.
模板:
已实现盈亏排名:
你当前位列第#{pnlRank}名,预估奖励{pnlReward} {rewardUnit}!

已实现回报率排名:
尚未进入排行榜。你当前的已实现回报率为{currentRoi}%,需达到至少{minRoi}%(当前排行榜最低门槛)才能入围。
CASE 2-B — on PnL%, off PnL (currentRank for sort_type=1 > 0; sort_type=7 == 0)
场景2-B — 进入盈亏率榜单,未进入盈亏榜单(sort_type=1的currentRank > 0;sort_type=7 == 0)
Template:
Realized ROI ranking:
You are currently ranked #{roiRank}, estimated reward {roiReward} {rewardUnit}!

Realized PnL ranking:
Not on the leaderboard yet. Your current realized PnL is ${currentPnl}. You need at least ${minPnl} (the current leaderboard minimum) to qualify.
Section ordering rule: the leaderboard the user IS ranked on ALWAYS goes first. Don't put the "Not on the leaderboard" section before the ranked one.
Unit rule: PnL% uses
%
suffix (no currency symbol); PnL uses
$
prefix (or the appropriate currency unit). Do NOT mix them up — the user's threshold for PnL is a dollar amount, not a percentage.
模板:
已实现回报率排名:
你当前位列第#{roiRank}名,预估奖励{roiReward} {rewardUnit}!

已实现盈亏排名:
尚未进入排行榜。你当前的已实现盈亏为${currentPnl},需达到至少${minPnl}(当前排行榜最低门槛)才能入围。
章节顺序规则:用户已进入的榜单必须放在前面。请勿将“未进入排行榜”章节放在已进入榜单之前。
单位规则:盈亏率使用
%
后缀(无货币符号);盈亏使用
$
前缀(或对应货币单位)。请勿混淆——盈亏的门槛是金额,而非百分比。
CASE 3 — off both leaderboards
场景3 — 未进入任何榜单
Template:
Your address is not on any leaderboard. Your current realized PnL is ${currentPnl}, realized ROI {currentRoi}%.
The current minimum to qualify: realized PnL ${minPnl}, realized ROI {minRoi}%.
模板:
你的地址未进入任何排行榜。你当前的已实现盈亏为${currentPnl},已实现回报率为{currentRoi}%。
当前入围门槛:已实现盈亏${minPnl},已实现回报率{minRoi}%。
Field-mapping rules
字段映射规则
  • {pnlRank}
    myRankInfo.currentRank
    of the PnL leaderboard (sort_type 7)
  • {pnlReward}
    myRankInfo.expectedRewards
    of the PnL leaderboard
  • {roiRank}
    myRankInfo.currentRank
    of the PnL% leaderboard (sort_type 1)
  • {roiReward}
    myRankInfo.expectedRewards
    of the PnL% leaderboard
  • {rewardUnit}
    myRankInfo.rewardUnit
    (e.g.
    DJT
    ); per-leaderboard if they ever differ
  • {totalReward}
    pnlReward + roiReward
    (numeric sum, same unit)
  • {currentRoi}
    ← user's PnL% score from
    myRankInfo.userTotal
    of the PnL% board (or 0 if backend returned null)
  • {currentPnl}
    ← user's PnL score from
    myRankInfo.userTotal
    of the PnL board
  • {minRoi}
    ← lowest qualifying PnL% — last entry's
    userTotal
    in the PnL% board's
    allRankInfos[]
  • {minPnl}
    ← lowest qualifying PnL — last entry's
    userTotal
    in the PnL board's
    allRankInfos[]
If the activity exposes leaderboards beyond PnL/PnL% (future expansion via
tabConfigs[]
), extend the same template pattern: one section per leaderboard, summary table aggregates all, total reward sums all
expectedRewards
.
format
:
1
=number,
2
=percentage,
3
=token amount with unit.
  • {pnlRank}
    ← 盈亏榜单(sort_type 7)的
    myRankInfo.currentRank
  • {pnlReward}
    ← 盈亏榜单的
    myRankInfo.expectedRewards
  • {roiRank}
    ← 盈亏率榜单(sort_type 1)的
    myRankInfo.currentRank
  • {roiReward}
    ← 盈亏率榜单的
    myRankInfo.expectedRewards
  • {rewardUnit}
    myRankInfo.rewardUnit
    (例如
    DJT
    );若各榜单单位不同,则按榜单分别使用
  • {totalReward}
    pnlReward + roiReward
    (数值求和,单位相同)
  • {currentRoi}
    ← 用户在盈亏率榜单的
    myRankInfo.userTotal
    中的盈亏率得分(若后端返回null则为0)
  • {currentPnl}
    ← 用户在盈亏榜单的
    myRankInfo.userTotal
    中的盈亏得分
  • {minRoi}
    ← 盈亏率榜单的最低入围门槛——
    allRankInfos[]
    最后一条记录的
    userTotal
  • {minPnl}
    ← 盈亏榜单的最低入围门槛——
    allRankInfos[]
    最后一条记录的
    userTotal
若活动提供盈亏/盈亏率之外的榜单(未来通过
tabConfigs[]
扩展),请遵循相同的模板模式:每个榜单一个章节,汇总表格聚合所有数据,总奖励为所有
expectedRewards
之和。
format
1
=数字,
2
=百分比,
3
=带单位的代币数量。

Step 6 — Claim Reward

步骤6 — 领取奖励

Check status first via
competition_user_status
:
rewardStatus
Action
0Not won — inform user, no claim needed
1Won — proceed to claim
2Already claimed
3Expired — "Your reward has expired and can no longer be claimed"
先通过
competition_user_status
检查状态:
rewardStatus
操作
0未获奖——告知用户,无需领取
1已获奖——继续领取流程
2已领取
3已过期——“你的奖励已过期,无法再领取”

Atomic claim (the only correct path)

原子领取(唯一正确流程)

Both the MCP tool
competition_claim
and the CLI
onchainos competition claim
now do the same atomic flow: pre-check
rewardStatus
, fetch calldata, sign each entry with the TEE session, broadcast on-chain, return txHash array. The CLI no longer returns raw unsigned calldata — the only externally visible behavior is the final result.
MCP (preferred when running inside Claude Code / any AI environment):
competition_claim(activity_name="...")  →  { rewardAmount, rewardUnit, succeeded[], failed[] }
CLI (terminal use, or AI shelling out via Bash):
bash
onchainos competition claim --activity-id <id> --evm-wallet <evm_addr> --sol-wallet <sol_addr>
MCP工具
competition_claim
和CLI命令
onchainos competition claim
现在执行相同的原子流程:预检查
rewardStatus
、获取调用数据、使用TEE会话签名每个条目、链上广播、返回txHash数组。CLI不再返回原始未签名调用数据——唯一对外可见的行为是最终结果。
MCP工具(在Claude Code/任何AI环境中运行时首选):
competition_claim(activity_name="...")  →  { rewardAmount, rewardUnit, succeeded[], failed[] }
CLI命令(终端使用,或AI通过Bash调用):
bash
onchainos competition claim --activity-id <id> --evm-wallet <evm_addr> --sol-wallet <sol_addr>

→ returns the same { rewardAmount, rewardUnit, succeeded[], failed[] } shape

→ 返回相同的 { rewardAmount, rewardUnit, succeeded[], failed[] } 结构


Result shape (both paths):
```json
{
  "rewardAmount": "460",
  "rewardUnit": "PYBOBO",
  "totalEntries": 1,
  "succeeded": [{"contractAddress": "...", "chain": "501", "txHash": "...", "orderId": "..."}],
  "failed": []
}
How to report to the user:
  • All succeeded (
    failed: []
    ): "Claimed {rewardAmount} {rewardUnit}, tx hash: {txHash}"
  • Partial success (some
    failed
    ): list each succeeded txHash, then list the failed entries with their
    error
    , then append the fixed failure-suggestion block (template below). Do NOT re-run claim blindly — succeeded entries already landed; another call will hit the "reward already claimed" guard.
  • All failed: the tool returns an error, not this shape — surface the error message verbatim, then append the fixed failure-suggestion block.
The flow blocks before signing if
rewardStatus
is 0 (not eligible), 2 (already claimed), or 3 (expired). The error message is plain text — relay it to the user. Skip the failure-suggestion block in these pre-check rejections (they are semantic, not transient — telling the user to "check Gas / try later" is misleading).

结果结构(两种方式相同):
```json
{
  "rewardAmount": "460",
  "rewardUnit": "PYBOBO",
  "totalEntries": 1,
  "succeeded": [{"contractAddress": "...", "chain": "501", "txHash": "...", "orderId": "..."}],
  "failed": []
}
如何向用户反馈:
  • 全部成功(
    failed: []
    ):"已领取{rewardAmount} {rewardUnit},交易哈希:{txHash}"
  • 部分成功(存在
    failed
    条目):列出每个成功的txHash,然后列出失败条目及其
    error
    ,最后追加固定的失败建议块(模板如下)。请勿盲目重新领取——成功条目已生效;再次调用会触发“奖励已领取”限制。
  • 全部失败:工具返回错误,而非上述结构——直接展示错误消息,然后追加固定的失败建议块
rewardStatus
为0(无资格)、2(已领取)或3(已过期),流程将在签名前终止。错误消息为纯文本——直接转发给用户。在这些预检查拒绝的情况下,跳过失败建议块(这些是语义错误,而非临时错误——告知用户“检查Gas/稍后重试”会产生误导)。
Fixed failure-suggestion block
固定失败建议块
<MUST> For runtime failures (signing/broadcast/simulation errors, network errors, unknown errors), append this block after the error description. Translate to the user's language while preserving the heading + 3 bullet items in this order. Do NOT add or remove items. </MUST>
Template:
Suggestions:
- The claim process requires Gas. Please make sure your Gas is sufficient.
- Try again later — this may be a transient network issue.
- If it fails repeatedly, please contact customer support.
<NEVER> - ❌ Do NOT show this block on pre-check rejections (rewardStatus=0/2/3) — the issue is not Gas / not transient. - ❌ Do NOT show this block on `code=11002` (not won) or `code=11008` (claim expired/already claimed) — same reason. </NEVER> <NEVER> - ❌ Do NOT chain `gateway_broadcast` after a claim call — the on-chain submission already happened inside the tool. - ❌ Do NOT manually construct, encode, or sign a transaction (no Python base58 encoding, no manual hex assembly). The TEE-managed wallet key is the only valid signer. - ❌ Do NOT inspect the result for an empty `base58CallData` and conclude the CLI cannot sign a Solana claim — that field is empirically empty for Solana; the CLI/MCP code internally falls back to encoding `tx.data` byte array via base58 and proceeds. Just trust the `succeeded[]` and `failed[]` arrays. - ❌ Do NOT split into a two-step "fetch calldata then wallet contract-call" flow — that mode no longer exists; the claim command is atomic. </NEVER>
On claim error (code 11002
not eligible for reward
):
"You did not win a reward and cannot claim."
On any other error: "Operation failed. Please contact customer support."
<MUST> 对于运行时失败(签名/广播/模拟错误、网络错误、未知错误),在错误描述后追加此块。翻译成用户使用的语言,同时保留标题+3个项目符号的顺序。请勿添加或删除项目。 </MUST>
模板:
建议:
- 领取流程需要Gas,请确保你的Gas充足。
- 稍后重试——这可能是临时网络问题。
- 若多次失败,请联系客服。
<NEVER> - ❌ 请勿在预检查拒绝(rewardStatus=0/2/3)时展示此块——问题并非Gas/临时错误。 - ❌ 请勿在`code=11002`(未获奖)或`code=11008`(奖励已过期/已领取)时展示此块——原因相同。 </NEVER> <NEVER> - ❌ 请勿在领取调用后链式调用`gateway_broadcast`——链上提交已在工具内部完成。 - ❌ 请勿手动构建、编码或签名交易(无需Python base58编码,无需手动十六进制组装)。TEE管理的钱包密钥是唯一有效的签名者。 - ❌ 请勿因Solana领取的`base58CallData`为空就认为CLI无法签名Solana领取——该字段在Solana情况下经验证为空;CLI/MCP代码会内部回退到将`tx.data`字节数组通过base58编码并继续执行。请信任`succeeded[]`和`failed[]`数组。 - ❌ 请勿拆分为“获取调用数据然后钱包合约调用”的两步流程——该模式已不再存在;领取命令为原子操作。 </NEVER>
领取错误(code 11002
not eligible for reward
):
"你未获得奖励,无法领取。"
其他任何错误: "操作失败,请联系客服。"

Additional Flows

附加流程

Query Registered Wallet

查询已注册钱包

When user asks "show my registered address" or similar:
  1. Call
    competition_user_status
    (MCP) — addresses auto-resolve from the active account; no
    wallet_status
    needed. CLI equivalent:
    onchainos competition user-status --evm-wallet <evm_addr> --sol-wallet <sol_addr>
    (omit
    --activity-id
    to query all activities).
  2. Find entries where
    joinStatus=1
  3. For each matched entry, present: competition name (
    activityName
    ) + chain (
    chainName
    ) + masked address (first4...last4). Use chain to determine which address was used (EVM or SOL).
If multiple entries match, list all of them.
Example (single):
Your Account 1 is registered for XXX Trading Competition. Registered address: Solana address DeEV...Fbx.
Example (multiple):
Your Account 1 is registered for the following trading competitions:
  • XXX Trading Competition (Solana): DeEV...Fbx
  • YYY Trading Competition (XLayer): 0x1234...abcd
If no entry has
joinStatus=1
:
You are not currently registered for any trading competition.
当用户询问“显示我的已注册地址”或类似问题时:
  1. 调用
    competition_user_status
    (MCP工具)——地址从活跃账户自动解析;无需
    wallet_status
    。CLI等效命令:
    onchainos competition user-status --evm-wallet <evm_addr> --sol-wallet <sol_addr>
    (省略
    --activity-id
    可查询所有活动)。
  2. 找到
    joinStatus=1
    的条目
  3. 对每个匹配的条目,展示:竞赛名称(
    activityName
    )+ 链(
    chainName
    )+ 掩码地址(前4位...后4位)。根据链确定使用的地址(EVM或SOL)。
若存在多个匹配条目,列出所有条目。
示例(单个条目):
你的Account 1已报名XXX交易竞赛。已注册地址:Solana地址 DeEV...Fbx。
示例(多个条目):
你的Account 1已报名以下交易竞赛:
  • XXX交易竞赛(Solana):DeEV...Fbx
  • YYY交易竞赛(XLayer):0x1234...abcd
若没有
joinStatus=1
的条目:
你当前未报名任何交易竞赛。

Wallet Export Guard

钱包导出确认

When the user requests to export the Agentic Wallet:
  1. Call
    competition_user_status
    (MCP) — addresses auto-resolved. CLI equivalent:
    onchainos competition user-status --evm-wallet <evm_addr> --sol-wallet <sol_addr>
    .
  2. If any
    joinStatus=1
    :
    Your wallet is registered for an Agentic Wallet trading competition. Exporting the wallet will forfeit your eligibility for this competition. Please confirm whether you want to proceed with the export.
  3. Only proceed with export if the user explicitly confirms.
当用户请求导出Agentic Wallet时:
  1. 调用
    competition_user_status
    (MCP工具)——地址自动解析。CLI等效命令:
    onchainos competition user-status --evm-wallet <evm_addr> --sol-wallet <sol_addr>
  2. 若存在
    joinStatus=1
    的条目:
    你的钱包已报名Agentic Wallet交易竞赛。导出钱包将导致你失去该竞赛的参赛资格。请确认是否继续导出。
  3. 仅在用户明确确认后才继续导出。

Status Codes

状态码

--status
filter parameter (input only)

--status
筛选参数(仅输入)

ValueMeaning
0Active competitions (default)
1Ended competitions
2All competitions
含义
0活跃竞赛(默认)
1已结束竞赛
2所有竞赛

Response field values

响应字段值

FieldValueMeaning
status3Competition active
status4Competition ended
joinStatus0Not joined
joinStatus1Joined
rewardStatus0Not won
rewardStatus1Won, not claimed
rewardStatus2Claimed
rewardStatus3Reward expired
字段含义
status3竞赛活跃
status4竞赛已结束
joinStatus0未报名
joinStatus1已报名
rewardStatus0未获奖
rewardStatus1已获奖,未领取
rewardStatus2已领取
rewardStatus3奖励已过期

Error Handling

错误处理

ErrorResponse
not logged in
Login is interactive (email + OTP) and cannot run inside this conversation. Tell the user verbatim:
Please run "onchainos wallet login <your_email>" in your terminal, then ask me again.
address limit reached
Registration failed: this wallet account is already registered and cannot register again
code 11002
not eligible for reward
You did not win a reward and cannot claim
code 11003
activity not found / status mismatch
The competition does not exist or its status no longer permits this action
code 11008
Claim expired
The reward has already been claimed or the claim window has expired
code 1860402
failed to assemble transaction
Backend failed to build the on-chain transaction. Ask the user to retry; if it persists, contact customer support
Sui-chain reward claims are not yet supported
Sui rewards must be claimed from the Sui-compatible wallet UI (this client only signs EVM and Solana)
region
/
not available in your region
Registration failed: service is not available in your region. Please switch to a supported region and try again.
Any other errorOperation failed. Please contact customer support.
错误响应
not logged in
登录为交互式操作(邮箱+OTP),无法在此对话中完成。请直接告知用户:
请在终端中运行"onchainos wallet login <your_email>",然后再次请求。
address limit reached
报名失败:该钱包账户已报名,无法重复报名
code 11002
not eligible for reward
你未获得奖励,无法领取
code 11003
activity not found / status mismatch
该竞赛不存在或其状态已不允许此操作
code 11008
Claim expired
奖励已领取或领取窗口已过期
code 1860402
failed to assemble transaction
后端无法构建链上交易。请用户重试;若问题持续,请联系客服
Sui-chain reward claims are not yet supported
Sui奖励需从兼容Sui的钱包UI领取(此客户端仅支持签名EVM和Solana交易)
region
/
not available in your region
报名失败:该服务在你的地区不可用,请切换到支持的地区后重试。
其他任何错误操作失败,请联系客服。
",