Skip to content

Commit

Permalink
Made script work with email
Browse files Browse the repository at this point in the history
  • Loading branch information
vbuterin committed Jul 17, 2014
1 parent 895aaf6 commit 410e84a
Show file tree
Hide file tree
Showing 2 changed files with 71 additions and 67 deletions.
134 changes: 69 additions & 65 deletions pyethsaletool.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,15 @@
import getpass
import pbkdf2 as PBKDF2
from bitcoin import *
import urllib2

from optparse import OptionParser

# Arguments

exodus = '1FxkfJQLJTXpW6QmxGT6oF43ZH959ns8Cq'
exodus = '3HE73tDm7q6wHMhCxfThDQFpBX9oq14ZaG'
minimum = 1000000
maximum = 150000000000

# Option parsing

Expand All @@ -24,8 +26,8 @@
default=None, dest='seed')
parser.add_option('-w', '--wallet',
default='ethwallet.json', dest='wallet')
parser.add_option('-b', '--backup',
default='ethwallet.bkp.json', dest='backup')
parser.add_option('-e', '--email',
default=None, dest='email')
parser.add_option('-o', '--overwrite',
default=False, dest='overwrite')

Expand All @@ -42,6 +44,12 @@ def pbkdf2(x):
return PBKDF2._pbkdf2(x, x, 2000)[:16]


# Makes a request to a given URL (first arg) and optional params (second arg)
def make_request(url, data, headers):
req = urllib2.Request(url, data, headers)
return urllib2.urlopen(req).read().strip()


# Prefer openssl because it's more well-tested and reviewed; otherwise,
# use pybitcointools' internal ecdsa implementation
try:
Expand Down Expand Up @@ -113,56 +121,55 @@ def getseed(encseed, pw, ethaddr):
return seed


def mkbackup(wallet, pw):
seed = getseed(wallet['encseed'], pw, wallet['ethaddr'])
return {
"withpw": aes.encryptData(pw, seed).encode('hex'),
"withwallet": aes.encryptData(wallet['bkp'], seed).encode('hex'),
"ethaddr": wallet['ethaddr']
}


def genwallet(seed, pw):
def genwallet(seed, pw, email):
encseed = aes.encryptData(pw, seed)
ethpriv = sha3(seed)
btcpriv = sha3(seed + '\x01')
ethaddr = sha3(secure_privtopub(ethpriv)[1:])[12:].encode('hex')
btcaddr = privtoaddr(btcpriv)
bkp = sha3(seed + '\x02').encode('hex')[:32]
return {
"encseed": encseed.encode('hex'),
"bkp": bkp,
"ethaddr": ethaddr,
"btcaddr": btcaddr,
"email": email
}


def finalize(wallet, unspent, pw):
def finalize(wallet, utxos, pw, addr=None):
seed = getseed(wallet["encseed"], pw, wallet["ethaddr"])
balance = sum([o["value"] for o in unspent])
balance = sum([o["value"] for o in utxos])
change = 0
if addr:
sys.stderr.write("Warning: purchasing into a custom address. The wallet file generated by this script will NOT be able to access your ETH\n")
outputethaddr = addr
else:
outputethaddr = wallet["ethaddr"]
if balance == 0:
raise Exception("No funds in address")
if balance < minimum:
raise Exception("Insufficient funds. Need at least 0.001 BTC")
outs = [
exodus+':'+str(balance - 30000),
hex_to_b58check(wallet["ethaddr"])+':10000'
]
tx = mktx(unspent, outs)
elif balance < minimum:
raise Exception("Insufficient funds. Need at least %s BTC" %
str(minimum * 0.00000001))
elif balance > maximum:
change = balance - maximum
balance = maximum
sys.stderr.write("Too much BTC. Returning excess to intermediate address as change\n")
outs = [
exodus+':'+str(balance - 40000),
hex_to_b58check(outputethaddr)+':10000',
str(wallet["btcaddr"])+':'+str(change)
]
else:
outs = [
exodus+':'+str(balance - 30000),
hex_to_b58check(outputethaddr)+':10000',
]
tx = mktx(utxos, outs)
btcpriv = sha3(seed+'\x01')
for i in range(len(unspent)):
for i in range(len(utxos)):
tx = secure_sign(tx, i, btcpriv)
return tx


def recover_bkp_pw(bkp, pw):
return getseed(bkp['withpw'], pw, bkp['ethaddr'])


def recover_bkp_wallet(bkp, wallet):
return getseed(bkp['withwallet'], wallet['bkp'], bkp['ethaddr'])


def ask_for_password(twice=False):
if options.pw:
return pbkdf2(options.pw)
Expand Down Expand Up @@ -198,25 +205,16 @@ def checkwrite(f, thunk):


