sp() 描述符:给静默支付一个标准写法 图 1
sp() 描述符:给静默支付一个标准写法 · 图 1

静默支付(BIP-352)是近年比特币收款隐私方向最受关注的方案之一:对方只需要你公开一个固定的「静默支付地址」,每次给你付款时,用他自己那笔输入的公钥做一次椭圆曲线运算,就能算出一枚全新的、链上看不出与你有关联的收款脚本。收得多了,区块链上就是一串彼此无关的普通 Taproot 输出。协议本身在 2023 年 3 月立项,2023 年定稿;但围绕它一直有个工程缺口——钱包行业有一套公认的「账户说明书」语言,也就是输出脚本描述符(BIP-380 家族),而静默支付迟迟没有标准写法,各家钱包只能各自约定怎么备份、怎么跨设备恢复这套密钥。BIP-392 就是来补这一块的:2026 年 2 月 6 日立项、Craig Raw 起草(他也是描述符体系 BIP-380/381/382/383 的作者),状态目前仍是草案。

它定义了一个新的顶层描述符表达式 sp(),并为此引入两种专用密钥编码。第一种叫 spscan,装的是「扫描私钥加支出公钥」这对组合——这正是收款方日常需要的最小集合:用扫描私钥在区块里认出属于自己的输出,但不必把支出私钥带在一台联网的热机器上。第二种叫 spspend,把扫描私钥和支出私钥都装进去,适合冷备份场景。两种编码都基于 Bech32m:主网的前缀(人类可读部分)分别是 spscan 和 spspend,测试网在前面加一个字母 t;数据部分先放一个字符 q 表示静默支付版本零,后面按 BIP-352 定义的序列化方式拼接密钥字节。

sp() 本身有两种形态。sp(KEY) 只带一个密钥表达式,接受 spscan 或 spspend 编码的密钥,可以附带密钥来源信息(master 指纹加派生路径),路径指向 BIP-352 推荐的派生层级——扫描钥走一分叉(1h/0),支出钥走另一分叉(0h/0)。sp(KEY,KEY) 则拆成两个参数:第一个必须是扫描私钥(WIF 或扩展私钥),第二个是支出钥,可以接受 BIP-380 体系里任何代表单一密钥的表达式——理论上甚至可以填 BIP-390 的 musig() 聚合公钥。规范同时明确:任何 sp() 表达式里都不允许非压缩公钥,因为 BIP-352 本身只接受压缩形式。这个描述符最终产出的仍是 P2TR 输出,也就是说钱包不需要发明新的地址类型,链上长相和 Taproot 完全一致。

为什么这件事值得单独立一个 BIP?描述符框架这几年已经成为比特币钱包备份、迁移、观察钱包导入的通用底座:importdescriptors 一条命令就能让 Core 接手一个账户,硬件钱包之间的账户交接也越来越依赖这一行文本。静默支付如果没有描述符写法,就意味着用户换钱包时要走私有流程,备份审计工具(列描述符、查校验和、扫描活动)也都对它失效。BIP-392 让「一个地址终身收款且笔笔不关联」这种高级玩法,获得了和普通地址同等的互操作待遇:备份还是一行带校验和的字符串,恢复还是导入描述符,云存储加密备份(BIP-138 那类)也能原样覆盖它。

还有一条容易被忽略的适用边界:sp() 是顶层描述符,不能嵌套进 multi()、and_v() 之类的组合结构里,因为它描述的「输出」依赖发送方输入公钥这个交易级变量,同一份描述符在不同交易里会物化成不同脚本——这与 pkh()、tr() 那种「一行文本对应一族固定脚本」的直觉不同,工具链(校验和计算、活动扫描、余额索引)都要为它开一条特例通道。BIP-392 把密钥、派生路径、版本字符三件事一次钉死,正是为了让这些特例有统一的处理入口。对普通用户,可以这样理解这次标准化的价值:以前用静默支付像住一间房东私搭的客房,家具很好但没有门牌号;现在它有了正规地址,搬家(换钱包)、托付(观察钱包)、查册(备份审计)都能按社区通用的手续办。

快速问答

问:sp() 和直接写 tr() 描述符有什么区别? 答:tr() 描述的是「一枚确定的 Taproot 输出」;sp() 描述的是「一个收款身份」,链上每笔付款的输出脚本都要由发送方用其输入公钥现算,钱包要靠扫描私钥把它们认领回来,两者不是一回事。

问:现在钱包能直接用它吗? 答:它是草案,落地取决于各家钱包和 Core 的支持进度;备份前确认你的钱包导出格式与恢复流程实际兼容,比盯着 BIP 编号更重要。

风险提示:密钥编码与派生路径属于钱包实现细节,跨设备恢复后请先用小额验证收款认领是否完整,再谈大额使用。

sp() 描述符:给静默支付一个标准写法 图 2
sp() 描述符:给静默支付一个标准写法 · 图 2