Working toward a vote for download System for Steemfiles.com
Over on Steemfiles.com you can pay for downloads. What if you could get a downloaded thing for voting for it? That's the idea of my latest contest. You can download a band performance by voting that post up. Today, I wrote source code for determining who gets the file.
The author will be compensated for every download. The script decides which user wins the download. There is more back-end work and a couple of hard coded values to remove.
Here it is:
#!/usr/local/bin/python3.6
# Gives a list of winners
import hashlib
from getpass import getpass
from steem.steem import Steem
import sys
from optparse import OptionParser
import steembase
parser = OptionParser()
parser.add_option('-l', '--permlink')
parser.add_option('-a','--author')
(options, args) = parser.parse_args()
post_author = 'steemfiles'
if options.permlink is not None:
post_permlink = options.permlink
if options.author is not None:
post_author = options.author
secret = getpass(prompt='Enter the secret text: ', stream=None)
steem = Steem()
# verify the user voted on the post
try:
active_votes = steem.get_active_votes(post_author, post_permlink)
except steembase.exceptions.RPCError as rpce:
print("Invalid permlink/author combination")
sys.exit(1)
def get_txid(vote_row):
vote_time = vote_row['time']
txs = steem.get_account_history(vote_row['voter'], index_from=999999999999999999, limit=0)
tx = txs[0][1]
high_value = txs[0][0]
low_value = 1
pivot_value = high_value # int((high_value + low_value)/2)
while tx['timestamp'] != vote_time and high_value - low_value > 100:
if tx['timestamp'] > vote_time:
high_value = pivot_value
else:
low_value = pivot_value
pivot_value = int((high_value + low_value)/2)
tx = steem.get_account_history(vote_row['voter'], index_from=pivot_value, limit=0)[0][1]
# switch to a linear search as we are pretty close already and this way we do not make so many RPC calls.
txs = steem.get_account_history(vote_row['voter'], index_from=high_value, limit=100)
for index,tx in txs:
if tx['timestamp'] == vote_time and tx['op'][0] == 'vote':
vote = tx['op'][1]
if vote['voter'] == vote_row['voter'] and vote['author'] == post_author and vote['permlink'] == post_permlink:
return tx['trx_id']
else:
assert(False)
def get_number_of_winners(author, permlink):
p = steem.get_content(author, permlink)
return float(p['total_payout_value'].split(' ')[0])/0.002
score_values = []
for vote_bc_row in active_votes:
try:
m = hashlib.sha256()
m.update((secret + ':' + get_txid(vote_bc_row)).encode('ascii'))
digest_string = m.hexdigest()
score = int(vote_bc_row['rshares']) * int(vote_bc_row['percent']) * int(vote_bc_row['weight']) * 1e59 / int(digest_string, base=16)
score_values += [[score, vote_bc_row['voter']]]
except KeyError as e:
print("No key ", e.args[0], " in ", vote_bc_row)
sys.exit(0)
score_values.sort()
winner_count = get_number_of_winners(post_author, post_permlink)
if winner_count > len(score_values):
print("Everybody wins!")
winner_count = len(score_values)
print(score_values)
if winner_count == 0:
print("There are no winners.")
sys.exit(0)
try:
print("winner list")
for i in range(len(score_values)-winner_count, len(score_values)):
print(score_values[i][1])
except TypeError:
print("Score values: ", score_values)