def test_htlc_from_opcode(): htlc = HTLC(network="testnet") htlc.from_opcode(opcode="OP_IF OP_HASH256 b9b9a0c47ecee7fd94812573a7b14afa02ec250dbdb5875a5" \ "5c4d02367fcc2ab OP_EQUALVERIFY OP_DUP OP_HASH160 7b7c4431a43b612a7" \ "2f8229935c469f1f6903658 OP_EQUALVERIFY OP_CHECKSIG OP_ELSE OP_5 OP" \ "_CHECKSEQUENCEVERIFY OP_DROP OP_DUP OP_HASH160 6bce65e58a50b979899" \ "30e9a4ff1ac1a77515ef1 OP_EQUALVERIFY OP_CHECKSIG OP_ENDIF") htlc_bytecode = htlc.bytecode() assert htlc_bytecode == "63aa20b9b9a0c47ecee7fd94812573a7b14afa02ec250dbdb5875a55c4d02367" \ "fcc2ab8876a9147b7c4431a43b612a72f8229935c469f1f690365888ac6755b2" \ "7576a9146bce65e58a50b97989930e9a4ff1ac1a77515ef188ac68" htlc_opcode = htlc.opcode() assert htlc_opcode == "OP_IF OP_HASH256 b9b9a0c47ecee7fd94812573a7b14afa02ec250dbdb5875a5" \ "5c4d02367fcc2ab OP_EQUALVERIFY OP_DUP OP_HASH160 7b7c4431a43b612a7" \ "2f8229935c469f1f6903658 OP_EQUALVERIFY OP_CHECKSIG OP_ELSE OP_5 OP" \ "_CHECKSEQUENCEVERIFY OP_DROP OP_DUP OP_HASH160 6bce65e58a50b979899" \ "30e9a4ff1ac1a77515ef1 OP_EQUALVERIFY OP_CHECKSIG OP_ENDIF" htlc_address = htlc.address() assert str(htlc_address) == "2N729UBGZB3xjsGFRgKivy4bSjkaJGMVSpB" htlc_hash = htlc.hash() assert str(htlc_hash) == "a914971894c58d85981c16c2059d422bcde0b156d04487" with pytest.raises(TypeError, match="op_code must be string format"): HTLC(network="mainnet").from_opcode(bool())
def test_htlc_init(): htlc = HTLC(network="testnet") htlc.init(secret_hash=sha256("BooOoom!"), recipient_address="mrmtGq2HMmqAogSsGDjCtXUpxrb7rHThFH", sender_address="mqLyrNDjpENRMZAoDpspH7kR9RtgvhWzYE", sequence=5) htlc_bytecode = htlc.bytecode() assert htlc_bytecode == "63aa20b9b9a0c47ecee7fd94812573a7b14afa02ec250dbdb5875a55c4d02367fcc2" \ "ab8876a9147b7c4431a43b612a72f8229935c469f1f690365888ac6755b27576a914" \ "6bce65e58a50b97989930e9a4ff1ac1a77515ef188ac68" htlc_opcode = htlc.opcode() assert htlc_opcode == "OP_IF OP_HASH256 b9b9a0c47ecee7fd94812573a7b14afa02ec250dbdb5875a5" \ "5c4d02367fcc2ab OP_EQUALVERIFY OP_DUP OP_HASH160 7b7c4431a43b612a7" \ "2f8229935c469f1f6903658 OP_EQUALVERIFY OP_CHECKSIG OP_ELSE OP_5 OP" \ "_CHECKSEQUENCEVERIFY OP_DROP OP_DUP OP_HASH160 6bce65e58a50b979899" \ "30e9a4ff1ac1a77515ef1 OP_EQUALVERIFY OP_CHECKSIG OP_ENDIF" htlc_hash = htlc.hash() assert str(htlc_hash) == "a914971894c58d85981c16c2059d422bcde0b156d04487" htlc_address = htlc.address() assert str(htlc_address) == "2N729UBGZB3xjsGFRgKivy4bSjkaJGMVSpB"
def test_bitcoin_fund_transaction(): htlc = HTLC(network=_["bitcoin"]["network"]).build_htlc( secret_hash=_["bitcoin"]["htlc"]["secret"]["hash"], recipient_address=_["bitcoin"]["wallet"]["recipient"]["address"], sender_address=_["bitcoin"]["wallet"]["sender"]["address"], endtime=_["bitcoin"]["htlc"]["endtime"]) unsigned_fund_transaction = FundTransaction( network=_["bitcoin"]["network"]) unsigned_fund_transaction.build_transaction( address=_["bitcoin"]["wallet"]["sender"]["address"], htlc=htlc, amount=_["bitcoin"]["amount"], unit=_["bitcoin"]["unit"]) assert unsigned_fund_transaction.type( ) == _["bitcoin"]["fund"]["unsigned"]["type"] assert unsigned_fund_transaction.fee( ) == _["bitcoin"]["fund"]["unsigned"]["fee"] assert unsigned_fund_transaction.hash( ) == _["bitcoin"]["fund"]["unsigned"]["hash"] assert unsigned_fund_transaction.raw( ) == _["bitcoin"]["fund"]["unsigned"]["raw"] assert unsigned_fund_transaction.json( ) == _["bitcoin"]["fund"]["unsigned"]["json"] assert unsigned_fund_transaction.transaction_raw( ) == clean_transaction_raw( transaction_raw=_["bitcoin"]["fund"]["unsigned"]["transaction_raw"]) signed_fund_transaction = unsigned_fund_transaction.sign(solver=FundSolver( xprivate_key=_["bitcoin"]["wallet"]["sender"]["root_xprivate_key"], path=_["bitcoin"]["wallet"]["sender"]["derivation"]["path"], account=_["bitcoin"]["wallet"]["sender"]["derivation"]["account"], change=_["bitcoin"]["wallet"]["sender"]["derivation"]["change"], address=_["bitcoin"]["wallet"]["sender"]["derivation"]["address"])) assert signed_fund_transaction.type( ) == _["bitcoin"]["fund"]["signed"]["type"] assert signed_fund_transaction.fee( ) == _["bitcoin"]["fund"]["signed"]["fee"] assert signed_fund_transaction.hash( ) == _["bitcoin"]["fund"]["signed"]["hash"] assert signed_fund_transaction.raw( ) == _["bitcoin"]["fund"]["signed"]["raw"] assert signed_fund_transaction.json( ) == _["bitcoin"]["fund"]["signed"]["json"] assert signed_fund_transaction.transaction_raw() == clean_transaction_raw( transaction_raw=_["bitcoin"]["fund"]["signed"]["transaction_raw"])
def test_bytom_htlc_init_validation(): with pytest.raises(ValueError, match="invalid network, only mainnet or testnet"): HTLC(network="unknown") with pytest.raises(ValueError, match="htlc script is none, initialization htlc first"): HTLC(network="testnet").bytecode() with pytest.raises(ValueError, match="htlc script is none, initialization htlc first"): HTLC(network="testnet").opcode() with pytest.raises(ValueError, match="htlc script is none, initialization htlc first"): HTLC(network="testnet").hash() with pytest.raises(ValueError, match="htlc script is none, initialization htlc first"): HTLC(network="testnet").address() with pytest.raises(TypeError, match="secret hash must be string format"): HTLC(network="mainnet").init(int(), str(), str(), int()) with pytest.raises(ValueError, match="invalid secret hash, length must be 64."): HTLC(network="mainnet").init(str(), str(), str(), int()) with pytest.raises(TypeError, match="recipient address must be string format"): HTLC(network="mainnet").init( "3a26da82ead15a80533a02696656b14b5dbfd84eb14790f2e1be5e9e45820eeb", float(), str(), int()) with pytest.raises(AddressError, match=r"invalid .* recipient .* address"): HTLC(network="mainnet").init( "3a26da82ead15a80533a02696656b14b5dbfd84eb14790f2e1be5e9e45820eeb", "2N729UBGZB3xjsGFRgKivy4bSjkaJGMVSpB", str(), int()) with pytest.raises(TypeError, match="sender address must be string format"): HTLC(network="testnet").init( "3a26da82ead15a80533a02696656b14b5dbfd84eb14790f2e1be5e9e45820eeb", "2N729UBGZB3xjsGFRgKivy4bSjkaJGMVSpB", bool(), int()) with pytest.raises(AddressError, match=r"invalid .* sender .* address"): HTLC(network="mainnet").init( "3a26da82ead15a80533a02696656b14b5dbfd84eb14790f2e1be5e9e45820eeb", "1EzQPm2RFqtY7fGpcjVkXvQ9xzEKhDZmWP", "muTnffLDR5LtFeLR2i3WsKVfdyvzfyPnVB", int()) with pytest.raises(TypeError, match="sequence must be integer format"): HTLC(network="testnet").init( "3a26da82ead15a80533a02696656b14b5dbfd84eb14790f2e1be5e9e45820eeb", "2N729UBGZB3xjsGFRgKivy4bSjkaJGMVSpB", "muTnffLDR5LtFeLR2i3WsKVfdyvzfyPnVB", str())
# Choose network mainnet or testnet NETWORK: str = "testnet" # Secret key hash SECRET_HASH: str = sha256("Hello Meheret!") # Bitcoin recipient address RECIPIENT_ADDRESS: str = "mgokpSJoX7npmAK1Zj8ze1926CLxYDt1iF" # Bitcoin sender address SENDER_ADDRESS: str = "mtvgBj3LTrdD4KxMzHFN4pwCEg1WC6kzQ2" # Expiration contract timestamp ENDTIME: int = get_current_timestamp(plus=3600) # 1 hour print("=" * 10, "Hash Time Lock Contract (HTLC) between Sender and Recipient") # Initialize Bitcoin HTLC htlc: HTLC = HTLC(network=NETWORK) # Build HTLC contract htlc.build_htlc(secret_hash=SECRET_HASH, recipient_address=RECIPIENT_ADDRESS, sender_address=SENDER_ADDRESS, endtime=ENDTIME) # Print all Bitcoin HTLC info's print("HTLC Agreements:", json.dumps(htlc.agreements, indent=4)) print("HTLC Bytecode:", htlc.bytecode()) print("HTLC OP_Code:", htlc.opcode()) print("HTLC Hash:", htlc.hash()) print("HTLC Contract Address:", htlc.contract_address()) print("HTLC Balance:", htlc.balance(unit="BTC"), "BTC") print("HTLC UTXO's:", htlc.utxos())
print("Sender Uncompressed:", sender_uncompressed) sender_address = sender_wallet.address() print("Sender Address:", sender_address) sender_hash = sender_wallet.hash() print("Sender Hash:", sender_hash) sender_p2pkh = sender_wallet.p2pkh() print("Sender P2PKH:", sender_p2pkh) sender_p2sh = sender_wallet.p2sh() print("Sender P2SH:", sender_p2sh) # sender_balance = sender_wallet.balance() # print("Sender Balance:", sender_balance) print("=" * 10, "Hash Time Lock Contract (HTLC) from Bytecode") # Initializing Hash Time Lock Contract (HTLC) htlc = HTLC(network=NETWORK) # Initializing HTLC from bytecode htlc.from_bytecode(bytecode=HTLC_BYTECODE) htlc_bytecode = htlc.bytecode() print("HTLC Bytecode:", htlc_bytecode) htlc_opcode = htlc.opcode() print("HTLC OP_Code:", htlc_opcode) htlc_hash = htlc.hash() print("HTLC Hash:", htlc_hash) htlc_address = htlc.address() print("HTLC Address:", htlc_address) print("=" * 10, "Unsigned Fund Transaction") # Initialization fund transaction
def test_bitcoin_fund_transaction(): unsigned_fund_transaction = FundTransaction(version=2, network=network) unsigned_fund_transaction.build_transaction( wallet=sender_wallet, htlc=HTLC(network=network).init( secret_hash=sha256("Hello Meheret!"), recipient_address=recipient_wallet.address(), sender_address=sender_wallet.address(), sequence=1000), amount=10_000) assert unsigned_fund_transaction.fee() == 678 assert unsigned_fund_transaction.hash( ) == "f05f2afb0706020cc15b66d63e2fd9d89cfe5ce7a9f458f3a8a6fb3c1849cf20" assert unsigned_fund_transaction.raw( ) == "0200000001ec312e92d8387b15f6238d4918344b62ab147d7f3844dc81e653776fe8b84ef30100000000ffffffff02102700000000000017a9142bb013c3e4beb08421dedcf815cb65a5c388178b87508a0e00000000001976a91464a8390b0b1685fcbf2d4b457118dc8da92d553488ac00000000" assert unsigned_fund_transaction.json() == { 'hex': '0200000001ec312e92d8387b15f6238d4918344b62ab147d7f3844dc81e653776fe8b84ef30100000000ffffffff02102700000000000017a9142bb013c3e4beb08421dedcf815cb65a5c388178b87508a0e00000000001976a91464a8390b0b1685fcbf2d4b457118dc8da92d553488ac00000000', 'txid': 'f05f2afb0706020cc15b66d63e2fd9d89cfe5ce7a9f458f3a8a6fb3c1849cf20', 'hash': 'f05f2afb0706020cc15b66d63e2fd9d89cfe5ce7a9f458f3a8a6fb3c1849cf20', 'size': 117, 'vsize': 117, 'version': 2, 'locktime': 0, 'vin': [{ 'txid': 'f34eb8e86f7753e681dc44387f7d14ab624b3418498d23f6157b38d8922e31ec', 'vout': 1, 'scriptSig': { 'asm': '', 'hex': '' }, 'sequence': '4294967295' }], 'vout': [{ 'value': '0.00010000', 'n': 0, 'scriptPubKey': { 'asm': 'OP_HASH160 2bb013c3e4beb08421dedcf815cb65a5c388178b OP_EQUAL', 'hex': 'a9142bb013c3e4beb08421dedcf815cb65a5c388178b87', 'type': 'p2sh', 'address': '2MwEDybGC34949zgzWX4M9FHmE3crDSUydP' } }, { 'value': '0.00952912', 'n': 1, 'scriptPubKey': { 'asm': 'OP_DUP OP_HASH160 64a8390b0b1685fcbf2d4b457118dc8da92d5534 OP_EQUALVERIFY OP_CHECKSIG', 'hex': '76a91464a8390b0b1685fcbf2d4b457118dc8da92d553488ac', 'type': 'p2pkh', 'address': 'mphBPZf15cRFcL5tUq6mCbE84XobZ1vg7Q' } }] } assert unsigned_fund_transaction.type() == "bitcoin_fund_unsigned" assert unsigned_fund_transaction.unsigned_raw( ) == "eyJmZWUiOiA2NzgsICJyYXciOiAiMDIwMDAwMDAwMWVjMzEyZTkyZDgzODdiMTVmNjIzOGQ0OTE4MzQ0YjYyYWIxNDdkN2YzODQ0ZGM4MWU2NTM3NzZmZThiODRlZjMwMTAwMDAwMDAwZmZmZmZmZmYwMjEwMjcwMDAwMDAwMDAwMDAxN2E5MTQyYmIwMTNjM2U0YmViMDg0MjFkZWRjZjgxNWNiNjVhNWMzODgxNzhiODc1MDhhMGUwMDAwMDAwMDAwMTk3NmE5MTQ2NGE4MzkwYjBiMTY4NWZjYmYyZDRiNDU3MTE4ZGM4ZGE5MmQ1NTM0ODhhYzAwMDAwMDAwIiwgIm91dHB1dHMiOiBbeyJhbW91bnQiOiA5NjM1OTAsICJuIjogMSwgInNjcmlwdCI6ICI3NmE5MTQ2NGE4MzkwYjBiMTY4NWZjYmYyZDRiNDU3MTE4ZGM4ZGE5MmQ1NTM0ODhhYyJ9XSwgIm5ldHdvcmsiOiAidGVzdG5ldCIsICJ0eXBlIjogImJpdGNvaW5fZnVuZF91bnNpZ25lZCJ9" signed_fund_transaction = unsigned_fund_transaction.sign(solver=FundSolver( private_key=sender_wallet.private_key())) assert signed_fund_transaction.fee() == 678 assert signed_fund_transaction.hash( ) == "7e52333d38b7571807caac7971c925dd2c007dbf34a6c46138ff3d0213281d60" assert signed_fund_transaction.raw( ) == "0200000001ec312e92d8387b15f6238d4918344b62ab147d7f3844dc81e653776fe8b84ef3010000006b483045022100b4d4de4c10bec380a9f07019d5232a9af9f0c2321e5efcf33f5326a60378144502203e1ab2ddaac8afade132832e715f055f956d3e730b9d035a4e99ec9dfdc7acfd012103c56a6005d4a8892d28cc3f7265e5685b548627d59108973e474c4e26f69a4c84ffffffff02102700000000000017a9142bb013c3e4beb08421dedcf815cb65a5c388178b87508a0e00000000001976a91464a8390b0b1685fcbf2d4b457118dc8da92d553488ac00000000" assert signed_fund_transaction.json() == { 'hex': '0200000001ec312e92d8387b15f6238d4918344b62ab147d7f3844dc81e653776fe8b84ef3010000006b483045022100b4d4de4c10bec380a9f07019d5232a9af9f0c2321e5efcf33f5326a60378144502203e1ab2ddaac8afade132832e715f055f956d3e730b9d035a4e99ec9dfdc7acfd012103c56a6005d4a8892d28cc3f7265e5685b548627d59108973e474c4e26f69a4c84ffffffff02102700000000000017a9142bb013c3e4beb08421dedcf815cb65a5c388178b87508a0e00000000001976a91464a8390b0b1685fcbf2d4b457118dc8da92d553488ac00000000', 'txid': '7e52333d38b7571807caac7971c925dd2c007dbf34a6c46138ff3d0213281d60', 'hash': '7e52333d38b7571807caac7971c925dd2c007dbf34a6c46138ff3d0213281d60', 'size': 224, 'vsize': 224, 'version': 2, 'locktime': 0, 'vin': [{ 'txid': 'f34eb8e86f7753e681dc44387f7d14ab624b3418498d23f6157b38d8922e31ec', 'vout': 1, 'scriptSig': { 'asm': '3045022100b4d4de4c10bec380a9f07019d5232a9af9f0c2321e5efcf33f5326a60378144502203e1ab2ddaac8afade132832e715f055f956d3e730b9d035a4e99ec9dfdc7acfd01 03c56a6005d4a8892d28cc3f7265e5685b548627d59108973e474c4e26f69a4c84', 'hex': '483045022100b4d4de4c10bec380a9f07019d5232a9af9f0c2321e5efcf33f5326a60378144502203e1ab2ddaac8afade132832e715f055f956d3e730b9d035a4e99ec9dfdc7acfd012103c56a6005d4a8892d28cc3f7265e5685b548627d59108973e474c4e26f69a4c84' }, 'sequence': '4294967295' }], 'vout': [{ 'value': '0.00010000', 'n': 0, 'scriptPubKey': { 'asm': 'OP_HASH160 2bb013c3e4beb08421dedcf815cb65a5c388178b OP_EQUAL', 'hex': 'a9142bb013c3e4beb08421dedcf815cb65a5c388178b87', 'type': 'p2sh', 'address': '2MwEDybGC34949zgzWX4M9FHmE3crDSUydP' } }, { 'value': '0.00952912', 'n': 1, 'scriptPubKey': { 'asm': 'OP_DUP OP_HASH160 64a8390b0b1685fcbf2d4b457118dc8da92d5534 OP_EQUALVERIFY OP_CHECKSIG', 'hex': '76a91464a8390b0b1685fcbf2d4b457118dc8da92d553488ac', 'type': 'p2pkh', 'address': 'mphBPZf15cRFcL5tUq6mCbE84XobZ1vg7Q' } }] } assert signed_fund_transaction.type() == "bitcoin_fund_signed"
def test_bitcoin_htlc(): htlc = HTLC(network=_["bitcoin"]["network"]).build_htlc( secret_hash=_["bitcoin"]["htlc"]["secret"]["hash"], recipient_address=_["bitcoin"]["wallet"]["recipient"]["address"], sender_address=_["bitcoin"]["wallet"]["sender"]["address"], sequence=_["bitcoin"]["htlc"]["sequence"]) assert htlc.bytecode() == _["bitcoin"]["htlc"]["bytecode"] assert htlc.opcode() == _["bitcoin"]["htlc"]["opcode"] assert htlc.hash() == _["bitcoin"]["htlc"]["hash"] assert htlc.address() == _["bitcoin"]["htlc"]["address"] htlc = HTLC(network=_["bitcoin"]["network"]).from_bytecode( bytecode=_["bitcoin"]["htlc"]["bytecode"]) assert htlc.bytecode() == _["bitcoin"]["htlc"]["bytecode"] assert htlc.opcode() == _["bitcoin"]["htlc"]["opcode"] assert htlc.hash() == _["bitcoin"]["htlc"]["hash"] assert htlc.address() == _["bitcoin"]["htlc"]["address"] htlc = HTLC(network=_["bitcoin"]["network"]).from_opcode( opcode=_["bitcoin"]["htlc"]["opcode"]) assert htlc.bytecode() == _["bitcoin"]["htlc"]["bytecode"] assert htlc.opcode() == _["bitcoin"]["htlc"]["opcode"] assert htlc.hash() == _["bitcoin"]["htlc"]["hash"] assert htlc.address() == _["bitcoin"]["htlc"]["address"]
# Getting recipient wallet information's recipient_address = recipient_wallet.address() print("Recipient Address:", recipient_address) recipient_hash = recipient_wallet.hash() print("Recipient Hash:", recipient_hash) recipient_p2pkh = recipient_wallet.p2pkh() print("Recipient P2PKH:", recipient_p2pkh) recipient_p2sh = recipient_wallet.p2sh() print("Recipient P2SH:", recipient_p2sh) recipient_balance = recipient_wallet.balance() print("Recipient Balance:", recipient_balance) print("=" * 10, "Hash Time Lock Contract (HTLC) between Sender and Recipient") # Initializing Hash Time Lock Contract (HTLC) htlc = HTLC(network=NETWORK) # Building new HTLC contract htlc.init( secret_hash=SECRET_HASH, recipient_address=recipient_address, sender_address=sender_address, sequence=SEQUENCE, ) htlc_bytecode = htlc.bytecode() print("HTLC Bytecode:", htlc_bytecode) htlc_opcode = htlc.opcode() print("HTLC OP_Code:", htlc_opcode) htlc_hash = htlc.hash() print("HTLC Hash:", htlc_hash) htlc_address = htlc.address()
def test_bitcoin_htlc(): htlc = HTLC(network=_["bitcoin"]["network"]).build_htlc( secret_hash=_["bitcoin"]["htlc"]["secret"]["hash"], recipient_address=_["bitcoin"]["wallet"]["recipient"]["address"], sender_address=_["bitcoin"]["wallet"]["sender"]["address"], endtime=_["bitcoin"]["htlc"]["endtime"]) assert htlc.bytecode() == _["bitcoin"]["htlc"]["bytecode"] assert htlc.opcode() == _["bitcoin"]["htlc"]["opcode"] assert htlc.hash() == _["bitcoin"]["htlc"]["hash"] assert htlc.contract_address() == _["bitcoin"]["htlc"]["contract_address"] assert htlc.agreements["secret_hash"] == _["bitcoin"]["htlc"][ "agreements"]["secret_hash"] assert htlc.agreements["recipient_address"] == _["bitcoin"]["htlc"][ "agreements"]["recipient_address"] assert htlc.agreements["sender_address"] == _["bitcoin"]["htlc"][ "agreements"]["sender_address"] # assert htlc.agreements["endtime"]["datetime"] == _["bitcoin"]["htlc"]["agreements"]["endtime"]["datetime"] assert htlc.agreements["endtime"]["timestamp"] == _["bitcoin"]["htlc"][ "agreements"]["endtime"]["timestamp"] htlc = HTLC(network=_["bitcoin"]["network"]).from_bytecode( bytecode=_["bitcoin"]["htlc"]["bytecode"]) assert htlc.bytecode() == _["bitcoin"]["htlc"]["bytecode"] assert htlc.opcode() == _["bitcoin"]["htlc"]["opcode"] assert htlc.hash() == _["bitcoin"]["htlc"]["hash"] assert htlc.contract_address() == _["bitcoin"]["htlc"]["contract_address"] htlc = HTLC(network=_["bitcoin"]["network"]).from_opcode( opcode=_["bitcoin"]["htlc"]["opcode"]) assert htlc.bytecode() == _["bitcoin"]["htlc"]["bytecode"] assert htlc.opcode() == _["bitcoin"]["htlc"]["opcode"] assert htlc.hash() == _["bitcoin"]["htlc"]["hash"] assert htlc.contract_address() == _["bitcoin"]["htlc"]["contract_address"]