Bitcoin SV 和 Bitcoin Core 之间首次跨链原子交换
我们已经执行了 Bitcoin SV 和 Bitcoin Core 之间的首次原子交换。 这一成就代表了比特币 SV 的重大进步,以去信任的方式促进了与其他区块链的无缝互操作性。

图片源自Gemini
在上一篇文章中,我们解释了原子交换的高级理论。 我们深入研究了使用哈希时间锁定合约(HTLC)在 BSV 和 BTC 之间进行原子交换的实际示例。 让我们将此过程分解为四个基本步骤,每个步骤都包含您可以自己运行的代码片段。
第 1 步:Alice 在 BTC 上发起交易
该过程从 Alice 开始,她选择一个随机整数 x 并使用 SHA-256 算法创建一个哈希值 (xHash)。 接下来,Alice 部署了一个 Pay-to-Witness-Script-Hash (P2WSH) 交易,其中包括她想要与 Bob 交易的 BTC 数量。
我们使用 bitcoinutils 库构建 Alice 的交易:
def main():# always remember to setup the networksetup('testnet')# TODO: remember to adjust the values marked by "TODO" to your use case.alicePriv = PrivateKey('TODO')alicePub = alicePriv.get_public_key()bobPub = PublicKey('TODO')txid = 'TODO' # Previous transaction IDvout = 2 # Previous transaction ouput indexamount = 0.00001850 # Amount in outputfee = 0.00000125 # Fee in new transactionx = 'f00cfd8df5f92d5e94d1ecbd9b427afd14e03f8a3292ca4128cd59ef7b9643bc'xHash = '1908c59a71781b7a44182ec39dd84a8a9e13dc31691fead8631730f5f5ab7b65'nBlocksLocked = '06' # 6 blocks ~ 1 hr# HTLC script:htlc_redeem_script = Script(['OP_IF','OP_SHA256',xHash,'OP_EQUALVERIFY',bobPub.to_hex(),'OP_CHECKSIG','OP_ELSE',nBlocksLocked,'OP_CHECKSEQUENCEVERIFY','OP_DROP',alicePriv.get_public_key().to_hex(),'OP_CHECKSIG','OP_ENDIF'])toAddress = P2wshAddress.from_script(htlc_redeem_script)# Create transaction input from tx id of utxo.txIn = TxInput(txid, vout)redeem_script1 = Script(['OP_DUP', 'OP_HASH160', alicePub.to_hash160(), 'OP_EQUALVERIFY', 'OP_CHECKSIG'])# Create transaction output, which contains the P2WSH for the HTLC script.txOut = TxOutput(to_satoshis(amount - fee), toAddress.to_script_pub_key())# Create transaction.tx = Transaction([txIn], [txOut], has_segwit=True)# Sign transaction.sig1 = alicePriv.sign_segwit_input(tx, 0, redeem_script1, to_satoshis(amount))tx.witnesses.append(Script([sig1, alicePub.to_hex()]))# Print raw signed transaction ready to be broadcast.print("\nRaw signed transaction:\n" + tx.serialize())print("\nTxId:", tx.get_txid())
执行后,代码将打印原始的序列化交易,我们可以使用 Blockstream 的区块浏览器将其广播到 BTC 网络。
该 P2WSH 交易脚本由条件子句组成,这些条件子句包括需要 Bob 的公钥和秘密 x,或者 Alice 的签名和花费交易的时间延迟。
Bob 在 BTC 上进行应答
作为回应,Bob 在 BSV 区块链上部署了等效的 sCrypt 智能合约,其中包含他准备与 Alice 交换的 BSV 金额。
class HashTimeLockContract extends SmartContract {@prop() readonly alicePubKey: PubKey@prop() readonly bobPubKey: PubKey@prop() readonly hashX: Sha256@prop() readonly timeout: bigint // Can be a timestamp or block height.// hash lock@method()public unlock(x: ByteString, aliceSig: Sig) {// Check if H(x) == this.hashXassert(sha256(x) == this.hashX, 'Invalid secret.')// Verify Alices signature.assert(this.checkSig(aliceSig, this.alicePubKey))}// time lock@method()public cancel(bobSig: Sig) {assert(this.ctx.locktime >= this.timeout, 'locktime has not yet expired')// Verify Bobs signature.assert(this.checkSig(bobSig, this.bobPubKey))}
}
Bob 获得了 x 的哈希值,但不是 x 本身,以及 Alice 的公钥。 然后,他使用以下部署代码部署智能合约:
const alicePubKey = bsv.PublicKey.fromHex('TODO')const bobPrivKey = bsv.PrivateKey.fromWIF('TODO')
const bobPubKey = bobPrivKey.publicKeyconst amount = 100000 // TODO: amount of BSV to be locked in the contractconst xHash = toByteString('1908c59a71781b7a44182ec39dd84a8a9e13dc31691fead8631730f5f5ab7b65'
)
const lockTimeMin = 1688715000 // Timestamp, after which Bob can withdraw his funds.await CrossChainSwap.compile()// Connect Bob signer.
const provider = new DefaultProvider(bsv.Networks.testnet)
const signer = new TestWallet(bobPrivKey, provider)const crossChainSwap = new CrossChainSwap(PubKey(alicePubKey.toHex()),PubKey(bobPubKey.toHex()),xHash,BigInt(lockTimeMin)
)
await crossChainSwap.connect(signer)// Contract deployment.
const deployTx = await crossChainSwap.deploy(amount)
console.log('CrossChainSwap contract deployed: ', deployTx.id)
第三步:Alice 解锁 Bob 的合约
成功部署 sCrypt 合约后,Alice 现在可以通过泄露秘密 x 来调用 Bob 合约的公共方法 unlock()。 结果,Alice 拥有了 Bob 的 BSV。
const deployedContractTXID = 'TODO'
const x = toByteString('f00cfd8df5f92d5e94d1ecbd9b427afd14e03f8a3292ca4128cd59ef7b9643bc')// Alice unlocks contract and takes the funds.
const provider = new DefaultProvider(bsv.Networks.testnet)
const signer = new TestWallet(alicePrivKey, provider)const tx = await signer.provider.getTransaction(deployedContractTXID)
const crossChainSwap = CrossChainSwap.fromTx(tx, 0)
await crossChainSwap.connect(signer)const { tx: callTx, atInputIndex } =await crossChainSwap.methods.unlock(x,(sigResps) => findSig(sigResps, alicePubKey),{pubKeyOrAddrToSign: alicePubKey,} as MethodCallOptions<CrossChainSwap>)
console.log('CrossChainSwap "unlock" method called: ', callTx.id)
第四步:Bob 取回 Alice 的 BTC
一旦 Alice 透露了 x,Bob 就可以用它来解锁 BTC 区块链上的 P2WSH UTXO。 这个过程允许鲍勃索取爱丽丝的比特币,从而完成原子交换。
def main():# always remember to setup the networksetup('testnet')# TODO: Set values:bobPriv = PrivateKey('TODO')bobPub = bobPriv.get_public_key()alicePub = PublicKey('TODO')txid = 'TODO' # Previous transaction IDvout = 0 # Previous transaction ouput indexamount = 0.00001725 # Amount in outputfee = 0.00000125 # Fee in new transactionx = 'f00cfd8df5f92d5e94d1ecbd9b427afd14e03f8a3292ca4128cd59ef7b9643bc'xHash = '1908c59a71781b7a44182ec39dd84a8a9e13dc31691fead8631730f5f5ab7b65'nBlocksLocked = '06' # 6 blocks ~ 1 hrtoAddress = P2wpkhAddress.from_address('TODO')# HTLC Script:htlc_redeem_script = Script(['OP_IF','OP_SHA256',xHash,'OP_EQUALVERIFY',bobPub.to_hex(),'OP_CHECKSIG','OP_ELSE',nBlocksLocked,'OP_CHECKSEQUENCEVERIFY','OP_DROP',alicePub.to_hex(),'OP_CHECKSIG','OP_ENDIF'])fromAddress = P2wshAddress.from_script(htlc_redeem_script)# Create transaction input from tx id of UTXOtxin = TxInput(txid, vout)txOut1 = TxOutput(to_satoshis(amount - fee), toAddress.to_script_pub_key())tx = Transaction([txin], [txOut1], has_segwit=True)# NOTE: In P2WSH, the argument for OP_IF and OP_NOTIF MUST be exactly an empty vector or 0x01, or the script evaluation fails immediately.# Normal unlock:sig1 = bobPriv.sign_segwit_input(tx, 0, htlc_redeem_script, to_satoshis(amount))tx.witnesses.append(Script([sig1,x,'01', # OP_TRUEhtlc_redeem_script.to_hex()]))# print raw signed transaction ready to be broadcastedprint("\nRaw signed transaction:\n" + tx.serialize())print("\nTxId:", tx.get_txid())
我们可以广播打印的原始交易并完成交换。
争议解决
在发生争议的情况下,Alice 和 Bob 都可以在一段时间后提取资金。
此功能提供了一种故障安全机制,可确保在交换不成功或有争议的情况下不会永久锁定资金。 时间限制为双方解锁各自的合同提供了足够的窗口。
在爱丽丝的例子中,我们可以修改见证人的构造:
# ...# Create transaction input from tx id of UTXO.
txin = TxInput(txid, vout, sequence=bytes.fromhex('FFFFFFFE'))# ...locktime = bytes.fromhex('64A7F990') # 1688730000
tx = Transaction([txin], [txOut1], has_segwit=True, locktime=locktime)# Withdrawal:
sig1 = alicePriv.sign_segwit_input(tx, 0, htlc_redeem_script, to_satoshis(amount))
tx.witnesses.append(Script([sig1,'', # OP_FALSEhtlc_redeem_script.to_hex()]))#...
传递 OP_FALSE 作为第一个输入将在 OP_ELSE 之后执行脚本,这会检查时间锁定是否已过期。
同样,在 Bob 的情况下,我们修改代码以调用 cancel 方法:
// Bob withdraws after timeout passed.
const { tx: callTx, atInputIndex } =await crossChainSwap.methods.cancel((sigResps) => findSig(sigResps, bobPubKey),{lockTime: 1688730000,pubKeyOrAddrToSign: bobPubKey,} as MethodCallOptions<CrossChainSwap>)
console.log('CrossChainSwap "cancel" method called: ', callTx.id)
首次成功跨链BTC-BSV互换
我们在 BSV 和 BTC 主网之间进行了首次成功的原子交换。
-
BTC 上的初始 P2WSH 交易:af7a8c31e489c18d6fe46141cf2cbc777aeb23672679eb199bde4813d6fe41d4
-
BSV 上等效的 sCrypt 智能合约交易:8598d203e8bdd45b7025e334cdebdef06be88381dec245d95108e658e8373f9c
-
Alice 调用
unlock方法:68c2c5a91645112df6b62a5ee6ea9e0e22f29499b88c9ccffc23f8f86ec63d09 -
鲍勃解锁了 BTC:9c697bf8f0d2c11285cfab3a2b8a856a1c18ae048d481c7bb3f93f9ccd2dbaad
这也是一个未完成的交换示例。 爱丽丝和鲍勃都收回了他们的资金。
- BTC: 395dde14e489208302c1d6ac3b4fc0db890c000fd79f3e836fc74043a54480ff
- BSV: 12e701237a1f6da2b69f1d4dab2b1208d3f6003f7b45ef178c5c7d9e00c54273
本文中显示的所有代码都可以在我们的 GitHub 上找到。
相关文章:
Bitcoin SV 和 Bitcoin Core 之间首次跨链原子交换
我们已经执行了 Bitcoin SV 和 Bitcoin Core 之间的首次原子交换。 这一成就代表了比特币 SV 的重大进步,以去信任的方式促进了与其他区块链的无缝互操作性。 图片源自Gemini 在上一篇文章中,我们解释了原子交换的高级理论。 我们深入研究了使用哈希时间…...
RT-DETR改进 | 2023 | InnerEIoU、InnerSIoU、InnerWIoU、InnerDIoU等二十余种损失函数
论文地址:官方Inner-IoU论文地址点击即可跳转 官方代码地址:官方代码地址-官方只放出了两种结合方式CIoU、SIoU 本位改进地址: 文末提供完整代码块-包括InnerEIoU、InnerCIoU、InnerDIoU等七种结合方式和其AlphaIoU变种结合起来可以达到二十…...
JDBC编程基础
JDBC编程基础 JDBC介绍创建JDBC项目的步骤1.引入依赖2.注册驱动3.获取数据库连接4.获取sql执行对象 JDBC 常用 API 详解sql执行对象PreparedStatement作用 事务管理结果集对象 JDBC项目demo测试 JDBC介绍 每个数据库都会提供一组API来支持程序员实现自己客户端,自己…...
Linux shell命令
Linux shell命令 1、Shell简介 Shell 是一个用 C 语言编写的程序,它是用户使用 Linux 的桥梁。Shell 既是一种命令语言,又是一种程序设计语言。 Shell 是指一种应用程序,这个应用程序提供了一个界面,用户通过这个界面访问…...
Vue 3 面试经验分享
🌷🍁 博主猫头虎(🐅🐾)带您 Go to New World✨🍁 🦄 博客首页——🐅🐾猫头虎的博客🎐 🐳 《面试题大全专栏》 🦕 文章图文…...
Vue简易的车牌输入键盘,可以根据需要修改
效果图如下: 代码如下: <template><div><div class"carNoBoxInput"><div style"padding: 6px;border: 2px solid #fff;border-radius: 6px;margin: 6px 3px 6px 6px;"><input class"inputBox"…...
十分钟搭建VScode C/C++运行环境
一、下载配置vscode 1.下载安装VScode 地址:https://code.visualstudio.com/download 下载后,运行安装程序 (VSCodeUserSetup-{version}.exe)。这只需要一分钟。安装程序会将 Visual Studio Code 添加到环境变量中%,可以使用CMD键入“code”…...
控制台gbk乱码
引用IntelliJ IDEA中 统一设置编码为utf-8或GBK-CSDN博客 特别注意file coding 的文件path和java的编码格式 配置...
Springboot日志-logback
logback-spring.xml的配置项 共有一个父标签、两种属性、三个节点: 一个父标签:configuration 两种属性:contextName和property 三个节点:appender、root、logger 日志级别 日志级别从低到高分为TRACE < DEBUG < INFO < WARN &…...
六、Lua 运算符
文章目录 一、Lua 运算符(一)算术运算符(二)关系运算符(三)逻辑运算符(四)其他运算符 二、运算符优先级 一、Lua 运算符 运算符是一个特殊的符号,用于告诉解释器执行特定…...
Android frameworks 开发总结十一
1.修改GMS的setup wizard 1.1 找到需要修改的文件 打开vendor/partner_gms/apps/GmsSampleIntegration/res/values/config.xml文件。以Arashi R为例: <resources><string name="wizard_script_uri" translatable="false">android.resource…...
学嵌入式,已经会用stm32做各种小东西了,下一步是什么
学嵌入式,已经会用stm32做各种小东西了,下一步是什么,研究stm32的内部吗? 针对题主这种类型的,首先我想提出几个技术问题。 1,除了那几个常用的外设,stm32上集成的众多外设是否都有实际的使用经…...
Java面试题10
1.MyBatis 中 #{}和 ${}的区别是什么? #{} 是预编译的占位符,MyBatis会将其转化为一个占位符参数,安全性较高,可以防止 SQL注入; ${} 是字符串替换,直接将内容替换到SQL语句中,不会进行参数处理…...
DBeaver连接MySQL提示“Public Key Retrieval is not allowed“问题解决方式
更新时间:2023年10月31日 11:37:53 作者:产品人小柒 dbeaver数据库连接工具,可以支持几乎所有的主流数据库.mysql,oracle.sqlserver,db2 等等,这篇文章主要给大家介绍了关于DBeaver连接MySQL提示"Public Key Retrieval is not allowed"问…...
振弦式轴力计和振弦采集仪组成的安全监测解决方案
振弦式轴力计和振弦采集仪组成的安全监测解决方案 振弦式轴力计和振弦采集仪是一种常用的结构安全监测工具,可以用于评估建筑物、桥梁、隧道或其他结构的结构健康状态和安全性能。这种监测方案较为先进、精确,并且能够监测长期的结构反应,因此…...
卡尔曼滤波
通过 Eigen 矩阵运算实现线性卡尔曼滤波。模拟的是一辆带火箭发动机的汽车,一开始沿着X轴匀速运动,到X轴中间开启火箭发动机匀加速向Y轴起飞。同理可以仿真(x,y,z,yaw,pitch,raw) 6自由度的真实飞行情况 #include <iostream&g…...
不受平台限制,Sketch 网页版震撼登场
Sketch 是一种基于 Mac 的矢量图形编辑器,可用于数字设计。其主要功能包括无损矢量编辑、完美像素精度和数百个插件同步功能,可导出预设和代码。它是目前流行的页面交互协作设计工具。但是 Sketch 最大的缺点是对 Windows/PC 用户不友好。严格来说&#…...
如何使用.pth训练模型
一.使用.pth训练模型的步骤如下: 1.导入必要的库和模型 import torch import torchvision.models as models# 加载预训练模型 model models.resnet50(pretrainedTrue) 2.定义数据集和数据加载器 # 定义数据集和数据加载器 dataset MyDataset() dataloader to…...
C++11线程以及线程同步
C11中提供的线程类std::thread,基于此类创建一个新的线程相对简单,只需要提供线程函数和线程对象即可 一.命名空间 this_thread C11 添加一个关于线程的命名空间std::this_pthread ,此命名空间中提供四个公共的成员函数; 1.1 get_id() 调用命名空间s…...
深度学习之基于YoloV3杂草识别系统
欢迎大家点赞、收藏、关注、评论啦 ,由于篇幅有限,只展示了部分核心代码。 文章目录 一项目简介 二、功能三、系统四. 总结 一项目简介 深度学习在图像识别领域已经取得了显著的成果,其中基于YOLO(You Only Look Once)…...
TDengine 快速体验(Docker 镜像方式)
简介 TDengine 可以通过安装包、Docker 镜像 及云服务快速体验 TDengine 的功能,本节首先介绍如何通过 Docker 快速体验 TDengine,然后介绍如何在 Docker 环境下体验 TDengine 的写入和查询功能。如果你不熟悉 Docker,请使用 安装包的方式快…...
抖音增长新引擎:品融电商,一站式全案代运营领跑者
抖音增长新引擎:品融电商,一站式全案代运营领跑者 在抖音这个日活超7亿的流量汪洋中,品牌如何破浪前行?自建团队成本高、效果难控;碎片化运营又难成合力——这正是许多企业面临的增长困局。品融电商以「抖音全案代运营…...
【git】把本地更改提交远程新分支feature_g
创建并切换新分支 git checkout -b feature_g 添加并提交更改 git add . git commit -m “实现图片上传功能” 推送到远程 git push -u origin feature_g...
IoT/HCIP实验-3/LiteOS操作系统内核实验(任务、内存、信号量、CMSIS..)
文章目录 概述HelloWorld 工程C/C配置编译器主配置Makefile脚本烧录器主配置运行结果程序调用栈 任务管理实验实验结果osal 系统适配层osal_task_create 其他实验实验源码内存管理实验互斥锁实验信号量实验 CMISIS接口实验还是得JlINKCMSIS 简介LiteOS->CMSIS任务间消息交互…...
ios苹果系统,js 滑动屏幕、锚定无效
现象:window.addEventListener监听touch无效,划不动屏幕,但是代码逻辑都有执行到。 scrollIntoView也无效。 原因:这是因为 iOS 的触摸事件处理机制和 touch-action: none 的设置有关。ios有太多得交互动作,从而会影响…...
现有的 Redis 分布式锁库(如 Redisson)提供了哪些便利?
现有的 Redis 分布式锁库(如 Redisson)相比于开发者自己基于 Redis 命令(如 SETNX, EXPIRE, DEL)手动实现分布式锁,提供了巨大的便利性和健壮性。主要体现在以下几个方面: 原子性保证 (Atomicity)ÿ…...
莫兰迪高级灰总结计划简约商务通用PPT模版
莫兰迪高级灰总结计划简约商务通用PPT模版,莫兰迪调色板清新简约工作汇报PPT模版,莫兰迪时尚风极简设计PPT模版,大学生毕业论文答辩PPT模版,莫兰迪配色总结计划简约商务通用PPT模版,莫兰迪商务汇报PPT模版,…...
uniapp 字符包含的相关方法
在uniapp中,如果你想检查一个字符串是否包含另一个子字符串,你可以使用JavaScript中的includes()方法或者indexOf()方法。这两种方法都可以达到目的,但它们在处理方式和返回值上有所不同。 使用includes()方法 includes()方法用于判断一个字…...
比较数据迁移后MySQL数据库和OceanBase数据仓库中的表
设计一个MySQL数据库和OceanBase数据仓库的表数据比较的详细程序流程,两张表是相同的结构,都有整型主键id字段,需要每次从数据库分批取得2000条数据,用于比较,比较操作的同时可以再取2000条数据,等上一次比较完成之后,开始比较,直到比较完所有的数据。比较操作需要比较…...
Web后端基础(基础知识)
BS架构:Browser/Server,浏览器/服务器架构模式。客户端只需要浏览器,应用程序的逻辑和数据都存储在服务端。 优点:维护方便缺点:体验一般 CS架构:Client/Server,客户端/服务器架构模式。需要单独…...
