我注意到一些STEEMIT在线工具返回数据很慢, 特别是当返回的数据很多行时, 经常需要等个几十秒, 非常的不友好. 比如, 现有138人代理给YY银行, 通过 这个代理查询工具 则需要几十秒才能返回数据.
今天我稍微研究了一下, 发现在使用 steem-python中的 converter 特别的慢.
1 2 3 4 | steem = Steem(nodes = steem_nodes) converter = Converter(steemd_instance = steem) while some loop: r.append( "sp": converter.vests_to_sp(vests)}) |
steem = Steem(nodes = steem_nodes) converter = Converter(steemd_instance = steem) while some loop: r.append( "sp": converter.vests_to_sp(vests)})
方法 converter.vests_to_sp() 很慢, 被调用在循环里时, 这就能解释为什么数据量越大的时候需要的时间越长. 看了converter.py代码:
1 2 3 4 5 6 7 | def steem_per_mvests(self): info = self.steemd.get_dynamic_global_properties() return (Amount(info["total_vesting_fund_steem"]).amount / (Amount(info["total_vesting_shares"]).amount / 1e6)) def vests_to_sp(self, vests): return vests / 1e6 * self.steem_per_mvests() |
def steem_per_mvests(self): info = self.steemd.get_dynamic_global_properties() return (Amount(info["total_vesting_fund_steem"]).amount / (Amount(info["total_vesting_shares"]).amount / 1e6)) def vests_to_sp(self, vests): return vests / 1e6 * self.steem_per_mvests()
我们可以看到 steem_per_mvests 实际上会调用 steemd 去区块链上取数据.
实际上这个数值我们并不需要实时的精确, 并且这个数值也不会变化太剧烈, 所以我们只要把 self.steem_per_mvests() 这个数值缓存起, 然后定期更新它就可以. 重写一下这个缓存版本的 vests_to_sp
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | import os def file_get_contents(filename): with open(filename) as f: return f.read() def vests_to_sp(vests): steem_per_mvests = 489.85031585637665 fname = "cache/steem_per_mvests.txt" try: if os.path.isfile(fname): x = file_get_contents(fname).strip() if len(x) > 1: x = float(x) if x > 0: steem_per_mvests = x except: pass return vests / 1e6 * steem_per_mvests |
import os def file_get_contents(filename): with open(filename) as f: return f.read() def vests_to_sp(vests): steem_per_mvests = 489.85031585637665 fname = "cache/steem_per_mvests.txt" try: if os.path.isfile(fname): x = file_get_contents(fname).strip() if len(x) > 1: x = float(x) if x > 0: steem_per_mvests = x except: pass return vests / 1e6 * steem_per_mvests
我们需要一个更新脚本 update_steem_per_mvests.py 用于定期的却STEEM区块链上取数据然后写入 steem_per_mvests.txt
1 2 3 4 5 6 7 8 9 10 11 12 13 | from steem.converter import Converter from steem import Steem from nodes import steem_nodes def file_put_contents(filename, data): with open(filename, 'w') as f: f.write(data) steem = Steem(nodes = steem_nodes) converter = Converter(steemd_instance = steem) x = converter.steem_per_mvests() file_put_contents('cache/steem_per_mvests.txt', str(x)) |
from steem.converter import Converter from steem import Steem from nodes import steem_nodes def file_put_contents(filename, data): with open(filename, 'w') as f: f.write(data) steem = Steem(nodes = steem_nodes) converter = Converter(steemd_instance = steem) x = converter.steem_per_mvests() file_put_contents('cache/steem_per_mvests.txt', str(x))
最后面只需要放在 crontab 定时执行即可(频率可以根据需要调整)
@hourly python3 update_steem_per_mvests.py > /dev/null 2>&1
在软件设计的时候, 我们尽可能的不要去区块链实时的取数据, 因为这样性能很低, 相反, 我们把那些不是非常需要100%精确的数据缓存起来, 然后异步的去更新, 这样整体性能就能反应快许多, 更加的 responsive.
YY的点赞机器人每次都会去取YY银行股东的名单, 这并不需要实时的准确, 所以, 只需要通过另一脚本定期(每隔几分钟)跑一次, 把名单写在本地文件里, 需要的时候瞬间就能返回数据, 大大的减少了机器人跑一次的时间.
英文: Improve Performance using Asynchronous Design (SteemIt)
loading...
上一篇: 使用AWK来估计您下次出块还需要多久? (SteemIt)
下一篇: 祝媳妇生日快乐