def get_latest_block(api_key: hug.types.text, request, hug_timer=5): """Retrieve the latest block's details (date & time) & output in JSON!""" if (check_api_token(api_key) == True): # Check the api key # API KEY VALID google_analytics(request, 'get_latest_block') chain = Blockchain() current_block_number = chain.get_current_block_num() block_date = chain.block_time(current_block_number) target_block = Block(current_block_number) return {'previous': target_block['previous'], 'timestamp': target_block['timestamp'], 'witness': target_block['witness'], 'transaction_merkle_root': target_block['transaction_merkle_root'], 'extensions': target_block['extensions'], 'witness_signature': target_block['witness_signature'], 'transactions': target_block['transactions'], 'id': target_block['id'], 'block_date': block_date, 'block_number': current_block_number, 'valid_block_number': True, 'valid_key': True, 'took': float(hug_timer)} else: # API KEY INVALID! return {'valid_key': False, 'took': float(hug_timer)}
class Testcases(unittest.TestCase): def setUp(self): fixture_data() self.chain = Blockchain(mode="head") def test_is_irv(self): self.assertFalse(self.chain.is_irreversible_mode()) def test_info(self): info = self.chain.info() for i in [ "time", "dynamic_flags", "head_block_id", "head_block_number", "last_budget_time", ]: self.assertIn(i, info) def test_parameters(self): info = self.chain.chainParameters() for i in [ "worker_budget_per_day", "maintenance_interval", ]: self.assertIn(i, info) def test_network(self): info = self.chain.get_network() for i in [ "chain_id", "core_symbol", "prefix", ]: self.assertIn(i, info) def test_props(self): info = self.chain.get_chain_properties() for i in [ "id", "chain_id", "immutable_parameters", ]: self.assertIn(i, info) def test_block_num(self): num = self.chain.get_current_block_num() self.assertTrue(num > 100) def test_block(self): block = self.chain.get_current_block() self.assertIsInstance(block, Block) self.chain.block_time(1) self.chain.block_timestamp(1) def test_list_accounts(self): for account in self.chain.get_all_accounts(): self.assertIsInstance(account, str) # Break already break
def ping(n, num, arr): # ping the blockchain and return latency try: start = time.time() chain = Blockchain(bitshares_instance=BitShares(n, num_retries=0), mode='head') # print(n,chain.rpc.chain_params["chain_id"]) ping_latency = time.time() - start current_block = chain.get_current_block_num() blocktimestamp = abs( chain.block_timestamp(current_block)) # + utc_offset) block_latency = time.time() - blocktimestamp # print (blocktimestamp) # print (time.time()) # print (block_latency) # print (ping_latency) # print (time.ctime()) # print (utc_offset) # print (chain.get_network()) if chain.get_network()['chain_id'] != ID: num.value = 333333 elif block_latency < (ping_latency + 4): num.value = ping_latency else: num.value = 111111 except: num.value = 222222 pass
def recent_block_creation(self, witness_id): """ returns True if witness id is in the N last blocks created """ btschain = Blockchain() block_created = False srt = None if self.witnesses and self.block_interval: srt = self.witnesses * self.block_interval else: srt = self.get_shuffle_round_time() currblock = btschain.get_current_block_num() startblock = srt * self.shuffle_rounds_alert c = ( '{{"jsonrpc": "2.0", "params": ["database", "get_block_header_batch", ' '[[{}]]], "method": "call", "id": 10}}'.format(",".join( str(x) for x in range(currblock - startblock, currblock)))) r = btsconf.confs["bts"].rpc.rpcexec(loads(c)) for bl in r: if bl[1] and bl[1]['witness'] == witness_id: block_created = True return block_created
def play_game(account, amountBet, userRoll): memo = Memo('bts-dice-game', account) nodeForConnections = 'wss://api.bitsharesdex.com' blockchain = Blockchain(node=nodeForConnections, mode='head') bitshares = BitShares( node=nodeForConnections, nobroadcast=False, ) blockNum = blockchain.get_current_block_num() userGuess = userRoll seed(blockNum * (userGuess + 1)) diceRatios = btsDiceRatios winRatio = diceRatios.get_ratio(userGuess) value = randint(1, 100) correctGuess = value < int(userGuess) bitshares.wallet.unlock('superSecretPassword') if winRatio is None: print('You submitted something not correct to this contract.') elif correctGuess: winningAmount = winRatio * amountBet winningString = "Correct! You guessed {0} and rolled {1}. You won {2:.5f} BTS.".format( userRoll, value, winningAmount) bitshares.transfer(account, winningAmount, 'BTS', winningString, account='bts-dice-game') print(winningString) else: losingString = "Incorrect. You guessed {0} and rolled {1}.".format( userRoll, value) bitshares.transfer(account, 0.00001, 'BTS', losingString, account='bts-dice-game') print( 'You guessed incorrectly. Your guess was {a} and you rolled {b}.'. format(a=userRoll, b=value))
def ping(n, num, arr): try: start = time.time() chain = Blockchain(bitshares_instance=BitShares(n, num_retries=0), mode='head') ping_latency = time.time() - start current_block = chain.get_current_block_num() blocktimestamp = abs( chain.block_timestamp(current_block) + utc_offset) block_latency = time.time() - blocktimestamp if block_latency < (ping_latency + 4): num.value = ping_latency else: num.value = 111111 except: num.value = 222222 pass
def dex( # Public AND Private API Bitshares command, amount=ANTISAT, price=None, depth=1, expiration=ANTISAT): MARKET = Market(BitPAIR, bitshares_instance=BitShares(nodes(), num_retries=0)) CHAIN = Blockchain(bitshares_instance=BitShares(nodes(), num_retries=0), mode='head') #MARKET.bitshares.wallet.unlock(PASS_PHRASE) ACCOUNT.refresh() if command == 'buy': # buy relentlessly until satisfied or currency exhausted print(('Bitshares API', command)) if price is None: price = ANTISAT print(('buying', amount, 'at', price)) attempt = 1 currency = float(ACCOUNT.balance(BitCURRENCY)) if amount > 0.998 * currency * price: amount = 0.998 * currency * price if amount > 0: while attempt: try: details = (MARKET.buy(price, amount, expiration)) print (details) attempt = 0 except: print(("buy attempt %s failed" % attempt)) attempt += 1 if attempt > 10: print ('buy aborted') return pass else: print('no currency to buy') if command == 'sell': # sell relentlessly until satisfied or assets exhausted expiration = 86400 * 7 print(('Bitshares API', command)) if price is None: price = SATOSHI print(('selling', amount, 'at', price)) attempt = 1 assets = float(ACCOUNT.balance(BitASSET)) if amount > 0.998 * assets: amount = 0.998 * assets if amount > 0: while attempt: try: details = (MARKET.sell(price, amount, expiration)) print (details) attempt = 0 except: print(("sell attempt %s failed" % attempt)) attempt += 1 if attempt > 10: print ('sell aborted') return pass else: print('no assets to sell') if command == 'cancel': # cancel all orders in this MARKET relentlessly until satisfied print(('Bitshares API', command)) orders = MARKET.accountopenorders() print((len(orders), 'open orders to cancel')) if len(orders): attempt = 1 order_list = [] for order in orders: order_list.append(order['id']) while attempt: try: details = MARKET.cancel(order_list) print (details) attempt = 0 except: print((attempt, 'cancel failed', order_list)) attempt += 1 if attempt > 10: print ('cancel aborted') return pass if command == 'orders': servers = nodes() orders_list =[] satisfied = 0 while not satisfied: #while len set triplicate for n in servers: sorders = [str(i) for i in orders_list] if (len(sorders) >= 3) and len(set(sorders[-3:])) == 1: orders = orders_list[-1] satisfied = 1 else: MARKET = Market(BitPAIR, bitshares_instance=BitShares(n, num_retries=0)) MARKET.bitshares.wallet.unlock(PASS_PHRASE) ACCOUNT.refresh() # dictionary of open orders in traditional format: # orderNumber, orderType, market, amount, price print(('Bitshares API', command)) orders = [] for order in MARKET.accountopenorders(): orderNumber = order['id'] asset = order['base']['symbol'] currency = order['quote']['symbol'] amount = float(order['base']) price = float(order['price']) orderType = 'buy' if asset == BitASSET: orderType = 'sell' price = 1 / price orders.append({'orderNumber': orderNumber, 'orderType': orderType, 'market': BitPAIR, 'amount': amount, 'price': price}) orders_list.append(orders) for o in orders: print (o) if len(orders) == 0: print ('no open orders') return orders if command == 'market_balances': # dictionary of currency and assets in this MARKET print(('Bitshares API', command)) currency = float(ACCOUNT.balance(BitCURRENCY)) assets = float(ACCOUNT.balance(BitASSET)) balances = {'currency': currency, 'assets': assets} print (balances) return balances if command == 'complete_balances': # dictionary of ALL account balances print(('Bitshares API', command)) raw = list(ACCOUNT.balances) balances = {} for i in range(len(raw)): balances[raw[i]['symbol']] = float(raw[i]['amount']) print (balances) return balances if command == 'book': try: opened = 0 while not opened: with open('book.txt', 'r') as f: book = f.read() opened = 1 except Exception as e: print (e) print ('book.txt failed, try again...') pass return literal(book) if command == 'last': try: opened = 0 while not opened: with open('last.txt', 'r') as f: last = f.read() opened = 1 except Exception as e: print (e) print ('last.txt failed, try again...') pass return literal(last) if command == 'account_value': # dictionary account value in BTS BTC and USD print(('Bitshares API', command)) raw = list(ACCOUNT.balances) balances = {} for i in range(len(raw)): balances[raw[i]['symbol']] = float(raw[i]['amount']) btc_value = 0 for asset, amount in list(balances.items()): market_pair = 'OPEN.BTC:' + asset market = Market(market_pair) price = float(market.ticker()['latest']) try: value = amount / price except: value = 0 if value < 0.0001: value = 0 else: if asset != 'USD': price = 1 / (price + SATOSHI) print((('%.4f' % value), 'OPEN.BTC', ('%.2f' % amount), asset, '@', ('%.8f' % price))) btc_value += value market_pair = 'OPEN.BTC:USD' market = Market(market_pair) price = float(market.ticker()['latest']) usd_value = btc_value * price market_pair = 'OPEN.BTC:BTS' market = Market(market_pair) price = float(market.ticker()['latest']) bts_value = btc_value * price print((('%.2f' % bts_value), 'BTS', ('%.4f' % btc_value), 'OPEN.BTC', ('%.2f' % usd_value), 'bitUSD')) return bts_value, btc_value, usd_value if command == 'blocktime': current_block = CHAIN.get_current_block_num() blocktime = CHAIN.block_time(current_block) blocktimestamp = CHAIN.block_timestamp(current_block) - 18000 now = time.time() latency = now - blocktimestamp print(('block :', current_block)) # print(('blocktime :', blocktime)) # print(('stamp :', blocktimestamp)) # print(('ctime(stamp) :', time.ctime(blocktimestamp))) # print(('now :', now)) print(('dex_rate latency :', ('%.2f' % latency))) return current_block, blocktimestamp, latency
class History(object): """This class contains an algorithm to figure out the block numbers in the blockchain that the user's dates refer to.""" def __init__(self): """ Initializes the History object. This method will be executed whenever we call an instance of the class.""" self.chain = Blockchain(mode='head') current_block_num = self.chain.get_current_block_num() # The upper bound block number self.upper = current_block_num # The lower bound block number self.lower = 1 def block_search(self, target_date): """ This call returns the block number corresponding to the date that was passed in. It uses a recursive loop that quickly searches for the block number by cutting the deck of block numbers in half every time and checking which half the desired date is in. The user is expected to pass in a date input through the user interface.""" upper = self.upper lower = self.lower mid = (upper + lower) / 2 while ((upper - mid) >= 2): if target_date > self.chain.block_time(int(mid)): lower = int(mid) mid = int((upper + lower) / 2) else: upper = int(mid) mid = int((upper + lower) / 2) return mid def fees_parser(self, start_date, end_date, csv_file="Untitled"): """ This parses the BitShares blockchain and aggregates historical fee data by type. The user is expected to input start and end dates on the user interface, which will be passed into this method. The dates need to be in datetime format.""" # This will pass in the start date and retrieve the block number for the first block to parse begin = self.block_search(start_date) # This will pass in the end date and retrieve the block number for # the last block to parse. As we want to fully capture the transactions # of the last day, we will pass in the next day's date and stop at the block just prior. stop = self.block_search(end_date + timedelta(days=1)) - 1 # List to temporarily hold the dictionaries until we store them in a dataframe storage = [] # We will iterate through the blocks and store relevant block information in a dictionary for blocknum in range(begin, stop + 1): # Dictionary to store block information block_data = dict() # To retrieve the blocks from the blockchain block = shared_bitshares_instance().rpc.get_block(blocknum) # Record the dates ts = pd.Timestamp(block["timestamp"]) block_data["Date"] = datetime.date(ts) # Iterating through the data within each block for tx in block["transactions"]: for op in tx["operations"]: key = getOperationNameForId(op[0]) # If the fee was paid in BTS, add the fee amount to the running total for each operation type if op[1]["fee"].get("asset_id") == "1.3.0": block_data[key] = block_data.get( key, 0) + op[1]["fee"].get("amount") # Append the dictionaries to the list for each block so that the data won't be lost storage.append(block_data) # Creating a dataframe to store the fee information data = pd.DataFrame(storage) data.fillna(0, inplace=True) # Aggregating at the daily level daily = data.groupby("Date") daily = daily.sum() daily.to_csv(str(csv_file) + ".csv")
class Testcases(unittest.TestCase): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.bts = BitShares( "wss://node.testnet.bitshares.eu", nobroadcast=True, ) self.bts.set_default_account("init0") set_shared_bitshares_instance(self.bts) self.chain = Blockchain(mode="head") def test_is_irv(self): self.assertFalse(self.chain.is_irreversible_mode()) def test_info(self): info = self.chain.info() for i in [ "time", "dynamic_flags", "head_block_id", "head_block_number", "last_budget_time" ]: self.assertIn(i, info) def test_parameters(self): info = self.chain.chainParameters() for i in [ "worker_budget_per_day", "maintenance_interval", ]: self.assertIn(i, info) def test_network(self): info = self.chain.get_network() for i in [ "chain_id", "core_symbol", "prefix", ]: self.assertIn(i, info) def test_props(self): info = self.chain.get_chain_properties() for i in [ "id", "chain_id", "immutable_parameters", ]: self.assertIn(i, info) def test_block_num(self): num = self.chain.get_current_block_num() self.assertTrue(num > 100) def test_block(self): block = self.chain.get_current_block() self.assertIsInstance(block, Block) self.chain.block_time(1) self.chain.block_timestamp(1) def test_list_accounts(self): for account in self.chain.get_all_accounts(): self.assertIsInstance(account, str) # Break already break