- 区块链
【免费下载链接】eos
An open source smart contract platform
本指南以 EOSIO 官方cleos客户端为操作主线,讲解如何使用cleos system undelegatebw撤销此前通过delegatebw委托给其他账户的 CPU(及 NET)带宽资源。读完本文,你将掌握该命令的完整参数语义、常用选项、底层实现原理与验证方法,能够在实际链上安全、准确地执行带宽撤销操作。
目标:撤销为账户或应用委托的资源
在 EOSIO 网络中,账户间的 CPU 与 NET 带宽通过delegatebw动作进行委托(delegate)。当业务场景变化——例如合作方不再需要你为其质押的带宽、或你自己需要收回质押的 CPU 资源时,就需要使用undelegatebw动作来撤销(undelegate)这部分资源。
执行撤销操作时,必须牢记一条硬性约束:
只有当初发起委托的账户(原始委托方)才能撤销对应的带宽资源。被委托方或其他任何第三方账户都无法代为撤销。
这一点在 how-to-undelegate-CPU.md 中有明确警示("Beware that only the account which originally delegated resource can undelegate"),也是整个撤销流程最重要的前提。
开始之前:前置条件与概念准备
在执行撤销操作前,请确认以下条件与概念:
- 安装受支持的
cleos版本:cleos随 EOSIO 软件一同发布,安装 EOSIO 即会安装cleos,具体安装方式参见 00_install。本仓库中cleos的入口实现位于 programs/cleos/main.cpp。 - 确保系统合约已部署:
eosio.contracts仓库中的参考系统合约(reference system contracts)必须已部署并用于管理系统资源。undelegatebw动作最终由系统合约中的eosio账户处理,本仓库本身不包含该系统合约源码,cleos只负责构造并发送该动作。 - 理解以下基础概念:
- 账户(Account):EOSIO 网络中的基本身份单元,资源的委托与撤销都以账户为粒度;
- 网络带宽(NET Bandwidth):决定账户每单位时间内可发送交易字节数上限的资源;
- CPU 带宽(CPU Bandwidth):决定账户交易执行可用 CPU 时间上限的资源。
核心操作:撤销 0.01 SYS 的 CPU 带宽
以下命令将此前从账户bob委托给账户alice的0.01 SYSCPU 带宽撤销回来(本示例来自 how-to-undelegate-CPU.md):
cleos system undelegatebw bob alice "0 SYS" "0.01 SYS"命令执行成功后,会得到类似如下的输出:
executed transaction: e7e7edb6c5556de933f9d663fea8b4a9cd56ece6ff2cebf056ddd0835efa6606 184 bytes 452 us # eosio <= eosio::undelegatebw {"from":"alice","receiver":"bob","unstake_net_quantity":"0.0000 EOS","unstake_cpu_qu... warning: transaction executed locally, but may not be confirmed by the network yet ]输出含义解析:
executed transaction: <txid>:交易 ID,随后是交易字节数(184 bytes)与本地执行耗时(452 us);# eosio <= eosio::undelegatebw:eosio系统账户接收并执行了undelegatebw动作,动作载荷中包含from(委托方)、receiver(被委托方)、unstake_net_quantity(撤销的 NET 数量)与unstake_cpu_quantity(撤销的 CPU 数量);- 末尾的
warning是正常提示:交易已在本地节点执行,但尚未确认上链。
位置参数逐一说明
根据命令参考文档 system-undelegatebw.md,该命令包含 4 个必填位置参数:
| 参数 | 类型 | 说明 |
|---|---|---|
from | TEXT | 撤销带宽的账户(即原始委托方) |
receiver | TEXT | 被撤销带宽的账户(即此前接收委托的账户) |
unstake_net_quantity | TEXT | 为 NET 带宽撤销的 EOS/SYS 数量 |
unstake_cpu_quantity | TEXT | 为 CPU 带宽撤销的 EOS/SYS 数量 |
因此cleos system undelegatebw bob alice "0 SYS" "0.01 SYS"的含义是:委托方bob从接收方alice处撤销0.01 SYS的 CPU 带宽,NET 部分撤销0 SYS。数量字符串必须带精度(如"0.01 SYS"),且需与链上符号(Symbol)一致。
需要留意的是,命令行中
from与receiver的先后顺序与自然语言描述容易混淆,请严格以命令参考文档中的参数顺序(先from后receiver)为准。
命令选项详解:控制交易签名、广播与费用预算
undelegatebw复用 cleos 的标准交易选项(同样来自 system-undelegatebw.md),可在实际使用中按需组合:
| 选项 | 说明 |
|---|---|
-h, --help | 打印帮助信息并退出 |
-x, --expirationTEXT | 设置交易过期时间(秒),默认 30s |
-f, --force-unique | 强制交易唯一,会消耗额外带宽,用于防止意外重复提交相同交易 |
-s, --skip-sign | 跳过签名(不使用钱包密钥签名) |
-d, --dont-broadcast | 不广播交易到网络(仅打印到 stdout) |
-r, --ref-blockTEXT | 设置 TAPOS(Transaction as Proof-of-Stake)使用的参考区块号或区块 ID |
-p, --permissionTEXT | 授权使用的账户与权限级别,格式account@permission,默认account@active |
--max-cpu-usage-msUINT | 设置交易执行的 CPU 预算上限(毫秒),默认 0 表示不限制 |
--max-net-usageUINT | 设置交易的 NET 用量预算上限(字节),默认 0 表示不限制 |
--delay-secUINT | 设置交易延迟秒数,默认 0s |
-j, --json | 以 JSON 格式打印结果 |
常用组合示例——只打印交易内容而不广播(可用于预先审查):
cleos system undelegatebw bob alice "0 SYS" "0.01 SYS" -d -j源码级剖析:cleos 如何构造 undelegatebw 动作
cleos system undelegatebw的底层实现在 programs/cleos/main.cpp 的undelegate_bandwidth_subcommand结构中。从源码可以看到完整的数据流:
undelegate_bandwidth->add_option("from", from_str, localized("The account undelegating bandwidth"))->required(); undelegate_bandwidth->add_option("receiver", receiver_str, localized("The account to undelegate bandwidth from"))->required(); undelegate_bandwidth->add_option("unstake_net_quantity", unstake_net_amount, localized("The amount of tokens to undelegate for network bandwidth"))->required(); undelegate_bandwidth->add_option("unstake_cpu_quantity", unstake_cpu_amount, localized("The amount of tokens to undelegate for CPU bandwidth"))->required(); add_standard_transaction_options_plus_signing(undelegate_bandwidth, "from@active");其回调函数则完成动作载荷的构造与发送:
undelegate_bandwidth->callback([this] { fc::variant act_payload = fc::mutable_variant_object() ("from", from_str) ("receiver", receiver_str) ("unstake_net_quantity", to_asset(unstake_net_amount)) ("unstake_cpu_quantity", to_asset(unstake_cpu_amount)); auto accountPermissions = get_account_permissions(tx_permission, {name(from_str), config::active_name}); send_actions({create_action(accountPermissions, config::system_account_name, "undelegatebw"_n, act_payload)}, signing_keys_opt.get_keys()); });关键实现事实:
- 动作目标:动作发送到
config::system_account_name(即eosio系统账户),动作名为undelegatebw,由已部署的系统合约执行资源账本更新; - 数量转换:用户输入的字符串数量经
to_asset()转换为asset类型,保证精度与符号合法性; - 默认权限:默认使用
from@active权限签名(add_standard_transaction_options_plus_signing(undelegate_bandwidth, "from@active")),也解释了为何只有from账户(原始委托方)能发起该操作——权限模型天然约束了操作主体; - 注意对比:与
delegatebw(实现于 programs/cleos/main.cpp)不同,undelegatebw的载荷只有from、receiver、unstake_net_quantity、unstake_cpu_quantity四个字段,没有transfer标志——带宽一旦撤销,其投票权与撤销权默认回归委托方。
相关操作:自我撤销(unstake)与 NET 撤销
撤销自己账户的带宽(unstake 场景)
当委托方与接收方是同一账户时(即自己给自己质押带宽),撤销操作退化为常见的 "unstake" 场景。参考 how-to-unstake-CPU.md,撤销alice自己账户0.01 SYSCPU 带宽的命令为:
cleos system undelegatebw alice alice "0.01 SYS" "0 SYS"此时from与receiver均为alice,动作载荷为{"from":"alice","receiver":"alice",...}。
撤销 NET 带宽
同样的命令结构也适用于 NET 带宽的撤销,参考 how-to-undelegate-NET.md,将 CPU 数量的0.01 SYS移到 NET 位置即可:
cleos system undelegatebw bob alice "0.01 SYS" "0 SYS"与委托命令的对照
撤销操作是委托操作的逆过程,委托命令见 how-to-delegate-CPU-resource.md:
cleos system delegatebw bob alice "0 SYS" "0.01 SYS"两者参数一一对应(stake_net_quantity/stake_cpu_quantity对应撤销时的unstake_net_quantity/unstake_cpu_quantity),完整的参数对照可查阅命令参考文档 system-delegatebw.md 与 system-undelegatebw.md,命令总索引见 system/index.md。
测试与验证:仓库中的撤销用例
本仓库的单元测试基建为我们提供了撤销操作的验证模板。在 unittests/eosio_system_tester.hpp 中,eosio_system_tester测试工具封装了unstake辅助函数,其构造的动作与cleos完全一致:
action_result unstake( const account_name& from, const account_name& to, const asset& net, const asset& cpu ) { return push_action( name(from), "undelegatebw"_n, mvo() ("from", from) ("receiver", to) ("unstake_net_quantity", net) ("unstake_cpu_quantity", cpu) ); }这印证了两点事实:
undelegatebw动作的标准载荷字段即为from、receiver、unstake_net_quantity、unstake_cpu_quantity,与 unittests/contracts/eosio.system/eosio.system.abi 中声明的 ABI 一致;- 测试中以
from账户为签名者推送动作,再次确认了"只有原始委托方才能撤销"的权限模型。
同时,tests/Node.py 等集成测试脚本中也有对undelegatebw的调用覆盖,可用于端到端流程验证。
注意事项与常见问题
- 只有原始委托方可以撤销:若账户 A 曾将带宽委托给 B,只有 A 能发起
undelegatebw,B 或第三方账户无权操作;撤销后资源回归 A,而非自动归属 B。 - 不能超额撤销:撤销数量不能超过此前委托的数量,否则系统合约会拒绝该动作。
- 交易确认:输出中的
warning: transaction executed locally, but may not be confirmed by the network yet属正常提示,最终以上链后的区块确认为准。 - 资源回收时机:
undelegatebw动作由系统合约处理,撤销的 token 会进入系统合约的资源回收流程,具体到账时机取决于系统合约实现(该合约源码不在本仓库内,来自独立的eosio.contracts仓库)。 - 权限设置:默认使用
from@active权限,如委托方使用自定义权限管理资源,可通过-p选项显式指定。
- 区块链
【免费下载链接】eos
An open source smart contract platform
相关推荐
EOSIO cleos system listbw 命令详解:查询账户委托带宽(Delegated Bandwidth)
EOSIO cleos system listbw 命令详解:查询账户委托带宽(Delegated Bandwidth) 导读 cleos system lis
区块链EOSIO 委托网络带宽(NET)资源:cleos system delegatebw 操作指南与底层原理
EOSIO 委托网络带宽(NET)资源:cleos system delegatebw 操作指南与底层原理 导读 本文基于本仓库(eo/eos)中《How to
区块链EOS 网络带宽(NET)解除质押完全指南:cleos system undelegatebw 实战解析
EOS 网络带宽(NET)解除质押完全指南:cleos system undelegatebw 实战解析 在 EOS 主网与基于 eosio 的链上,账户通过质
区块链
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考