w = tryopen(options.wallet)
b = tryopen(options.backup)
# Generate new wallet
if not len(args):
pass
elif args[0] == 'genwallet':
args.append('help')
if args[0] == 'genwallet':
pw = ask_for_password(True)
newwal = genwallet(ask_for_seed(), pw)
email = options.email or raw_input("Please enter email: ")
newwal = genwallet(ask_for_seed(), pw, email)
checkwrite(options.wallet, lambda: json.dumps(newwal))
if options.backup:
checkwrite(options.backup, lambda: json.dumps(mkbackup(newwal, pw)))
print "Your intermediate Bitcoin address is:", newwal['btcaddr']
# Backup existing wallet
elif args[0] == 'mkbackup':
if not w:
print "Must specify wallet with -w"
if not opts['backup']:
opts['backup'] = 'ethwallet.bkp.json'
pw = password()
checkwrite(opts['backup'], lambda: json.dumps(mkbackup(w, pw)))
print "Be absolutely sure to keep the wallet safe and backed up, and do not lose your password"
# Get wallet Bitcoin address
elif args[0] == 'getbtcaddress':
if not w:
Expand All @@ -242,16 +240,11 @@ def checkwrite(f, thunk):
print encode_privkey(sha3(getseed(w['encseed'], pw, w['ethaddr'])), 'hex')
# Recover wallet seed
elif args[0] == 'recover':
if not w and not b:
print "Must have wallet or backup file"
elif not b:
if not w:
print "Must have wallet file"
else:
pw = ask_for_password()
print "Your seed is:", getseed(w['encseed'], pw, w['ethaddr'])
elif not w:
pw = ask_for_password()
print "Your seed is:", getseed(b['withpw'], pw, b['ethaddr'])
else:
print "Your seed is:", getseed(b['withwallet'], w['bkp'], b['ethaddr'])
# Finalize a wallet
elif args[0] == 'finalize':
try:
Expand All @@ -262,25 +255,36 @@ def checkwrite(f, thunk):
except:
raise Exception("Blockchain.info and Blockr.io both down. Cannot get transaction outputs to finalize. Remember that your funds stored in the intermediate address can always be recovered by running './pyethsaletool.py getbtcprivkey' and importing the output into a Bitcoin wallet like blockchain.info")
pw = ask_for_password()
tx = finalize(w, u, pw)
if len(args) == 1:
tx = finalize(w, u, pw)
else:
# Finalize into custom address
tx = finalize(w, u, pw, args[1])
try:
print pushtx(tx)
except:
try:
print eligius_pushtx(tx)
except:
raise Exception("Blockchain.info and Eligius both down. Cannot send transaction. Remember that your funds stored in the intermediate address can always be recovered by running './pyethsaletool.py getbtcprivkey' and importing the output into a Bitcoin wallet like blockchain.info")
headers = {
'Content-Type': 'application/json',
'Accept': 'application/json, text/plain, */*'
}
make_request('https://sale.ethereum.org/sendmail',
json.dumps({"tx": tx, "email": w["email"], "emailjson": w}),
headers=headers)
# sha3 calculator
elif args[0] == 'sha3':
print sha3(sys.argv[2]).encode('hex')
# Help
else:
print 'Use "pyethsaletool genwallet" to generate a wallet'
print 'Use "pyethsaletool mkbackup" to make a backup of a wallet (using -w and -b)'
print 'Use "pyethsaletool getbtcaddress" to output the intermediate Bitcoin address you need to send funds to'
print 'Use "pyethsaletool getbtcprivkey" to output the private key to your intermediate Bitcoin address'
print 'Use "pyethsaletool getethaddress" to output the Ethereum address'
print 'Use "pyethsaletool getethprivkey" to output the Ethereum private key'
print 'Use "pyethsaletool finalize" to finalize the funding process once you have deposited to the intermediate address'
print 'Use "pyethsaletool recover" to recover the seed if you are missing either your wallet or your password'
print 'Use -s to specify a seed, -w to specify a wallet file, -b to specify a backup file and -p to specify a password when creating a wallet. The -w, -b and -p options also work with other commands.'
print 'Use "python pyethsaletool.py genwallet" to generate a wallet'
print 'Use "python pyethsaletool.py getbtcaddress" to output the intermediate Bitcoin address you need to send funds to'
print 'Use "python pyethsaletool.py getbtcprivkey" to output the private key to your intermediate Bitcoin address'
print 'Use "python pyethsaletool.py getethaddress" to output the Ethereum address'
print 'Use "python pyethsaletool.py getethprivkey" to output the Ethereum private key'
print 'Use "python pyethsaletool.py finalize" to finalize the funding process once you have deposited to the intermediate address'
print 'Use "python pyethsaletool.py finalize 00c40fe2095423509b9fd9b754323158af2310f3" (or some other ethereum address) to purchase directly into some other Ethereum address'
print 'Use "python pyethsaletool.py recover" to recover the seed if you are missing either your wallet or your password'
print 'Use -s to specify a seed, -w to specify a wallet file and -p to specify a password when creating a wallet. The -w, -b and -p options also work with other commands.'
4 changes: 2 additions & 2 deletions pylist.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,9 @@ def pbkdf2(x):

def processtx(txhex):
txouts = b.deserialize(txhex)['outs']
if txouts[0]['value'] >= 960000 and len(txouts) >= 2:
if txouts[0]['value'] >= 970000 and len(txouts) >= 2:
ethaddr = b.b58check_to_hex(b.script_to_address(txouts[1]['script']))
v = txouts[0]['value'] + 40000
v = txouts[0]['value'] + 30000
print "Tx:", h
print "Satoshis:", v
print "Estimated ETH (min):", v * 1337 / 10**8
Expand Down

0 comments on commit 410e84a

Please sign in to comment.