Rename to commitment

This commit is contained in:
Jay Graber 2017-07-26 13:23:12 -07:00
parent 2b7d00b73e
commit 941ef40390
8 changed files with 230 additions and 129 deletions

View File

@ -47,15 +47,15 @@ def get_keys(funder_address, redeemer_address):
def privkey(address):
bitcoind.dumpprivkey(address)
def hashtimelockcontract(funder, redeemer, secret, locktime):
def hashtimelockcontract(funder, redeemer, commitment, locktime):
funderAddr = CBitcoinAddress(funder)
redeemerAddr = CBitcoinAddress(redeemer)
h = sha256(secret)
# h = sha256(secret)
blocknum = bitcoind.getblockcount()
print("Current blocknum", blocknum)
redeemblocknum = blocknum + locktime
print("REDEEMBLOCKNUM BITCOIN", redeemblocknum)
redeemScript = CScript([OP_IF, OP_SHA256, h, OP_EQUALVERIFY,OP_DUP, OP_HASH160,
redeemScript = CScript([OP_IF, OP_SHA256, x(commitment), OP_EQUALVERIFY,OP_DUP, OP_HASH160,
redeemerAddr, OP_ELSE, redeemblocknum, OP_CHECKLOCKTIMEVERIFY, OP_DROP, OP_DUP, OP_HASH160,
funderAddr, OP_ENDIF,OP_EQUALVERIFY, OP_CHECKSIG])
print("Redeem script for p2sh contract on Bitcoin blockchain:", b2x(redeemScript))
@ -108,6 +108,11 @@ def get_tx_details(txid):
# redeems automatically after buyer has funded tx, by scanning for transaction to the p2sh
# i.e., doesn't require buyer telling us fund txid
def auto_redeem(contract, secret):
print("Parsing script for auto_redeem...")
scriptarray = parse_script(contract.redeemScript)
redeemblocknum = scriptarray[8]
redeemPubkey = scriptarray[6]
refundPubkey = scriptarray[13]
# How to find redeemScript and redeemblocknum from blockchain?
print("Contract in auto redeem", contract.__dict__)
p2sh = contract.p2sh
@ -124,11 +129,11 @@ def auto_redeem(contract, secret):
print("Found {0} in p2sh {1}, redeeming...".format(amount, p2sh))
# Parsing redeemblocknum from the redeemscript of the p2sh
redeemblocknum = find_redeemblocknum(contract)
# redeemblocknum = find_redeemblocknum(contract)
blockcount = bitcoind.getblockcount()
print("\nCurrent blocknum at time of redeem on Bitcoin:", blockcount)
if blockcount < redeemblocknum:
redeemPubKey = find_redeemAddr(contract)
# redeemPubKey = find_redeemAddr(contract)
print('redeemPubKey', redeemPubKey)
else:
print("nLocktime exceeded, refunding")
@ -169,7 +174,68 @@ def auto_redeem(contract, secret):
else:
print("No contract for this p2sh found in database", p2sh)
def redeem_contract(contract, secret):
# How to find redeemScript and redeemblocknum from blockchain?
print("Contract in redeem_contract", contract.__dict__)
p2sh = contract.p2sh
#checking there are funds in the address
amount = check_funds(p2sh)
if(amount == 0):
print("address ", p2sh, " not funded")
quit()
fundtx = find_transaction_to_address(p2sh)
amount = fundtx['amount'] / COIN
print("Found fundtx:", fundtx)
p2sh = P2SHBitcoinAddress(p2sh)
if fundtx['address'] == p2sh:
print("Found {0} in p2sh {1}, redeeming...".format(amount, p2sh))
# TODO: Decodescript is not working, add back in.
# redeemblocknum = find_redeemblocknum(contract)
blockcount = bitcoind.getblockcount()
print("\nCurrent blocknum at time of redeem on Zcash:", blockcount)
if blockcount < contract.redeemblocknum:
# redeemPubKey = find_redeemAddr(contract)
redeemPubKey = P2PKHBitcoinAddress.from_bytes(x('7788b4511a25fba1092e67b307a6dcdb6da125d9'))
print('redeemPubKey', redeemPubKey)
zec_redeemScript = CScript(x(contract.redeemScript))
txin = CMutableTxIn(fundtx['outpoint'])
txout = CMutableTxOut(fundtx['amount'] - FEE, redeemPubKey.to_scriptPubKey())
# Create the unsigned raw transaction.
tx = CMutableTransaction([txin], [txout])
sighash = SignatureHash(zec_redeemScript, tx, 0, SIGHASH_ALL)
# TODO: figure out how to better protect privkey
privkey = bitcoind.dumpprivkey(redeemPubKey)
sig = privkey.sign(sighash) + bytes([SIGHASH_ALL])
print("SECRET", secret)
preimage = b(secret)
txin.scriptSig = CScript([sig, privkey.pub, preimage, OP_TRUE, zec_redeemScript])
print("txin.scriptSig", b2x(txin.scriptSig))
txin_scriptPubKey = zec_redeemScript.to_p2sh_scriptPubKey()
print('Redeem txhex', b2x(tx.serialize()))
VerifyScript(txin.scriptSig, txin_scriptPubKey, tx, 0, (SCRIPT_VERIFY_P2SH,))
print("script verified, sending raw tx")
txid = bitcoind.sendrawtransaction(tx)
print("Txid of submitted redeem tx: ", b2x(lx(b2x(txid))))
print("TXID SUCCESSFULLY REDEEMED")
return 'redeem_tx', b2x(lx(b2x(txid)))
else:
print("nLocktime exceeded, refunding")
refundPubKey = find_refundAddr(contract)
print('refundPubKey', refundPubKey)
txid = bitcoind.sendtoaddress(refundPubKey, fundtx['amount'] - FEE)
print("Txid of refund tx:", b2x(lx(b2x(txid))))
print("TXID SUCCESSFULLY REFUNDED")
return 'refund_tx', b2x(lx(b2x(txid)))
else:
print("No contract for this p2sh found in database", p2sh)
# takes hex and returns array of decoded script op codes
# This seems to be a costly operation, minimize frequency of calls.
def parse_script(script_hex):
redeemScript = zcashd.decodescript(script_hex)
scriptarray = redeemScript['asm'].split(' ')
@ -216,9 +282,6 @@ def find_transaction_to_address(p2sh):
bitcoind.importaddress(p2sh, "", False)
txs = bitcoind.listunspent()
for tx in txs:
# print("tx addr:", tx['address'])
# print(type(tx['address']))
# print(type(p2sh))
if tx['address'] == CBitcoinAddress(p2sh):
print("Found tx to p2sh", p2sh)
print(tx)

72
cli.py
View File

@ -6,34 +6,44 @@ from trades import *
from xcat import *
import ast
def find_role(contract):
# Obviously when regtest created both addrs on same machine, role is both.
if parse_addrs(contract.initiator):
return 'initiator'
else:
return 'fulfiller'
def save_state(trade):
save(trade)
db.create
def parse_addrs(address):
if address[:1] == 'm':
status = bXcat.validateaddress(address)
else:
status = zXcat.validateaddress(address)
status = status['ismine']
print("Address {0} is mine: {1}".format(address, status))
return status
def checkSellActions(trade):
def checkSellStatus(trade):
if trade.buy.get_status() == 'funded':
seller_redeem(trade)
secret = get_secret()
print("SECRET found in checksellactions", secret)
trade = seller_redeem_p2sh(trade, secret)
print("TRADE SUCCESSFULLY REDEEMED", trade)
save_state(trade)
elif trade.buy.get_status() == 'empty':
print("Buyer has not yet funded the contract where you offered to buy {0}, please wait for them to complete their part.".format(trade.buy.currency))
elif trade.buy.get_status() == 'redeemed':
print("You have already redeemed the p2sh on the second chain of this trade.")
def checkBuyActions(trade):
def checkBuyStatus(trade):
if trade.sell.get_status() == 'funded' and trade.buy.get_status() != 'redeemed':
print("One active trade available, fulfilling buyer contract...")
buyer_fulfill(trade)
# they should calculate redeemScript for themselves
htlc = create_htlc(trade.buy.currency, trade.buy.fulfiller, trade.buy.initiator, trade.commitment, trade.buy.locktime)
print("Buyer p2sh:", htlc['p2sh'])
# If the two p2sh match...
if buyer_p2sh == contract.buy.p2sh:
fund_tx = fund_contract(trade.buy)
trade.buy.fund_tx = fund_tx
print("trade buy with redeemscript?", trade.buy.__dict__)
save_state(trade)
else:
print("Compiled p2sh for htlc does not match what seller sent.")
elif trade.buy.get_status() == 'redeemed':
buyer_redeem(trade)
# TODO: secret parsing
# secret = parse_secret(trade.buy.currency, trade.buy.redeem_tx)
secret = get_secret()
print("Found secret", secret)
txid = auto_redeem_p2sh(trade.sell, secret)
print("TXID after buyer redeem", txid)
print("XCAT trade complete!")
def instantiateTrade(trade):
@ -61,7 +71,7 @@ if __name__ == '__main__':
hexstr = args.argument[0]
trade = x2s(hexstr)
trade = instantiateTrade(ast.literal_eval(trade))
db.create(trade)
save_state(trade)
# print(trade.toJ)
elif command == 'exporttrade':
trade = get_trade()
@ -73,10 +83,10 @@ if __name__ == '__main__':
trade = instantiateTrade(trade)
if find_role(trade.sell) == 'initiator':
role = 'seller'
checkSellActions(trade)
checkSellStatus(trade)
else:
role = 'buyer'
checkBuyActions(trade)
checkBuyStatus(trade)
elif command == 'newtrade':
erase_trade()
role = 'seller'
@ -92,3 +102,19 @@ if __name__ == '__main__':
txid = args.argument[0]
trade = db.get(txid)
print(x2s(b2x(trade)))
# Ad hoc testing starts here
elif command == "step1":
erase_trade()
print("Creating new XCAT trade...")
trade = seller_initiate(Trade())
# Save it to leveldb
save_state(trade)
elif command == "step2":
trade = get_trade()
checkBuyStatus(trade)
elif command == "step3":
trade = get_trade()
checkSellStatus(trade)
elif command == "step4":
trade = get_trade()
checkBuyStatus(trade)

View File

@ -8,9 +8,9 @@ db = plyvel.DB('/tmp/testdb', create_if_missing=True)
trade = get_trade()
## txid we retrieve by
if trade and 'sell' in trade:
if 'fund_tx' in trade['sell']:
txid = trade['sell']['fund_tx']
if trade and trade.sell:
if hasattr(trade.sell, 'fund_tx'):
txid = trade.sell.fund_tx
# Takes object, saves json as bytes
def create(trade):

View File

@ -1 +1 @@
UYH0XxCs
2E8ASX0w

View File

@ -1,10 +1,11 @@
import json
class Trade(object):
def __init__(self, sell=None, buy=None):
def __init__(self, sell=None, buy=None, commitment=None):
'''Create a new trade with a sell contract and buy contract across two chains'''
self.sell = sell
self.buy = buy
self.commitment = commitment
def toJSON(self):
return json.dumps(self, default=lambda o: o.__dict__,

View File

@ -1 +0,0 @@
{"buy": {"fulfiller": "tmTjZSg4pX2Us6V5HttiwFZwj464fD2ZgpY", "initiator": "tmFRXyju7ANM7A9mg75ZjyhFW1UJEhUPwfQ", "p2sh": "t2TcYheueGfEnT2SKYMLWNXKfyzrMLKc6y2", "redeemblocknum": 113817, "currency": "zcash", "amount": 1.2, "redeemScript": "63a820b67f875a86ea6be94a1f6e44857daa739df84421ba2402dd968185b7d58371b68876a9143ea29256c9d2888ca23de42a8b8e69ca2ec235b1670399bc01b17576a914c5acca6ef39c843c7a9c3ad01b2da95fe2edf5ba6888ac"}, "sell": {"fulfiller": "mrQzUGU1dwsWRx5gsKKSDPNtrsP65vCA3Z", "initiator": "myfFr5twPYNwgeXyjCmGcrzXtCmfmWXKYp", "fund_tx": "1171aeda64eff388b3568fa4675d0ca78852911109bbe42e0ef11ad6bf1b159e", "p2sh": "2NEy1foaQU3wkMu7yygW1GZYhikeSxq6ZCq", "redeemblocknum": 911, "currency": "bitcoin", "amount": 3.5, "redeemScript": "63a820b67f875a86ea6be94a1f6e44857daa739df84421ba2402dd968185b7d58371b68876a9147788b4511a25fba1092e67b307a6dcdb6da125d967028f03b17576a914c7043e62a7391596116f54f6a64c8548e97d3fd96888ac"}}

126
xcat.py
View File

@ -17,11 +17,11 @@ def check_p2sh(currency, address):
print("Checking funds in Zcash p2sh")
return zXcat.check_funds(address)
def create_htlc(currency, funder, redeemer, secret, locktime):
def create_htlc(currency, funder, redeemer, commitment, locktime):
if currency == 'bitcoin':
sell_p2sh = bXcat.hashtimelockcontract(funder, redeemer, secret, locktime)
sell_p2sh = bXcat.hashtimelockcontract(funder, redeemer, commitment, locktime)
else:
sell_p2sh = zXcat.hashtimelockcontract(funder, redeemer, secret, locktime)
sell_p2sh = zXcat.hashtimelockcontract(funder, redeemer, commitment, locktime)
return sell_p2sh
def fund_htlc(currency, p2sh, amount):
@ -30,12 +30,16 @@ def fund_htlc(currency, p2sh, amount):
else:
txid = zXcat.fund_htlc(p2sh, amount)
return txid
#
# def fund_buy_contract(trade):
# buy = trade.buy
# txid = fund_htlc(buy.currency, buy.p2sh, buy.amount)
# setattr(trade.buy, 'fund_tx', txid)
# save(trade)
# return txid
def fund_buy_contract(trade):
buy = trade.buy
txid = fund_htlc(buy.currency, buy.p2sh, buy.amount)
setattr(trade.buy, 'fund_tx', txid)
save(trade)
def fund_contract(contract):
txid = fund_htlc(contract.currency, contract.p2sh, contract.amount)
return txid
def fund_sell_contract(trade):
@ -45,22 +49,22 @@ def fund_sell_contract(trade):
save(trade)
return txid
def create_sell_p2sh(trade, secret, locktime):
def create_sell_p2sh(trade, commitment, locktime):
# CREATE SELL CONTRACT
sell = trade.sell
contract = create_htlc(sell.currency, sell.initiator, sell.fulfiller, secret, locktime)
contract = create_htlc(sell.currency, sell.initiator, sell.fulfiller, commitment, locktime)
print("sell contract", contract)
setattr(trade.sell, 'p2sh', contract['p2sh'])
setattr(trade.sell, 'redeemScript', contract['redeemScript'])
setattr(trade.sell, 'redeemblocknum', contract['redeemblocknum'])
save(trade)
def create_buy_p2sh(trade, secret, locktime):
def create_buy_p2sh(trade, commitment, locktime):
## CREATE BUY CONTRACT
buy = trade.buy
print("Now creating buy contract on the {0} blockchain where you will wait for the buyer to send funds...".format(buy.currency))
print("HTLC DETAILS", buy.currency, buy.fulfiller, buy.initiator, secret, locktime)
buy_contract = create_htlc(buy.currency, buy.fulfiller, buy.initiator, secret, locktime)
print("HTLC DETAILS", buy.currency, buy.fulfiller, buy.initiator, commitment, locktime)
buy_contract = create_htlc(buy.currency, buy.fulfiller, buy.initiator, commitment, locktime)
print("Buy contract", buy_contract)
setattr(trade.buy, 'p2sh', buy_contract['p2sh'])
@ -70,7 +74,7 @@ def create_buy_p2sh(trade, secret, locktime):
save(trade)
def redeem_p2sh(contract, secret):
def auto_redeem_p2sh(contract, secret):
currency = contract.currency
if currency == 'bitcoin':
res = bXcat.auto_redeem(contract, secret)
@ -78,10 +82,20 @@ def redeem_p2sh(contract, secret):
res = zXcat.auto_redeem(contract, secret)
return res
def print_trade(role):
print("\nTrade status for {0}:".format(role))
trade = get_trade()
pprint(trade)
def redeem_p2sh(contract, secret):
currency = contract.currency
if currency == 'bitcoin':
res = bXcat.redeem_contract(contract, secret)
else:
res = zXcat.redeem_contract(contract, secret)
return res
def parse_secret(chain, txid):
if chain == 'bitcoin':
secret = bXcat.parse_secret(txid)
else:
secret = zXcat.parse_secret(txid)
#### Main functions determining user flow from command line
def buyer_redeem(trade):
@ -104,7 +118,7 @@ def buyer_redeem(trade):
save(trade)
exit()
def seller_redeem(trade):
def seller_redeem_p2sh(trade, secret):
buy = trade.buy
userInput.authorize_seller_redeem(buy)
@ -113,12 +127,11 @@ def seller_redeem(trade):
exit()
else:
# Seller redeems buyer's funded tx (contract in p2sh)
secret = userInput.retrieve_password()
tx_type, txid = redeem_p2sh(trade.buy, secret)
print("Setting tx_type: txid", tx_type, txid)
setattr(trade.buy, tx_type, txid)
save(trade)
print("You have redeemed {0} {1}!".format(buy.amount, buy.currency))
print_trade('seller')
return trade
def buyer_fulfill(trade):
buy = trade.buy
@ -157,11 +170,13 @@ def seller_initiate(trade):
print(trade.buy.__dict__)
secret = userInput.create_password()
save_secret(secret)
hash_of_secret = sha256(secret)
# TODO: Implement locktimes and mock block passage of time
sell_locktime = 5
buy_locktime = 10 # Must be more than first tx
print("Creating pay-to-script-hash for sell contract...")
create_sell_p2sh(trade, secret, sell_locktime)
create_sell_p2sh(trade, hash_of_secret, sell_locktime)
userInput.authorize_fund_sell(trade)
@ -170,68 +185,5 @@ def seller_initiate(trade):
create_buy_p2sh(trade, secret, buy_locktime)
trade.commitment = b2x(hash_of_secret)
return trade
if __name__ == '__main__':
print("ZEC <-> BTC XCAT (Cross-Chain Atomic Transactions)")
print("=" * 50)
trade = get_trade()
if trade == None:
htlcTrade = Trade()
print("New empty trade")
else:
buy = Contract(trade['buy'])
sell = Contract(trade['sell'])
htlcTrade = Trade(buy=buy, sell=sell)
try:
if sys.argv[1] == 'new':
erase_trade()
role = 'seller'
htlcTrade = Trade()
print("Creating new XCAT transaction...")
else:
role = sys.argv[1]
print("Your role in demo:", role)
except:
if trade == None:
print("No active trades available.")
res = input("Would you like to initiate a trade? (y/n) ")
if res == 'y':
role = 'seller'
else:
exit()
else:
print("Trade exists, run script as buyer or seller to complete trade.")
exit()
if htlcTrade.buy is not None and htlcTrade.sell is not None:
if htlcTrade.sell.get_status() == 'redeemed' and htlcTrade.buy.get_status() == 'redeemed':
print("This trade is already complete! Trade details:")
pprint(trade)
exit()
if role == "seller":
if htlcTrade.sell == None:
seller_initiate(htlcTrade)
elif htlcTrade.buy.get_status() == 'funded':
seller_redeem(htlcTrade)
elif htlcTrade.buy.get_status() == 'empty':
print("Buyer has not yet funded the contract where you offered to buy {0}, please wait for them to complete their part.".format(htlcTrade.buy.currency))
else:
# Need better way of preventing buyer from having secret
# if 'status' not in trade['buy'] and trade['sell']['status'] == 'funded':
if htlcTrade.sell.get_status() == 'funded' and htlcTrade.buy.get_status() != 'redeemed':
print("One active trade available, fulfilling buyer contract...")
buyer_fulfill(htlcTrade)
# How to monitor if txs are included in blocks -- should use blocknotify and a monitor daemon?
# p2sh = trade['buy']['p2sh']
# check_blocks(p2sh)
elif htlcTrade.buy.get_status() == 'redeemed':
# Seller has redeemed buyer's tx, buyer can now redeem.
buyer_redeem(htlcTrade)
print("XCAT trade complete!")
# Note: there is some little endian weirdness in the bXcat and zXcat files, need to handle the endianness of txids better & more consistently

View File

@ -36,16 +36,16 @@ def get_keys(funder_address, redeemer_address):
def privkey(address):
zcashd.dumpprivkey(address)
def hashtimelockcontract(funder, redeemer, secret, locktime):
def hashtimelockcontract(funder, redeemer, commitment, locktime):
funderAddr = CBitcoinAddress(funder)
redeemerAddr = CBitcoinAddress(redeemer)
h = sha256(secret)
# h = sha256(secret)
blocknum = zcashd.getblockcount()
print("Current blocknum", blocknum)
redeemblocknum = blocknum + locktime
print("REDEEMBLOCKNUM ZCASH", redeemblocknum)
# can rm op_dup and op_hash160 if you replace addrs with pubkeys (as raw hex/bin data?), and can rm last op_equalverify (for direct pubkey comparison)
zec_redeemScript = CScript([OP_IF, OP_SHA256, h, OP_EQUALVERIFY,OP_DUP, OP_HASH160,
zec_redeemScript = CScript([OP_IF, OP_SHA256, x(commitment), OP_EQUALVERIFY,OP_DUP, OP_HASH160,
redeemerAddr, OP_ELSE, redeemblocknum, OP_CHECKLOCKTIMEVERIFY, OP_DROP, OP_DUP, OP_HASH160,
funderAddr, OP_ENDIF,OP_EQUALVERIFY, OP_CHECKSIG])
print("Redeem script for p2sh contract on Zcash blockchain:", b2x(zec_redeemScript))
@ -77,7 +77,7 @@ def get_tx_details(txid):
def find_transaction_to_address(p2sh):
zcashd.importaddress(p2sh, "", False)
txs = zcashd.listunspent()
txs = zcashd.listunspent(0, 100)
for tx in txs:
# print("tx addr:", tx['address'])
# print(type(tx['address']))
@ -128,7 +128,6 @@ def parse_secret(txid):
# redeems automatically after buyer has funded tx, by scanning for transaction to the p2sh
# i.e., doesn't require buyer telling us fund txid
def auto_redeem(contract, secret):
# How to find redeemScript and redeemblocknum from blockchain?
print("Contract in auto redeem", contract.__dict__)
@ -187,13 +186,74 @@ def auto_redeem(contract, secret):
else:
print("No contract for this p2sh found in database", p2sh)
def redeem_contract(contract, secret):
# How to find redeemScript and redeemblocknum from blockchain?
print("Contract in redeem contract", contract.__dict__)
p2sh = contract.p2sh
#checking there are funds in the address
amount = check_funds(p2sh)
if(amount == 0):
print("address ", p2sh, " not funded")
quit()
fundtx = find_transaction_to_address(p2sh)
amount = fundtx['amount'] / COIN
print("Found fundtx:", fundtx)
p2sh = P2SHBitcoinAddress(p2sh)
if fundtx['address'] == p2sh:
print("Found {0} in p2sh {1}, redeeming...".format(amount, p2sh))
# Where can you find redeemblocknum in the transaction?
# redeemblocknum = find_redeemblocknum(contract)
blockcount = zcashd.getblockcount()
print("\nCurrent blocknum at time of redeem on Zcash:", blockcount)
if blockcount < contract.d:
# TODO: parse the script once, up front.
redeemPubKey = find_redeemAddr(contract)
print('redeemPubKey', redeemPubKey)
zec_redeemScript = CScript(x(contract.redeemScript))
txin = CMutableTxIn(fundtx['outpoint'])
txout = CMutableTxOut(fundtx['amount'] - FEE, redeemPubKey.to_scriptPubKey())
# Create the unsigned raw transaction.
tx = CMutableTransaction([txin], [txout])
sighash = SignatureHash(zec_redeemScript, tx, 0, SIGHASH_ALL)
# TODO: figure out how to better protect privkey
privkey = zcashd.dumpprivkey(redeemPubKey)
sig = privkey.sign(sighash) + bytes([SIGHASH_ALL])
print("SECRET", secret)
preimage = secret.encode('utf-8')
txin.scriptSig = CScript([sig, privkey.pub, preimage, OP_TRUE, zec_redeemScript])
print("txin.scriptSig", b2x(txin.scriptSig))
txin_scriptPubKey = zec_redeemScript.to_p2sh_scriptPubKey()
print('Redeem txhex', b2x(tx.serialize()))
VerifyScript(txin.scriptSig, txin_scriptPubKey, tx, 0, (SCRIPT_VERIFY_P2SH,))
print("script verified, sending raw tx")
txid = zcashd.sendrawtransaction(tx)
print("Txid of submitted redeem tx: ", b2x(lx(b2x(txid))))
print("TXID SUCCESSFULLY REDEEMED")
return 'redeem_tx', b2x(lx(b2x(txid)))
else:
print("nLocktime exceeded, refunding")
refundPubKey = find_refundAddr(contract)
print('refundPubKey', refundPubKey)
txid = zcashd.sendtoaddress(refundPubKey, fundtx['amount'] - FEE)
print("Txid of refund tx:", b2x(lx(b2x(txid))))
print("TXID SUCCESSFULLY REFUNDED")
return 'refund_tx', b2x(lx(b2x(txid)))
else:
print("No contract for this p2sh found in database", p2sh)
def parse_script(script_hex):
redeemScript = zcashd.decodescript(script_hex)
scriptarray = redeemScript['asm'].split(' ')
return scriptarray
def find_redeemblocknum(contract):
print("In find_redeemblocknum")
scriptarray = parse_script(contract.redeemScript)
print("Returning scriptarray", scriptarray)
redeemblocknum = scriptarray[8]
return int(redeemblocknum)