From d5dd602c1db2c62d2754a3ab71d82decbc5c7b1d Mon Sep 17 00:00:00 2001 From: mtrela <mtrela@syncad.com> Date: Tue, 28 Jul 2020 15:27:13 +0200 Subject: [PATCH] Votes inserted by `vote_operation` and updated by `effective_comment_vote_operation` operation --- hive/indexer/blocks.py | 3 +- hive/indexer/posts.py | 11 +++-- hive/indexer/votes.py | 108 ++++++++++++++++++++++++++++++++++------- 3 files changed, 99 insertions(+), 23 deletions(-) diff --git a/hive/indexer/blocks.py b/hive/indexer/blocks.py index a8ed93683..4c049d0c9 100644 --- a/hive/indexer/blocks.py +++ b/hive/indexer/blocks.py @@ -229,6 +229,7 @@ class Blocks: if not is_initial_sync: Accounts.dirty(op['author']) # lite - rep Accounts.dirty(op['voter']) # lite - stats + Votes.vote_op(op) # misc ops elif op_type == 'transfer_operation': @@ -254,7 +255,7 @@ class Blocks: (vote_ops, comment_payout_ops) = Blocks.prepare_vops(vops, cls._head_block_date) for k, v in vote_ops.items(): - Votes.vote_op(v, cls._head_block_date) + Votes.effective_comment_vote_op(v, cls._head_block_date) op_type = 'effective_comment_vote_operation' if op_type in cls.ops_stats: cls.ops_stats[op_type] += 1 diff --git a/hive/indexer/posts.py b/hive/indexer/posts.py index e60cc40be..d3184e3e2 100644 --- a/hive/indexer/posts.py +++ b/hive/indexer/posts.py @@ -287,13 +287,14 @@ class Posts: pending_payout = 0 #Calculations of all dates - if ( total_payout_value is not None ): - payout_at = date - last_payout = date - if ( is_paidout is not None ): payout_at = date - cashout_time = date + last_payout = date + cashout_time = "1969-12-31T23:59:59" + else: + if ( total_payout_value is not None ): + payout_at = date #Here should be `cashout_time` + last_payout = date values.append("('{}', '{}', {}, {}, {}, {}, {}, {}, {}, {}, {}, '{}'::timestamp, {}, {}, {})".format( author, diff --git a/hive/indexer/votes.py b/hive/indexer/votes.py index b5ce7cfdd..e5e47947f 100644 --- a/hive/indexer/votes.py +++ b/hive/indexer/votes.py @@ -10,6 +10,7 @@ DB = Db.instance() class Votes: """ Class for managing posts votes """ _votes_data = {} + _effective_votes_data = {} @classmethod def get_vote_count(cls, author, permlink): @@ -64,34 +65,51 @@ class Votes: cls._votes_data[key] = dict(voter=voter, author=author, permlink=permlink, - vote_percent=vop['vote_percent'], - weight=vop['weight'], - rshares=vop['rshares'], - last_update=date) + weight=vop['weight']) @classmethod - def flush(cls): + def effective_comment_vote_op(cls, vop, date): + """ Process effective_comment_vote_operation """ + voter = vop['voter'] + author = vop['author'] + permlink = vop['permlink'] + + if(cls.inside_flush): + log.info("Adding new effective comment vote into '_effective_votes_data' dict") + raise "Fatal error" + + key = voter + "/" + author + "/" + permlink + + cls._effective_votes_data[key] = dict(voter=voter, + author=author, + permlink=permlink, + vote_percent=vop['vote_percent'], + weight=vop['weight'], + rshares=vop['rshares'], + last_update=date) + + @classmethod + def flush_votes(cls): """ Flush vote data from cache to database """ - cls.inside_flush = True if cls._votes_data: sql = """ INSERT INTO hive_votes - (post_id, voter_id, author_id, permlink_id, weight, rshares, vote_percent, last_update) - select data_source.post_id, data_source.voter_id, data_source.author_id, data_source.permlink_id, data_source.weight, data_source.rshares, data_source.vote_percent, data_source.last_update - from + (post_id, voter_id, author_id, permlink_id, weight) + select data_source.post_id, data_source.voter_id, data_source.author_id, data_source.permlink_id, data_source.weight + from ( - SELECT hp.id as post_id, ha_v.id as voter_id, ha_a.id as author_id, hpd_p.id as permlink_id, t.weight, t.rshares, t.vote_percent, t.last_update + SELECT hp.id as post_id, ha_v.id as voter_id, ha_a.id as author_id, hpd_p.id as permlink_id, t.weight from ( VALUES - -- voter, author, permlink, weight, rshares, vote_percent, last_update + -- voter, author, permlink, weight {} - ) AS T(voter, author, permlink, weight, rshares, vote_percent, last_update) + ) AS T(voter, author, permlink, weight) INNER JOIN hive_accounts ha_v ON ha_v.name = t.voter INNER JOIN hive_accounts ha_a ON ha_a.name = t.author INNER JOIN hive_permlink_data hpd_p ON hpd_p.permlink = t.permlink - INNER JOIN hive_posts hp ON hp.author_id = ha_a.id AND hp.permlink_id = hpd_p.id - ) as data_source(post_id, voter_id, author_id, permlink_id, weight, rshares, vote_percent, last_update) + INNER JOIN hive_posts hp ON hp.author_id = ha_a.id AND hp.permlink_id = hpd_p.id + ) as data_source(post_id, voter_id, author_id, permlink_id, weight) ON CONFLICT ON CONSTRAINT hive_votes_ux1 DO UPDATE SET @@ -107,8 +125,8 @@ class Votes: values_limit = 1000 for _, vd in cls._votes_data.items(): - values.append("('{}', '{}', '{}', {}, {}, {}, '{}'::timestamp)".format( - vd['voter'], vd['author'], vd['permlink'], vd['weight'], vd['rshares'], vd['vote_percent'], vd['last_update'])) + values.append("('{}', '{}', '{}', {})".format( + vd['voter'], vd['author'], vd['permlink'], vd['weight'])) if len(values) >= values_limit: values_str = ','.join(values) @@ -123,4 +141,60 @@ class Votes: values.clear() cls._votes_data.clear() - cls.inside_flush = False + + @classmethod + def flush_effective_votes(cls): + """ Flush vote data from cache to database """ + if cls._effective_votes_data: + sql = """ + UPDATE hive_votes AS hv SET + weight = data_source.weight, + rshares = data_source.rshares, + vote_percent = data_source.vote_percent, + last_update = data_source.last_update, + num_changes = hv.num_changes + 1 + FROM + ( + SELECT ha_v.id as voter_id, ha_a.id as author_id, hpd_p.id as permlink_id, t.weight, t.rshares, t.vote_percent, t.last_update + FROM + ( + VALUES + -- voter, author, permlink, weight, rshares, vote_percent, last_update + {} + ) AS T(voter, author, permlink, weight, rshares, vote_percent, last_update) + INNER JOIN hive_accounts ha_v ON ha_v.name = t.voter + INNER JOIN hive_accounts ha_a ON ha_a.name = t.author + INNER JOIN hive_permlink_data hpd_p ON hpd_p.permlink = t.permlink + ) as data_source(voter_id, author_id, permlink_id, weight, rshares, vote_percent, last_update) + WHERE hv.voter_id = data_source.voter_id and hv.author_id = data_source.author_id and hv.permlink_id = data_source.permlink_id; + """ + + values = [] + values_limit = 1000 + + for _, vd in cls._effective_votes_data.items(): + values.append("('{}', '{}', '{}', {}, {}, {}, '{}'::timestamp)".format( + vd['voter'], vd['author'], vd['permlink'], vd['weight'], vd['rshares'], vd['vote_percent'], vd['last_update'])) + + if len(values) >= values_limit: + values_str = ','.join(values) + actual_query = sql.format(values_str) + DB.query(actual_query) + values.clear() + + if len(values) > 0: + values_str = ','.join(values) + actual_query = sql.format(values_str) + DB.query(actual_query) + values.clear() + + cls._effective_votes_data.clear() + + @classmethod + def flush(cls): + cls.inside_flush = True + + cls.flush_votes() + cls.flush_effective_votes() + + cls.inside_flush = False \ No newline at end of file -- GitLab