diff --git a/blockstack/lib/operations/announce.py b/blockstack/lib/operations/announce.py
index 0c509b703..cea580c6c 100644
--- a/blockstack/lib/operations/announce.py
+++ b/blockstack/lib/operations/announce.py
@@ -21,20 +21,24 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, make_op_return_tx, make_op_return_outputs, \
- make_op_return_script, broadcast_transaction, serialize_transaction, \
- script_hex_to_address, get_unspents
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import make_op_return_script, \
+ calculate_change_amount, make_pay_to_address_script
+
+from keylib import ECPrivateKey, ECPublicKey
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import *
+from ..blockchain import get_tx_inputs
# consensus hash fields (none for announcements)
FIELDS = []
-def build(message_hash, testset=False):
+def build(message_hash):
"""
Record format:
@@ -53,7 +57,7 @@ def build(message_hash, testset=False):
readable_script = "ANNOUNCE 0x%s" % (message_hash)
hex_script = blockstack_script_to_hex(readable_script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
@@ -89,6 +93,40 @@ def make_outputs( data, inputs, change_address, pay_fee=True ):
]
+def state_transition(blockchain_name, message_hash, private_key, user_public_key=None):
+
+ # sanity check
+ pay_fee = True
+ if user_public_key is not None:
+ pay_fee = False
+
+ if user_public_key is None and private_key is None:
+ raise Exception("Missing both public and private key")
+
+ if len(message_hash) != 40:
+ raise Exception("Invalid message hash: not 20 bytes")
+
+ if not is_hex( message_hash ):
+ raise Exception("Invalid message hash: not hex")
+
+ pubk = None
+
+ if user_public_key is not None:
+ # subsidizing
+ pubk = ECPublicKey( user_public_key )
+
+ else:
+ # ordering directly
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ inputs = get_tx_inputs( blockchain_name, from_address )
+
+ nulldata = build(message_hash)
+ outputs = make_outputs( nulldata, inputs, from_address, pay_fee=pay_fee )
+ return inputs, outputs
+
+
def broadcast(message_hash, private_key, blockchain_client, testset=False, blockchain_broadcaster=None, user_public_key=None, tx_only=False):
# sanity check
@@ -112,35 +150,30 @@ def broadcast(message_hash, private_key, blockchain_client, testset=False, block
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
- from_address = None
- inputs = None
- private_key_obj = None
-
+ pubk = None
+
if user_public_key is not None:
# subsidizing
- pubk = BitcoinPublicKey( user_public_key )
+ pubk = ECPublicKey( user_public_key )
- from_address = pubk.address()
- inputs = get_unspents( from_address, blockchain_client )
+ else:
+ # ordering directly
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
- elif private_key is not None:
- # ordering directly
- pubk = BitcoinPrivateKey( private_key ).public_key()
- public_key = pubk.to_hex()
-
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
-
nulldata = build(message_hash, testset=testset)
outputs = make_outputs( nulldata, inputs, from_address, pay_fee=pay_fee )
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {'unsigned_tx': unsigned_tx}
else:
- signed_tx = tx_serialize_and_sign( inputs, outputs, private_key_obj )
+ signed_tx = tx_serialize_sign( inputs, outputs, private_key )
response = broadcast_transaction( signed_tx, blockchain_broadcaster )
response.update({'data': nulldata})
return response
diff --git a/blockstack/lib/operations/nameimport.py b/blockstack/lib/operations/nameimport.py
index 6fbd2c41f..4b14019ca 100644
--- a/blockstack/lib/operations/nameimport.py
+++ b/blockstack/lib/operations/nameimport.py
@@ -21,11 +21,13 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, \
- analyze_private_key, serialize_sign_and_broadcast, make_op_return_script, \
- make_pay_to_address_script, b58check_encode, b58check_decode, serialize_transaction
-
-from pybitcoin.transactions.outputs import calculate_change_amount
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import make_op_return_script, \
+ calculate_change_amount, make_pay_to_address_script
+
+from keylib import b58check_encode
+
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
@@ -33,8 +35,8 @@ from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import *
from ..hashing import hash256_trunc128
-
-from ..nameset import NAMEREC_FIELDS
+from ..blockchain import get_tx_inputs
+from ..nameset import NAMEREC_FIELDS, get_namespace_from_name
# consensus hash fields (ORDER MATTERS!)
FIELDS = NAMEREC_FIELDS + [
@@ -59,7 +61,8 @@ def get_import_update_hash_from_outputs( outputs, recipient ):
ret = None
count = 0
for output in outputs:
-
+
+ """
output_script = output['scriptPubKey']
output_asm = output_script.get('asm')
output_hex = output_script.get('hex')
@@ -69,6 +72,13 @@ def get_import_update_hash_from_outputs( outputs, recipient ):
ret = hexlify( b58check_decode( str(output_addresses[0]) ) )
break
+ """
+ if output.type() != "data":
+ continue
+
+ if output.sender_id() != recipient:
+ ret = hexlify(b58check_decode( output.addresses()[0] ))
+ break
if ret is None:
raise Exception("No update hash found")
@@ -76,7 +86,7 @@ def get_import_update_hash_from_outputs( outputs, recipient ):
return ret
-def build(name, testset=False):
+def build(name):
"""
Takes in a name to import. Name must include the namespace ID.
@@ -96,7 +106,7 @@ def build(name, testset=False):
readable_script = "NAME_IMPORT 0x%s" % (hexlify(name))
hex_script = blockstack_script_to_hex(readable_script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
@@ -133,30 +143,46 @@ def make_outputs( data, inputs, recipient_address, sender_address, update_hash_b
]
+def state_transition(name, recipient_address, update_hash, private_key):
+
+ blockchain_name = namespace_to_blockchain( get_namespace_from_name( name ) )
+
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_tx_inputs( blockchain_name, from_address )
+
+ # NAME_IMPORT outputs
+ nulldata = build(name)
+ update_hash_b58 = b58check_encode( unhexlify(update_hash) )
+ outputs = make_outputs(nulldata, inputs, recipient_address, from_address, update_hash_b58, format='hex')
+
+ return inputs, outputs
+
+
def broadcast(name, recipient_address, update_hash, private_key, blockchain_client, blockchain_broadcaster=None, tx_only=False, testset=False):
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
- nulldata = build(name, testset=testset)
-
- # convert update_hash from a hex string so it looks like an address
- update_hash_b58 = b58check_encode( unhexlify(update_hash) )
-
- # get inputs and from address
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
-
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
# NAME_IMPORT outputs
+ nulldata = build(name, testset=testset)
+ update_hash_b58 = b58check_encode( unhexlify(update_hash) )
outputs = make_outputs(nulldata, inputs, recipient_address, from_address, update_hash_b58, format='hex')
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {"unsigned_tx": unsigned_tx}
else:
# serialize, sign, and broadcast the tx
- response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
+ signed_tx = tx_serialize_sign( inputs, outputs, private_key )
+ response = broadcast_transaction( signed_tx, blockchain_broadcaster )
+ # response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
# response = {'success': True }
response.update({'data': nulldata})
diff --git a/blockstack/lib/operations/namespacepreorder.py b/blockstack/lib/operations/namespacepreorder.py
index ff9ec7805..a6143a111 100644
--- a/blockstack/lib/operations/namespacepreorder.py
+++ b/blockstack/lib/operations/namespacepreorder.py
@@ -21,11 +21,12 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, serialize_transaction, \
- analyze_private_key, serialize_sign_and_broadcast, make_op_return_script, \
- make_pay_to_address_script, b58check_encode, b58check_decode, BlockchainInfoClient, hex_hash160
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key, serialize_sign_and_broadcast
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import make_op_return_script, \
+ calculate_change_amount, make_pay_to_address_script
-from pybitcoin.transactions.outputs import calculate_change_amount
+from keylib import ECPrivateKey
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
@@ -34,6 +35,7 @@ from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import *
from ..hashing import hash_name
+from ..blockchain import get_tx_inputs
# consensus hash fields (ORDER MATTERS!)
FIELDS = [
@@ -117,11 +119,40 @@ def make_outputs( data, inputs, change_addr, fee, pay_fee=True, format='bin' ):
"value": calculate_change_amount(inputs, bill, dust_fee)},
# burn address
- {"script_hex": make_pay_to_address_script(BLOCKSTORE_BURN_ADDRESS),
+ {"script_hex": make_pay_to_address_script(BLOCKSTACK_BURN_ADDRESS),
"value": op_fee}
]
+def state_transition( namespace_id, register_addr, consensus_hash, private_key, fee ):
+ """
+ Propagate a namespace.
+
+ Arguments:
+ namespace_id human-readable (i.e. base-40) name of the namespace
+ register_addr the addr of the key that will reveal the namespace (mixed into the preorder to prevent name preimage attack races)
+ private_key the Bitcoin address that created this namespace, and can populate it.
+ """
+
+ blockchain_name = virtualchain.namespace_to_blocokchain( namespace_id )
+
+ pk = ECPrivateKey( private_key )
+ pubk = pk.public_key()
+ from_address = pubk.address()
+ pubkey_hex = pubk.to_hex()
+
+ inputs = get_tx_outputs( blockchain_name, from_address )
+
+ # build custom outputs here
+ pubkey_hex = pk.public_key().to_hex()
+ script_pubkey = get_script_pubkey( pubkey_hex )
+
+ nulldata = build( namespace_id, script_pubkey, register_addr, consensus_hash )
+ outputs = make_outputs(nulldata, inputs, from_address, fee, format='hex')
+
+ return inputs, outputs
+
+
def broadcast( namespace_id, register_addr, consensus_hash, private_key, blockchain_client, fee, pay_fee=True, tx_only=False, testset=False, blockchain_broadcaster=None ):
"""
Propagate a namespace.
@@ -134,26 +165,28 @@ def broadcast( namespace_id, register_addr, consensus_hash, private_key, blockch
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
-
- pubkey_hex = BitcoinPrivateKey( private_key ).public_key().to_hex()
-
+
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
+ # build custom outputs here
+
+ pubkey_hex = ECPrivateKey( private_key ).public_key().to_hex()
script_pubkey = get_script_pubkey( pubkey_hex )
nulldata = build( namespace_id, script_pubkey, register_addr, consensus_hash, testset=testset )
-
- # get inputs and from address
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
-
- # build custom outputs here
outputs = make_outputs(nulldata, inputs, from_address, fee, format='hex')
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {"unsigned_tx": unsigned_tx}
else:
# serialize, sign, and broadcast the tx
- response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
+ signed_tx = tx_serialize_sign( inputs, outputs, private_key )
+ response = broadcast_transaction( signed_tx, blockchain_broadcaster )
+ # response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
# response = {'success': True }
response.update({'data': nulldata})
diff --git a/blockstack/lib/operations/namespaceready.py b/blockstack/lib/operations/namespaceready.py
index f4dd3b204..bdf92ff0f 100644
--- a/blockstack/lib/operations/namespaceready.py
+++ b/blockstack/lib/operations/namespaceready.py
@@ -21,15 +21,19 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, BlockchainInfoClient, hex_hash160, make_op_return_tx, serialize_transaction, broadcast_transaction, make_op_return_outputs
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import make_op_return_script, \
+ calculate_change_amount, make_pay_to_address_script
+
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import *
+from ..blockchain import get_tx_inputs
-import virtualchain
log = virtualchain.get_logger("blockstack-server")
from namespacereveal import FIELDS as NAMESPACE_REVEAL_FIELDS
@@ -66,6 +70,20 @@ def build( namespace_id, testset=False ):
return packaged_script
+def state_transition( namespace_id, private_key ):
+
+ blockchain_name = namespace_to_blockchain( namespace_id )
+ nulldata = build( namespace_id )
+
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_tx_inputs( blockchain_name, from_address )
+
+ # OP_RETURN outputs
+ outputs = make_op_return_outputs( nulldata, inputs, from_address, fee=DEFAULT_OP_RETURN_FEE, format='hex' )
+ return inputs, outputs
+
+
def broadcast( namespace_id, private_key, blockchain_client, testset=False, tx_only=False, blockchain_broadcaster=None ):
if blockchain_broadcaster is None:
@@ -73,15 +91,16 @@ def broadcast( namespace_id, private_key, blockchain_client, testset=False, tx_o
nulldata = build( namespace_id, testset=testset )
- # get inputs and from address
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
# OP_RETURN outputs
outputs = make_op_return_outputs( nulldata, inputs, from_address, fee=DEFAULT_OP_RETURN_FEE, format='hex' )
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {'unsigned_tx': signed_tx}
else:
diff --git a/blockstack/lib/operations/namespacereveal.py b/blockstack/lib/operations/namespacereveal.py
index fbb6e7452..42fcf0de3 100644
--- a/blockstack/lib/operations/namespacereveal.py
+++ b/blockstack/lib/operations/namespacereveal.py
@@ -21,11 +21,10 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, serialize_transaction, \
- analyze_private_key, serialize_sign_and_broadcast, make_op_return_script, \
- make_pay_to_address_script, b58check_encode, b58check_decode, BlockchainInfoClient, hex_hash160
-
-from pybitcoin.transactions.outputs import calculate_change_amount
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import make_op_return_script, \
+ calculate_change_amount, make_pay_to_address_script
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
@@ -36,8 +35,8 @@ from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import blockstack_script_to_hex, add_magic_bytes
from ..hashing import hash_name
+from ..blockchain import get_tx_inputs
-import virtualchain
log = virtualchain.get_logger("blockstack-log")
# consensus hash fields (ORDER MATTERS!)
@@ -145,7 +144,7 @@ def namespacereveal_sanity_check( namespace_id, version, lifetime, coeff, base,
# version: 2 bytes
# namespace ID: up to 19 bytes
-def build( namespace_id, version, reveal_addr, lifetime, coeff, base, bucket_exponents, nonalpha_discount, no_vowel_discount, testset=False ):
+def build( namespace_id, version, reveal_addr, lifetime, coeff, base, bucket_exponents, nonalpha_discount, no_vowel_discount ):
"""
Record to mark the beginning of a namespace import in the blockchain.
This reveals the namespace ID, and encodes the preorder's namespace rules.
@@ -196,12 +195,12 @@ def build( namespace_id, version, reveal_addr, lifetime, coeff, base, bucket_exp
readable_script = "NAMESPACE_REVEAL 0x%s 0x%s 0x%s 0x%s 0x%s 0x%s 0x%s" % (life_hex, coeff_hex, base_hex, bucket_hex, discount_hex, version_hex, namespace_id_hex)
hex_script = blockstack_script_to_hex(readable_script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
-def make_outputs( data, inputs, reveal_addr, change_addr, format='bin', testset=False ):
+def make_outputs( data, inputs, reveal_addr, change_addr, format='bin' ):
"""
Make outputs for a register:
[0] OP_RETURN with the name
@@ -227,6 +226,33 @@ def make_outputs( data, inputs, reveal_addr, change_addr, format='bin', testset=
+def state_transition( namespace_id, reveal_addr, lifetime, coeff, base_cost, bucket_exponents, nonalpha_discount, no_vowel_discount, private_key ):
+ """
+ Propagate a namespace.
+
+ Arguments:
+ namespace_id human-readable (i.e. base-40) name of the namespace
+ reveal_addr address to own this namespace until it is ready
+ lifetime: the number of blocks for which names will be valid (pass a negative value for "infinite")
+ coeff: cost multipler
+ base_cost: the base cost (i.e. cost of a 1-character name), in satoshis
+ bucket_exponents: bucket cost exponents to which to raise the base cost
+ nonalpha_discount: discount multipler for non-alpha-character names
+ no_vowel_discount: discount multipler for no-vowel names
+ """
+
+ blockchain_name = virtualchain.namespace_to_blockchain(namespace_id)
+ nulldata = build( namespace_id, BLOCKSTACK_VERSION, reveal_addr, lifetime, coeff, base_cost, bucket_exponents, nonalpha_discount, no_vowel_discount )
+
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_tx_inputs( blockchain_name, from_address )
+
+ # build custom outputs here
+ outputs = make_outputs(nulldata, inputs, reveal_addr, from_address, format='hex')
+ return inputs, outputs
+
+
def broadcast( namespace_id, reveal_addr, lifetime, coeff, base_cost, bucket_exponents, nonalpha_discount, no_vowel_discount, private_key, blockchain_client, tx_only=False, blockchain_broadcaster=None, testset=False ):
"""
Propagate a namespace.
@@ -247,19 +273,22 @@ def broadcast( namespace_id, reveal_addr, lifetime, coeff, base_cost, bucket_exp
nulldata = build( namespace_id, BLOCKSTACK_VERSION, reveal_addr, lifetime, coeff, base_cost, bucket_exponents, nonalpha_discount, no_vowel_discount, testset=testset )
- # get inputs and from address
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
-
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
# build custom outputs here
outputs = make_outputs(nulldata, inputs, reveal_addr, from_address, format='hex')
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {"unsigned_tx": unsigned_tx}
else:
# serialize, sign, and broadcast the tx
- response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
+ signed_tx = tx_serialize_sign( inputs, outputs, private_key )
+ response = broadcast_transaction( signed_tx, blockchain_broadcaster )
+ # response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
# response = {'success': True }
response.update({'data': nulldata})
diff --git a/blockstack/lib/operations/preorder.py b/blockstack/lib/operations/preorder.py
index 0032519bd..1d6c928a3 100644
--- a/blockstack/lib/operations/preorder.py
+++ b/blockstack/lib/operations/preorder.py
@@ -21,14 +21,12 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, serialize_transaction, \
- analyze_private_key, serialize_sign_and_broadcast, make_op_return_script, \
- make_pay_to_address_script, b58check_encode, b58check_decode, BlockchainInfoClient, \
- hex_hash160, bin_hash160, BitcoinPrivateKey, BitcoinPublicKey, script_hex_to_address, get_unspents, \
- make_op_return_outputs
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key, serialize_sign_and_broadcast
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import tx_serialize, script_hex_to_address, make_op_return_script, \
+ calculate_change_amount, make_pay_to_address_script
-
-from pybitcoin.transactions.outputs import calculate_change_amount
+from keylib import ECPrivateKey, ECPublicKey
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
@@ -36,6 +34,8 @@ from ..b40 import b40_to_hex, is_b40
from ..config import *
from ..scripts import *
from ..hashing import hash_name
+from ..blockchain import get_tx_inputs
+from ..nameset import get_namespace_from_name
# consensus hash fields (ORDER MATTERS!)
FIELDS = [
@@ -52,7 +52,7 @@ FIELDS = [
'op_fee', # blockstack fee (sent to burn address)
]
-def build(name, script_pubkey, register_addr, consensus_hash, name_hash=None, testset=False):
+def build(name, script_pubkey, register_addr, consensus_hash, name_hash=None):
"""
Takes a name, including the namespace ID (but not the id: scheme), a script_publickey to prove ownership
of the subsequent NAME_REGISTER operation, and the current consensus hash for this block (to prove that the
@@ -82,7 +82,7 @@ def build(name, script_pubkey, register_addr, consensus_hash, name_hash=None, te
script = 'NAME_PREORDER 0x%s 0x%s' % (name_hash, consensus_hash)
hex_script = blockstack_script_to_hex(script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
@@ -111,11 +111,46 @@ def make_outputs( data, inputs, sender_addr, fee, format='bin' ):
"value": calculate_change_amount(inputs, bill, dust_fee)},
# burn address
- {"script_hex": make_pay_to_address_script(BLOCKSTORE_BURN_ADDRESS),
+ {"script_hex": make_pay_to_address_script(BLOCKSTACK_BURN_ADDRESS),
"value": op_fee}
]
+def state_transition(name, private_key, register_addr, consensus_hash, fee, subsidy_public_key=None):
+ """
+ Builds and broadcasts a preorder transaction.
+
+ @subsidy_public_key: if given, the public part of the subsidy key
+ """
+
+ namespace_id = get_namespace_from_name( name )
+ blockchain_name = namespace_to_blockchain( namespace_id )
+
+ # sanity check
+ if subsidy_public_key is None and private_key is None:
+ raise Exception("Missing both client public and private key")
+
+ pubk = None
+ script_pubkey = None # to be mixed into preorder hash
+
+ if subsidy_public_key is not None:
+ # subsidizing
+ pubk = ECPublicKey( subsidy_public_key )
+ script_pubkey = get_script_pubkey( subsidy_public_key )
+
+ else:
+ # ordering directly
+ pubk = ECPrivateKey( private_key ).public_key()
+ script_pubkey = get_script_pubkey( public_key )
+
+ from_address = pubk.address()
+ inputs = get_tx_inputs( blockchain_name, from_address )
+
+ nulldata = build( name, script_pubkey, register_addr, consensus_hash, testset=testset)
+ outputs = make_outputs(nulldata, inputs, from_address, fee, format='hex')
+ return inputs, outputs
+
+
def broadcast(name, private_key, register_addr, consensus_hash, blockchain_client, fee, blockchain_broadcaster=None, subsidy_public_key=None, tx_only=False, testset=False):
"""
Builds and broadcasts a preorder transaction.
@@ -134,40 +169,35 @@ def broadcast(name, private_key, register_addr, consensus_hash, blockchain_clien
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
- from_address = None # change address
- inputs = None
- private_key_obj = None
+ pubk = None
script_pubkey = None # to be mixed into preorder hash
if subsidy_public_key is not None:
# subsidizing
- pubk = BitcoinPublicKey( subsidy_public_key )
-
- from_address = BitcoinPublicKey( subsidy_public_key ).address()
-
- inputs = get_unspents( from_address, blockchain_client )
+ pubk = ECPublicKey( subsidy_public_key )
script_pubkey = get_script_pubkey( subsidy_public_key )
else:
# ordering directly
- pubk = BitcoinPrivateKey( private_key ).public_key()
- public_key = pubk.to_hex()
+ pubk = ECPrivateKey( private_key ).public_key()
script_pubkey = get_script_pubkey( public_key )
-
- # get inputs and from address using private key
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
-
+
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
nulldata = build( name, script_pubkey, register_addr, consensus_hash, testset=testset)
outputs = make_outputs(nulldata, inputs, from_address, fee, format='hex')
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {"unsigned_tx": unsigned_tx}
else:
# serialize, sign, and broadcast the tx
- response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
+ signed_tx = tx_serialize_sign( inputs, outputs, private_key )
+ response = broadcast_transaction( inputs, outputs, blockchain_broadcaster )
+ # response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
response.update({'data': nulldata})
return response
@@ -225,7 +255,7 @@ def get_fees( inputs, outputs ):
log.error("outputs[2] has no decipherable burn address")
return (None, None)
- if addr_hash != BLOCKSTORE_BURN_ADDRESS:
+ if addr_hash != BLOCKSTACK_BURN_ADDRESS:
log.error("outputs[2] is not the burn address")
return (None, None)
diff --git a/blockstack/lib/operations/register.py b/blockstack/lib/operations/register.py
index 906ab93b1..1073aa790 100644
--- a/blockstack/lib/operations/register.py
+++ b/blockstack/lib/operations/register.py
@@ -21,12 +21,12 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, serialize_transaction, \
- analyze_private_key, serialize_sign_and_broadcast, make_op_return_script, \
- make_pay_to_address_script, b58check_encode, b58check_decode, BlockchainInfoClient, hex_hash160, \
- BitcoinPrivateKey, get_unspents, script_hex_to_address
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import tx_serialize, script_hex_to_address, make_op_return_script, \
+ calculate_change_amount, make_pay_to_address_script
-from pybitcoin.transactions.outputs import calculate_change_amount
+from keylib import ECPrivateKey, ECPublicKey
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
@@ -34,9 +34,9 @@ from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import *
from ..hashing import hash256_trunc128
-from ..nameset import NAMEREC_FIELDS
+from ..nameset import NAMEREC_FIELDS, get_namespace_from_name
+from ..blockchain import get_tx_inputs
-import virtualchain
log = virtualchain.get_logger("blockstack-server")
# consensus hash fields (ORDER MATTERS!)
@@ -61,6 +61,7 @@ def get_registration_recipient_from_outputs( outputs ):
ret = None
for output in outputs:
+ """
output_script = output['scriptPubKey']
output_asm = output_script.get('asm')
output_hex = output_script.get('hex')
@@ -72,6 +73,12 @@ def get_registration_recipient_from_outputs( outputs ):
# ret = (output_hex, output_addresses[0])
ret = output_hex
break
+ """
+ if output.type() != "data":
+ continue
+
+ ret = output.sender_id()
+ break
if ret is None:
raise Exception("No registration address found")
@@ -79,7 +86,7 @@ def get_registration_recipient_from_outputs( outputs ):
return ret
-def build(name, testset=False):
+def build(name):
"""
Takes in the name that was preordered, including the namespace ID (but not the id: scheme)
Returns a hex string representing up to LENGTHS['blockchain_id_name'] bytes.
@@ -97,7 +104,7 @@ def build(name, testset=False):
readable_script = "NAME_REGISTRATION 0x%s" % (hexlify(name))
hex_script = blockstack_script_to_hex(readable_script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
@@ -168,12 +175,46 @@ def make_outputs( data, change_inputs, register_addr, change_addr, renewal_fee=N
outputs.append(
# burn address (when renewing)
- {"script_hex": make_pay_to_address_script(BLOCKSTORE_BURN_ADDRESS),
+ {"script_hex": make_pay_to_address_script(BLOCKSTACK_BURN_ADDRESS),
"value": op_fee}
)
return outputs
+
+def state_transition(name, private_key, register_addr, renewal_fee=None, user_public_key=None, subsidy_public_key=None):
+
+ namespace_id = get_namespace_from_name( name )
+ blockchain_name = namespace_to_blockchain( namespace_id )
+
+ if subsidy_public_key is None and private_key is None:
+ raise Exception("Missing both public and private key")
+
+ subsidized_renewal = False
+
+ if subsidy_public_key is not None:
+ # subsidizing
+
+ if user_public_key is not None and renewal_fee is not None:
+ # renewing, and subsidizing the renewal
+ pubk = ECPublicKey( user_public_key )
+ subsidized_renewal = True
+
+ else:
+ # registering or renewing under the subsidy key
+ pubk = ECPublicKey( subsidy_public_key )
+
+ elif private_key is not None:
+ # ordering directly
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ unspents = get_tx_inputs( blockchain_name, from_address )
+
+ nulldata = build(name)
+ outputs = make_outputs(nulldata, change_inputs, register_addr, from_address, renewal_fee=renewal_fee, pay_fee=(not subsidized_renewal), format='hex')
+ return inputs, outputs
+
def broadcast(name, private_key, register_addr, blockchain_client, renewal_fee=None, blockchain_broadcaster=None, tx_only=False, user_public_key=None, subsidy_public_key=None, testset=False):
@@ -190,47 +231,42 @@ def broadcast(name, private_key, register_addr, blockchain_client, renewal_fee=N
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
-
- from_address = None
- change_inputs = None
- private_key_obj = None
+
subsidized_renewal = False
if subsidy_public_key is not None:
# subsidizing
- pubk = BitcoinPublicKey( subsidy_public_key )
if user_public_key is not None and renewal_fee is not None:
# renewing, and subsidizing the renewal
- from_address = BitcoinPublicKey( user_public_key ).address()
+ pubk = ECPublicKey( user_public_key )
subsidized_renewal = True
else:
# registering or renewing under the subsidy key
- from_address = pubk.address()
-
- change_inputs = get_unspents( from_address, blockchain_client )
+ pubk = ECPublicKey( subsidy_public_key )
elif private_key is not None:
# ordering directly
- pubk = BitcoinPrivateKey( private_key ).public_key()
- public_key = pubk.to_hex()
-
- # get inputs and from address using private key
- private_key_obj, from_address, change_inputs = analyze_private_key(private_key, blockchain_client)
-
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ unspents = get_unspents( from_ddress, blockchain_client )
+
nulldata = build(name, testset=testset)
outputs = make_outputs(nulldata, change_inputs, register_addr, from_address, renewal_fee=renewal_fee, pay_fee=(not subsidized_renewal), format='hex')
if tx_only:
- unsigned_tx = serialize_transaction( change_inputs, outputs )
+ unsigned_tx = tx_serialize( change_inputs, outputs )
return {"unsigned_tx": unsigned_tx}
else:
# serialize, sign, and broadcast the tx
- response = serialize_sign_and_broadcast(change_inputs, outputs, private_key_obj, blockchain_broadcaster)
+ signed_tx = tx_serialize_sign( change_inputs, outputs, private_key )
+ response = broadcast_transaction( signed_tx, blockchain_broadcaster )
+ # response = serialize_sign_and_broadcast(change_inputs, outputs, private_key_obj, blockchain_broadcaster)
response.update({'data': nulldata})
return response
@@ -295,7 +331,7 @@ def get_fees( inputs, outputs ):
if addr_hash is None:
return (None, None)
- if addr_hash != BLOCKSTORE_BURN_PUBKEY_HASH:
+ if addr_hash != BLOCKSTACK_BURN_PUBKEY_HASH:
return (None, None)
dust_fee = (len(inputs) + 3) * DEFAULT_DUST_FEE + DEFAULT_OP_RETURN_FEE
diff --git a/blockstack/lib/operations/revoke.py b/blockstack/lib/operations/revoke.py
index 2312c93d8..270d69008 100644
--- a/blockstack/lib/operations/revoke.py
+++ b/blockstack/lib/operations/revoke.py
@@ -21,23 +21,25 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, make_op_return_tx, make_op_return_outputs, \
- make_op_return_script, broadcast_transaction, serialize_transaction, \
- script_hex_to_address, get_unspents
+# from blockstack_utxo import get_unspents, broadcast_transaction, analyze_private_key
+import virtualchain
+from virtualchain.lib.blockchain.bitcoin import tx_serialize, script_hex_to_address, make_op_return_script
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
+from keylib import ECPublicKey, ECPrivateKey
from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import *
-from ..nameset import NAMEREC_FIELDS
+from ..blockchain import get_tx_inputs
+from ..nameset import NAMEREC_FIELDS, get_namespace_from_name
# consensus hash fields (ORDER MATTERS!)
FIELDS = NAMEREC_FIELDS
-def build(name, testset=False):
+def build(name):
"""
Takes in the name, including the namespace ID (but not the id: scheme)
Returns a hex string representing up to LENGTHS['blockchain_id_name'] bytes.
@@ -55,7 +57,7 @@ def build(name, testset=False):
readable_script = "NAME_REVOKE 0x%s" % (hexlify(name))
hex_script = blockstack_script_to_hex(readable_script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
@@ -91,8 +93,40 @@ def make_outputs( data, inputs, change_address, pay_fee=True ):
]
-def broadcast(name, private_key, blockchain_client, testset=False, blockchain_broadcaster=None, user_public_key=None, tx_only=False):
+def state_transition(name, private_key, user_public_key=None):
+ namespace_id = get_namespace_from_name( name )
+ blockchain_name = namespace_to_blockchain( namespace_id )
+
+ # sanity check
+ pay_fee = True
+ if user_public_key is not None:
+ pay_fee = False
+
+ pubk = None
+ if user_public_key is not None:
+ # subsidizing
+ pubk = ECPublicKey( user_public_key )
+
+ else:
+ # ordering directly
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
+ nulldata = build(name, testset=testset)
+ outputs = make_outputs( nulldata, inputs, from_address, pay_fee=pay_fee )
+
+ return inputs, outputs
+
+
+
+def broadcast(name, private_key, user_public_key=None):
+
+ namespace_id = get_namespace_from_name( name )
+ blockchain_name = namespace_to_blockchain( namespace_id )
+
# sanity check
pay_fee = True
if user_public_key is not None:
@@ -108,30 +142,25 @@ def broadcast(name, private_key, blockchain_client, testset=False, blockchain_br
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
- from_address = None
- inputs = None
- private_key_obj = None
-
+
+ pubk = None
if user_public_key is not None:
# subsidizing
- pubk = BitcoinPublicKey( user_public_key )
+ pubk = ECPublicKey( user_public_key )
- from_address = pubk.address()
- inputs = get_unspents( from_address, blockchain_client )
-
- elif private_key is not None:
+ else:
# ordering directly
- pubk = BitcoinPrivateKey( private_key ).public_key()
- public_key = pubk.to_hex()
+ pubk = ECPrivateKey( private_key ).public_key()
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
-
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
nulldata = build(name, testset=testset)
outputs = make_outputs( nulldata, inputs, from_address, pay_fee=pay_fee )
-
+
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {'unsigned_tx': unsigned_tx}
else:
diff --git a/blockstack/lib/operations/transfer.py b/blockstack/lib/operations/transfer.py
index 786d0b61d..0c9aef146 100644
--- a/blockstack/lib/operations/transfer.py
+++ b/blockstack/lib/operations/transfer.py
@@ -21,20 +21,24 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, serialize_transaction, \
- analyze_private_key, serialize_sign_and_broadcast, make_op_return_script, \
- make_pay_to_address_script, BitcoinPrivateKey, BitcoinPublicKey, get_unspents, script_hex_to_address
-
-from pybitcoin.transactions.outputs import calculate_change_amount
+from keylib import ECPrivateKey, ECPublicKey
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
+from blockstack_utxo import analyze_private_key, get_unspents, broadcast_transaction
+
+import virtualchain.lib.blockchain.bitcoin as virtualchain_bitcoin
+from virtualchain_bitcoin import make_pay_to_address_script, \
+ make_op_return_script, script_hex_to_address, calculate_change_amount, \
+ calculate_change_amount, tx_serialize
+
from ..b40 import b40_to_hex, bin_to_b40, is_b40
from ..config import *
from ..scripts import *
from ..hashing import hash256_trunc128
-from ..nameset import NAMEREC_FIELDS
+from ..nameset import NAMEREC_FIELDS, get_namespace_from_name
+from ..blockchain import get_tx_inputs
# consensus hash fields (ORDER MATTERS!)
FIELDS = NAMEREC_FIELDS + [
@@ -56,7 +60,8 @@ def get_transfer_recipient_from_outputs( outputs ):
ret = None
for output in outputs:
-
+
+ """
output_script = output['scriptPubKey']
output_asm = output_script.get('asm')
output_hex = output_script.get('hex')
@@ -66,6 +71,12 @@ def get_transfer_recipient_from_outputs( outputs ):
ret = output_hex
break
+ """
+ if output.type() != "data":
+ break
+
+ ret = output.sender_id()
+ break
if ret is None:
raise Exception("No recipients found")
@@ -90,7 +101,7 @@ def transfer_sanity_check( name, consensus_hash ):
return True
-def build(name, keepdata, consensus_hash, testset=False):
+def build(name, keepdata, consensus_hash):
"""
Takes in a name to transfer. Name must include the namespace ID, but not the scheme.
@@ -118,7 +129,7 @@ def build(name, keepdata, consensus_hash, testset=False):
readable_script = 'NAME_TRANSFER 0x%s 0x%s 0x%s' % (disposition_hex, name_hash, consensus_hash)
hex_script = blockstack_script_to_hex(readable_script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
@@ -153,6 +164,37 @@ def make_outputs( data, inputs, new_name_owner_address, change_address, pay_fee=
]
+def state_transition(name, destination_address, keepdata, consensus_hash, private_key, user_public_key=None):
+
+ namespace_id = get_namespace_from_name(name)
+ blockchain_name = namespace_to_blockchain( namespace_id )
+
+ # sanity check
+ pay_fee = True
+ if user_public_key is not None:
+ pay_fee = False
+
+ if user_public_key is None and private_key is None:
+ raise Exception("Missing both public and private key")
+
+ pubk = None
+
+ if user_public_key is not None:
+ # subsidizing
+ pubk = ECPublicKey( user_public_key )
+
+ else:
+ # ordering directly
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ inputs = get_tx_inputs( blockchain_name, from_address )
+
+ nulldata = build(name, keepdata, consensus_hash )
+ outputs = make_outputs(nulldata, inputs, destination_address, from_address, pay_fee=pay_fee, format='hex')
+ return inputs, outputs
+
+
def broadcast(name, destination_address, keepdata, consensus_hash, private_key, blockchain_client, blockchain_broadcaster=None, tx_only=False, user_public_key=None, testset=False):
# sanity check
@@ -169,37 +211,33 @@ def broadcast(name, destination_address, keepdata, consensus_hash, private_key,
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
-
- from_address = None
- inputs = None
- private_key_obj = None
+
+ pubk = None
if user_public_key is not None:
# subsidizing
- pubk = BitcoinPublicKey( user_public_key )
+ pubk = ECPublicKey( user_public_key )
- from_address = pubk.address()
- inputs = get_unspents( from_address, blockchain_client )
-
- elif private_key is not None:
+ else:
# ordering directly
- pubk = BitcoinPrivateKey( private_key ).public_key()
- public_key = pubk.to_hex()
-
- # get inputs and from address using private key
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
+ pubk = ECPrivateKey( private_key ).public_key()
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
nulldata = build(name, keepdata, consensus_hash, testset=testset)
outputs = make_outputs(nulldata, inputs, destination_address, from_address, pay_fee=pay_fee, format='hex')
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {"unsigned_tx": unsigned_tx}
else:
# serialize, sign, and broadcast the tx
- response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
+ signed_tx = tx_serialize_sign( inputs, outputs, private_key )
+ response = broadcast_transaction( signed_tx, blockchain_broadcaster )
+ # response = serialize_sign_and_broadcast(inputs, outputs, private_key_obj, blockchain_broadcaster)
response.update({'data': nulldata})
return response
diff --git a/blockstack/lib/operations/update.py b/blockstack/lib/operations/update.py
index 31bac2613..ddc374f35 100644
--- a/blockstack/lib/operations/update.py
+++ b/blockstack/lib/operations/update.py
@@ -21,10 +21,8 @@
along with Blockstack. If not, see .
"""
-from pybitcoin import embed_data_in_blockchain, make_op_return_tx, BlockchainInfoClient, BitcoinPrivateKey, \
- BitcoinPublicKey, get_unspents, script_hex_to_address, hex_hash160, broadcast_transaction, serialize_transaction, \
- make_op_return_outputs, make_op_return_script
-
+from blockstack_utxo import get_unspents, broadcast_transaction
+from keylib import ECPrivateKey, ECPublicKey
from utilitybelt import is_hex
from binascii import hexlify, unhexlify
@@ -33,9 +31,13 @@ from ..config import *
from ..scripts import *
from ..hashing import hash256_trunc128
-from ..nameset import NAMEREC_FIELDS
+from ..nameset import NAMEREC_FIELDS, get_namespace_from_name
+from ..blockchain import get_tx_inputs
import virtualchain
+from virtualchain import hex_hash160
+from virtualchain.lib.blockchain.bitcoin import script_hex_to_address, make_op_return_script, tx_serialize, tx_serialize_and_sign, tx_output_is_op_return
+
log = virtualchain.get_logger("blockstack-server")
# consensus hash fields (ORDER MATTERS!)
@@ -64,7 +66,7 @@ def update_sanity_test( name, consensus_hash, data_hash ):
return True
-def build(name, consensus_hash, data_hash=None, testset=False):
+def build(name, consensus_hash, data_hash=None):
"""
Takes in the name to update the data for and the data update itself.
Name must include the namespace ID, but not the scheme.
@@ -84,7 +86,7 @@ def build(name, consensus_hash, data_hash=None, testset=False):
readable_script = 'NAME_UPDATE 0x%s 0x%s' % (hex_name, data_hash)
hex_script = blockstack_script_to_hex(readable_script)
- packaged_script = add_magic_bytes(hex_script, testset=testset)
+ packaged_script = add_magic_bytes(hex_script)
return packaged_script
@@ -120,6 +122,40 @@ def make_outputs( data, inputs, change_address, pay_fee=True ):
]
+def state_transition(name, data_hash, consensus_hash, private_key, user_public_key=None):
+ """
+ Write a name update into the blockchain.
+ Returns a JSON object with 'data' set to the nulldata and 'transaction_hash' set to the transaction hash on success.
+ """
+
+ namespace_id = get_namespace_from_name(name)
+ blockchain_name = namespace_to_blockchain( namespace_id )
+
+ # sanity check
+ pay_fee = True
+ if user_public_key is not None:
+ pay_fee = False
+
+ if user_public_key is None and private_key is None:
+ raise Exception("Missing both public and private key")
+
+ pubk = None
+ if user_public_key is not None:
+ # subsidizing
+ pubk = ECPublicKey( user_public_key )
+
+ else:
+ # ordering directly
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ inputs = get_tx_inputs( blockchain_name, from_address )
+
+ nulldata = build(name, consensus_hash, data_hash=data_hash)
+ outputs = make_outputs( nulldata, inputs, from_address, pay_fee=pay_fee )
+ return inputs, outputs
+
+
def broadcast(name, data_hash, consensus_hash, private_key, blockchain_client, blockchain_broadcaster=None, tx_only=False, user_public_key=None, testset=False):
"""
Write a name update into the blockchain.
@@ -141,37 +177,29 @@ def broadcast(name, data_hash, consensus_hash, private_key, blockchain_client, b
if blockchain_broadcaster is None:
blockchain_broadcaster = blockchain_client
- from_address = None
- inputs = None
- private_key_obj = None
-
+ pubk = None
if user_public_key is not None:
# subsidizing
- pubk = BitcoinPublicKey( user_public_key )
- from_address = pubk.address()
-
- # get inputs from utxo provider
- inputs = get_unspents( from_address, blockchain_client )
+ pubk = ECPublicKey( user_public_key )
- elif private_key is not None:
+ else:
# ordering directly
- pubk = BitcoinPrivateKey( private_key ).public_key()
- public_key = pubk.to_hex()
-
- # get inputs and from address using private key
- private_key_obj, from_address, inputs = analyze_private_key(private_key, blockchain_client)
-
+ pubk = ECPrivateKey( private_key ).public_key()
+
+ from_address = pubk.address()
+ inputs = get_unspents( from_address, blockchain_client )
+
nulldata = build(name, consensus_hash, data_hash=data_hash, testset=testset)
outputs = make_outputs( nulldata, inputs, from_address, pay_fee=pay_fee )
if tx_only:
- unsigned_tx = serialize_transaction( inputs, outputs )
+ unsigned_tx = tx_serialize( inputs, outputs )
return {'unsigned_tx': unsigned_tx}
else:
- signed_tx = tx_serialize_and_sign( inputs, outputs, private_key_obj )
+ signed_tx = tx_serialize_sign( inputs, outputs, private_key )
response = broadcast_transaction( signed_tx, blockchain_broadcaster )
response.update({'data': nulldata})
return response