Esempio n. 1
0
    def do_test_recompress_storage(self, *, archive: bool) -> None:
        self.nodes = sanity.rpc_tx_status.start_cluster(archive=archive)

        # Give the network some time to generate a few blocks.  The same goes
        # for other sleeps in this method.
        time.sleep(5)

        # Execute a few transactions
        sanity.rpc_tx_status.test_tx_status(self.nodes)
        time.sleep(5)

        # Recompress storage on each node
        for idx, node in enumerate(self.nodes):
            logger.info(f'Stopping node{idx}')
            node.kill(gentle=True)

            node_dir = pathlib.Path(node.node_dir)
            self._call(node, 'recompress-storage',
                       '--output-dir=' + str(node_dir / 'data-new'))
            (node_dir / 'data').rename(node_dir / 'data-old')
            (node_dir / 'data-new').rename(node_dir / 'data')

            cmd = self._call(node, 'view-state', 'apply-range',
                             '--start-index=0', '--verbose-output')

        # Restart all nodes with the new database
        for idx, node in enumerate(self.nodes):
            logger.info(f'Starting node{idx}')
            node.start()

        # Execute a few more transactions
        time.sleep(5)
        sanity.rpc_tx_status.test_tx_status(self.nodes, nonce_offset=3)
Esempio n. 2
0
def get_up_to(from_, to):
    global first_epoch_switch_height, last_epoch

    for height, hash_ in utils.poll_blocks(nodes[0],
                                           timeout=TIMEOUT,
                                           poll_interval=0.01):
        block = nodes[0].get_block(hash_)

        hash_to_height[hash_] = height
        height_to_hash[height] = hash_

        cur_epoch = block['result']['header']['epoch_id']

        hash_to_epoch[hash_] = cur_epoch
        hash_to_next_epoch[hash_] = block['result']['header']['next_epoch_id']

        if (first_epoch_switch_height is None and last_epoch is not None
                and last_epoch != cur_epoch):
            first_epoch_switch_height = height
        last_epoch = cur_epoch

        if height >= to:
            break

    for i in range(from_, to + 1):
        hash_ = height_to_hash[i]
        logger.info(
            f"{i} {hash_} {hash_to_epoch[hash_]} {hash_to_next_epoch[hash_]}")

        if len(epochs) == 0 or epochs[-1] != hash_to_epoch[hash_]:
            epochs.append(hash_to_epoch[hash_])
Esempio n. 3
0
def get_metrics(node_name: str,
                node: cluster.BootNode) -> typing.Dict[str, int]:
    """Fetches partial encoded chunk request count metrics from node.

    Args:
        node_name: Node’s name used when logging the counters.  This is purely
            for debugging.
        node: Node to fetch metrics from.

    Returns:
        A `{key: count}` dictionary where key is in ‘method/success’ format.
        The values correspond to the
        near_partial_encoded_chunk_request_processing_time_count Prometheus
        metric.
    """
    url = 'http://{}:{}/metrics'.format(*node.rpc_addr())
    response = requests.get(url)
    response.raise_for_status()

    metric_name = 'near_partial_encoded_chunk_request_processing_time'
    histogram = next(
        (metric
         for metric in prometheus_client.parser.text_string_to_metric_families(
             response.content.decode('utf8')) if metric.name == metric_name),
        None)
    if not histogram:
        return {}

    counts = dict((sample.labels['method'] + '/' + sample.labels['success'],
                   int(sample.value)) for sample in histogram.samples
                  if sample.name.endswith('_count'))
    logger.info(f'{node_name} counters: ' +
                '; '.join(f'{key}: {count}'
                          for key, count in sorted(counts.items())))
    return counts
Esempio n. 4
0
def do_moar_stakes(last_block_hash, update_expected):
    global next_nonce, all_stakes, fake_stakes, sequence

    if len(sequence) == 0:
        stakes = [0, 0, 0]
        # have 1-2 validators with stake, and the remaining without
        # make numbers dibisable by 1M so that we can easily distinguish a situation when the current locked amt has some reward added to it (not divisable by 1M) vs not (divisable by 1M)
        stakes[random.randint(0, 2)] = random.randint(
            70000000000000000000000000, 100000000000000000000000000) * 1000000
        stakes[random.randint(0, 2)] = random.randint(
            70000000000000000000000000, 100000000000000000000000000) * 1000000
    else:
        stakes = sequence[0]
        sequence = sequence[1:]

    vals = get_validators()
    val_id = int(list(vals)[0][4:])
    for i in range(3):
        tx = sign_staking_tx(nodes[i].signer_key, nodes[i].validator_key,
                             stakes[i], next_nonce,
                             base58.b58decode(last_block_hash.encode('utf8')))
        nodes[val_id].send_tx(tx)
        next_nonce += 1

    if update_expected:
        fake_stakes = [0, 0, 0]
        all_stakes.append(stakes)
    else:
        fake_stakes = stakes

    logger.info("Sent %s staking txs: %s" %
                ("REAL" if update_expected else "fake", stakes))
Esempio n. 5
0
 def __init__(self,
              key,
              init_nonce,
              base_block_hash,
              rpc_info=None,
              rpc_infos=None):
     """
     `rpc_info` takes precedence over `rpc_infos` for compatibility. One of them must be set.
     If `rpc_info` is set, only this RPC node will be contacted.
     Otherwise if `rpc_infos` is set, an RPC node will be selected randomly
     from that set for each transaction attempt.
     """
     self.key = key
     self.nonce = init_nonce
     self.base_block_hash = base_block_hash
     assert rpc_info or rpc_infos
     if rpc_info:
         assert not rpc_infos
         rpc_infos = [rpc_info]
     self.rpc_infos = rpc_infos
     assert key.account_id
     self.tx_timestamps = []
     logger.info(
         f'Creating Account {key.account_id} {init_nonce} {self.rpc_infos[0]} {key.pk} {key.sk}'
     )
Esempio n. 6
0
def start_node(node):
    m = node.machine
    logger.info(f'INFO: Starting node {m.name}')
    pid = get_near_pid(m)
    if pid == '':
        start_process = m.run('sudo -u ubuntu -i', input=TMUX_START_SCRIPT)
        assert start_process.returncode == 0, m.name + '\n' + start_process.stderr
def init_token2_account(account, i):
    s = f'{{"account_id": "{account.key.account_id}"}}'
    tx_res = mocknet_helpers.retry_and_ignore_errors(
        lambda: account.send_call_contract_raw_tx(
            mocknet.TOKEN2_ACCOUNT, 'storage_deposit', bytes(s,
                                                             encoding='utf-8'),
            1250000000000000000000))  # 0.00125 * 1e24)
    logger.info(f'Account {account.key.account_id} storage_deposit {tx_res}')

    s = f'{{"token_account_id": "{mocknet.TOKEN2_ACCOUNT}"}}'
    logger.info(
        f'Calling function "register_token" with arguments {s} on account {i}')
    tx_res = mocknet_helpers.retry_and_ignore_errors(
        lambda: account.
        send_call_contract_raw_tx(mocknet.SKYWARD_ACCOUNT, 'register_token',
                                  bytes(s, encoding='utf-8'), 0.01 * 1e24))
    logger.info(
        f'Account {account.key.account_id} register_token token2 {tx_res}')

    # The next transaction depends on the previous transaction succeeded.
    # Sleeping for 1 second is the poor man's solution for waiting for that transaction to succeed.
    # This works because the contracts are being deployed slow enough to keep block production above 1 bps.
    mocknet_helpers.wait_at_least_one_block()

    s = f'{{"receiver_id": "{account.key.account_id}", "amount": "1000000000000000000"}}'
    logger.info(
        f'Calling function "ft_transfer" with arguments {s} on account {i}')
    tx_res = mocknet_helpers.retry_and_ignore_errors(
        get_token2_owner_account().send_call_contract_raw_tx(
            mocknet.TOKEN2_ACCOUNT, 'ft_transfer', bytes(s, encoding='utf-8'),
            1))
    logger.info(
        f'{get_token2_owner_account().key.account_id} ft_transfer to {account.key.account_id} {tx_res}'
    )
Esempio n. 8
0
def check_slow_blocks(initial_metrics, final_metrics):
    delta = Metrics.diff(final_metrics, initial_metrics)
    slow_process_blocks = delta.block_processing_time[
        'le +Inf'] - delta.block_processing_time['le 1']
    logger.info(
        f'Number of blocks processing for more than 1s: {slow_process_blocks}')
    return slow_process_blocks == 0
Esempio n. 9
0
def get_test_accounts_from_args(argv):
    node_account_id = argv[1]
    pk = argv[2]
    sk = argv[3]
    rpc_nodes = argv[4].split(',')
    num_nodes = int(argv[5])
    max_tps = float(argv[6])
    logger.info(f'rpc_nodes: {rpc_nodes}')

    node_account_key = key.Key(node_account_id, pk, sk)
    test_account_keys = [
        key.Key(mocknet.load_testing_account_id(node_account_id, i), pk, sk)
        for i in range(mocknet.NUM_ACCOUNTS)
    ]

    base_block_hash = mocknet_helpers.get_latest_block_hash()

    rpc_infos = [(rpc_addr, mocknet_helpers.RPC_PORT) for rpc_addr in rpc_nodes]
    node_account = account.Account(node_account_key,
                                   mocknet_helpers.get_nonce_for_pk(
                                       node_account_key.account_id,
                                       node_account_key.pk),
                                   base_block_hash,
                                   rpc_infos=rpc_infos)
    accounts = [
        account.Account(key,
                        mocknet_helpers.get_nonce_for_pk(
                            key.account_id, key.pk),
                        base_block_hash,
                        rpc_infos=rpc_infos) for key in test_account_keys
    ]
    max_tps_per_node = max_tps / num_nodes
    return node_account, accounts, max_tps_per_node
Esempio n. 10
0
 def send_moar_txs(self, last_block_hash, num, use_routing):
     last_balances = [x for x in self.expected_balances]
     for i in range(num):
         while True:
             from_ = random.randint(0, self.num_nodes - 1)
             if self.nodes[from_] is not None:
                 break
         to = random.randint(0, self.num_nodes - 2)
         if to >= from_:
             to += 1
         amt = random.randint(0, 500)
         if self.expected_balances[from_] >= amt:
             logger.info("Sending a tx from %s to %s for %s" %
                         (from_, to, amt))
             tx = sign_payment_tx(
                 self.nodes[from_].signer_key, 'test%s' % to, amt,
                 self.next_nonce,
                 base58.b58decode(last_block_hash.encode('utf8')))
             if use_routing:
                 self.nodes[0].send_tx(tx)
             else:
                 self.nodes[self.act_to_val[from_]].send_tx(tx)
             self.expected_balances[from_] -= amt
             self.expected_balances[to] += amt
             self.next_nonce += 1
Esempio n. 11
0
def collect_gcloud_config(num_nodes):
    tempdir = get_near_tempdir()
    keys = []
    for i in range(num_nodes):
        node_dir = tempdir / f'node{i}'
        if not node_dir.exists():
            # TODO: avoid hardcoding the username
            logger.info(f'downloading node{i} config from gcloud')
            node_dir.mkdir(parents=True, exist_ok=True)
            host = gcloud.get(f'pytest-node-{user_name()}-{i}')
            for filename in ('config.json', 'signer0_key.json',
                             'validator_key.json', 'node_key.json'):
                host.download(f'/home/bowen_nearprotocol_com/.near/{filename}',
                              str(node_dir))
        with open(node_dir / 'signer0_key.json') as f:
            key = json.load(f)
        keys.append(key)
    with open(tempdir / 'node0' / 'config.json') as f:
        config = json.load(f)
    ip_addresses = map(lambda x: x.split('@')[-1],
                       config['network']['boot_nodes'].split(','))
    res = {
        'nodes':
        list(map(lambda x: {
            'ip': x.split(':')[0],
            'port': 3030
        }, ip_addresses)),
        'accounts':
        keys
    }
    outfile = tempdir / 'gcloud_config.json'
    with open(outfile, 'w') as f:
        json.dump(res, f)
    os.environ[cluster.CONFIG_ENV_VAR] = str(outfile)
Esempio n. 12
0
def __download_binary(release: str, deploy: str) -> Executables:
    """Download binary for given release and deploy."""
    logger.info(f'Getting neard for {release}@{_UNAME} (deploy={deploy})')
    neard = _OUT_DIR / f'neard-{release}-{deploy}'
    basehref = f'{_BASEHREF}/nearcore/{_UNAME}/{release}/{deploy}'
    __download_file_if_missing(neard, f'{basehref}/neard')
    return Executables(_OUT_DIR, neard)
Esempio n. 13
0
def start_node(node, upgrade_schedule=None):
    m = node.machine
    logger.info(f'Starting node {m.name}')
    attempt = 0
    success = False
    while attempt < 3:
        pid = get_near_pid(m)
        if pid != '':
            success = True
            break
        start_process = m.run('sudo -u ubuntu -i',
                              input=neard_start_script(
                                  node,
                                  upgrade_schedule=upgrade_schedule,
                                  epoch_height=0))
        if start_process.returncode == 0:
            success = True
            break
        logger.warn(
            f'Failed to start process, returncode: {start_process.returncode}\n{node.instance_name}\n{start_process.stderr}'
        )
        attempt += 1
        time.sleep(1)
    if not success:
        raise Exception(f'Could not start node {node.instance_name}')
Esempio n. 14
0
    def __get_transaction(self) -> typing.Tuple[JsonDict, JsonDict]:
        """Fetches transaction and its block from the node if not yet retrieved.

        Returns:
            (block, transaction) tuple where first element is Rosetta Block
            object and second Rosetta Transaction object.
        """
        if self.__block and self.__transaction:
            return self.__block, self.__transaction
        timeout = time.monotonic() + 10
        while time.monotonic() < timeout:
            while True:
                try:
                    block = self._rpc.get_block(block_id=self._block_id)
                except RuntimeError:
                    block = None
                if not block:
                    break
                for tx in block['transactions']:
                    if tx['transaction_identifier']['hash'] == self.hash:
                        related = ', '.join(
                            related['transaction_identifier']['hash']
                            for related in tx.get('related_transactions',
                                                  ())) or 'none'
                        logger.info(f'Receipts of {self.hash}: {related}')
                        self.__memoised = (block, tx)
                        return self.__memoised
                self._block_id = int(block['block_identifier']['index']) + 1
            time.sleep(0.25)
        assert False, f'Transaction {self.hash} did not complete in 10 seconds'
Esempio n. 15
0
def transfer_between_nodes(nodes):
    logger.info('Testing transfer between mocknet validators')
    node = nodes[0]
    alice = get_validator_account(nodes[1])
    bob = get_validator_account(nodes[0])
    transfer_amount = 100
    get_balance = lambda account: int(
        node.get_account(account.account_id)['result']['amount'])

    alice_initial_balance = get_balance(alice)
    alice_nonce = node.get_nonce_for_pk(alice.account_id, alice.pk)
    bob_initial_balance = get_balance(bob)
    logger.info(f'Alice initial balance: {alice_initial_balance}')
    logger.info(f'Bob initial balance: {bob_initial_balance}')

    last_block_hash = node.get_latest_block().hash_bytes

    tx, tx_hash = sign_payment_tx_and_get_hash(alice, bob.account_id,
                                               transfer_amount,
                                               alice_nonce + 1,
                                               last_block_hash)
    send_transaction(node, tx, tx_hash, alice.account_id)

    alice_final_balance = get_balance(alice)
    bob_final_balance = get_balance(bob)
    logger.info(f'Alice final balance: {alice_final_balance}')
    logger.info(f'Bob final balance: {bob_final_balance}')

    # Check mod 1000 to ignore the cost of the transaction itself
    assert (alice_initial_balance -
            alice_final_balance) % 1000 == transfer_amount
    assert bob_final_balance - bob_initial_balance == transfer_amount
Esempio n. 16
0
def stop_node(node):
    m = node.machine
    logger.info(f'Stopping node {m.name}')
    pid = get_near_pid(m)
    if pid != '':
        m.run('bash', input=kill_proccess_script(pid))
        m.run('sudo -u ubuntu -i', input=TMUX_STOP_SCRIPT)
Esempio n. 17
0
def compute_seats(stakes, num_block_producer_seats):
    max_stake = 0
    for i in stakes:
        max_stake = max(max_stake, i[0])

    # Compute seats assignment.
    l = 0
    r = max_stake + 1
    seat_price = -1
    while r - l > 1:
        tmp_seat_price = (l + r) // 2
        num_seats = 0
        for i in range(len(stakes)):
            num_seats += stakes[i][0] // tmp_seat_price
        if num_seats <= num_block_producer_seats:
            r = tmp_seat_price
        else:
            l = tmp_seat_price
    seat_price = r
    logger.info(f'compute_seats seat_price: {seat_price}')

    seats = []
    for stake, item in stakes:
        seats.append((stake // seat_price, stake, item))
    seats.sort(reverse=True)
    return seats
Esempio n. 18
0
def get_up_to(from_, to):
    global hash_to_height, hash_to_epoch, hash_to_next_epoch, height_to_hash, epochs, first_epoch_switch_height, last_epoch

    while True:
        assert time.time() - started < TIMEOUT

        status = nodes[0].get_status()
        height = status['sync_info']['latest_block_height']
        hash_ = status['sync_info']['latest_block_hash']

        block = nodes[0].get_block(hash_)

        hash_to_height[hash_] = height
        height_to_hash[height] = hash_

        cur_epoch = block['result']['header']['epoch_id']

        hash_to_epoch[hash_] = cur_epoch
        hash_to_next_epoch[hash_] = block['result']['header']['next_epoch_id']

        if first_epoch_switch_height is None and last_epoch is not None and last_epoch != cur_epoch:
            first_epoch_switch_height = height
        last_epoch = cur_epoch

        if height >= to:
            break

    for i in range(from_, to + 1):
        hash_ = height_to_hash[i]
        logger.info(
            f"{i} {hash_} {hash_to_epoch[hash_]} {hash_to_next_epoch[hash_]}")

        if len(epochs) == 0 or epochs[-1] != hash_to_epoch[hash_]:
            epochs.append(hash_to_epoch[hash_])
Esempio n. 19
0
    def start(self, *, boot_node: BootNode = None, skip_starting_proxy=False):
        if self._proxy_local_stopped is not None:
            while self._proxy_local_stopped.value != 2:
                logger.info(f'Waiting for previous proxy instance to close')
                time.sleep(1)

        env = os.environ.copy()
        env["RUST_BACKTRACE"] = "1"
        env["RUST_LOG"] = "actix_web=warn,mio=warn,tokio_util=warn,actix_server=warn,actix_http=warn," + env.get(
            "RUST_LOG", "debug")

        cmd = self._get_command_line(self.near_root, self.node_dir, boot_node,
                                     self.binary_name)
        node_dir = pathlib.Path(self.node_dir)
        self.stdout_name = node_dir / 'stdout'
        self.stderr_name = node_dir / 'stderr'
        with open(self.stdout_name, 'ab') as stdout, \
             open(self.stderr_name, 'ab') as stderr:
            self._process = subprocess.Popen(cmd,
                                             stdin=subprocess.DEVNULL,
                                             stdout=stdout,
                                             stderr=stderr,
                                             env=env)
        self._pid = self._process.pid

        if not skip_starting_proxy:
            self.start_proxy_if_needed()

        try:
            self.wait_for_rpc(10)
        except:
            logger.error(
                '=== failed to start node, rpc does not ready in 10 seconds')
Esempio n. 20
0
 def wrapper(stopped, error, *args):
     try:
         func(stopped, error, *args)
     except Exception as e:
         traceback.print_exc()
         logger.info(f"Process {func.__name__} failed with {repr(e)}")
         error.value = 1
Esempio n. 21
0
async def main():
    key_pair_0 = nacl.signing.SigningKey(key_seed())
    tracker = LogTracker(nodes[0])
    conn = await connect(nodes[0].addr())
    await run_handshake(conn, nodes[0].node_key.pk, key_pair_0, listen_port=12345)

    num_nodes = 300

    def create_update():
        key_pairs = [key_pair_0] +  [nacl.signing.SigningKey(key_seed()) for _ in range(num_nodes - 1)]
        nonces = [[1] * num_nodes for _ in range(num_nodes)]

        edges = []
        for i in range(num_nodes):
            for j in range(i):
                edge = create_edge(key_pairs[i], key_pairs[j], nonces[i][j])
                edges.append(edge)
        return create_sync_data(edges=edges)

    asyncio.get_event_loop().create_task(consume(conn))

    for i in range(3):
        update = create_update()
        logger.info("Sending update...")
        await conn.send(update)
        logger.info("Sent...")
        await asyncio.sleep(1)

    assert tracker.check("delay_detector: LONG DELAY!") is False
Esempio n. 22
0
 async def handle(self, msg, fr, to):
     if msg.enum == 'Block':
         h = msg.Block.BlockV2.header.inner_lite().height
         logger.info(f"Height: {h}")
         if h >= 10:
             logger.info('SUCCESS')
             success.value = 1
     return True
Esempio n. 23
0
def poll_blocks(node: cluster.LocalNode,
                *,
                timeout: float = 120,
                poll_interval: float = 0.25,
                __target: typing.Optional[int] = None,
                **kw) -> typing.Iterable[cluster.BlockId]:
    """Polls a node about the latest block and yields it when it changes.

    The function continues yielding blocks indefinitely (so long as the node
    continues reporting its status) until timeout is reached or the caller stops
    reading yielded values.  Reaching the timeout is considered to be a failure
    condition and thus it results in an `AssertionError`.  The expected usage is
    that caller reads blocks until some condition is met at which point it stops
    iterating over the generator.

    Args:
        node: Node to query about its latest block.
        timeout: Total timeout from the first status request sent to the node.
        poll_interval: How long to wait in seconds between each status request
            sent to the node.
        kw: Keyword arguments passed to `BaseDone.get_latest_block` method.
    Yields:
        A `cluster.BlockId` object for each each time node’s latest block
        changes including the first block when function starts.  Note that there
        is no guarantee that there will be no skipped blocks.
    Raises:
        AssertionError: If more than `timeout` seconds passes from the start of
            the iteration.
    """
    end = time.monotonic() + timeout
    start_height = -1
    count = 0
    previous = -1

    while time.monotonic() < end:
        latest = node.get_latest_block(**kw)
        if latest.height != previous:
            if __target:
                msg = f'{latest}  (waiting for #{__target})'
            else:
                msg = str(latest)
            logger.info(msg)
            yield latest
            previous = latest.height
            if start_height == -1:
                start_height = latest.height
            count += 1
        time.sleep(poll_interval)

    msg = 'Timed out polling blocks from a node\n'
    if count > 0:
        msg += (f'First block: {start_height}; last block: {previous}\n'
                f'Total blocks returned: {count}')
    else:
        msg += 'No blocks were returned'
    if __target:
        msg += f'\nWaiting for block: {__target}'
    raise AssertionError(msg)
Esempio n. 24
0
def main():
    nodes = []

    # Build the container
    run(('make', 'DOCKER_TAG=' + _DOCKER_IMAGE_TAG, 'docker-nearcore'))
    try:
        dot_near = pathlib.Path.home() / '.near'

        # Initialise local network
        cmd = f'neard --home /home/near localnet --v {NUM_NODES} --prefix test'
        docker_run(cmd, volume=(dot_near, '/home/near'))

        # Start all the nodes
        for ordinal in range(NUM_NODES):
            logger.info(f'Starting node {ordinal}')
            node = DockerNode(ordinal, dot_near / f'test{ordinal}')
            node.start(boot_node=nodes)
            nodes.append(node)

        # Wait for them to initialise
        for ordinal, node in enumerate(nodes):
            logger.info(f'Waiting for node {ordinal} to respond')
            node.wait_for_rpc(10)

        # Wait for BLOCKS blocks to be generated
        latest = utils.wait_for_blocks(nodes[0], target=BLOCKS)

        # Fetch latest block from all the nodes
        blocks = []
        for ordinal, node in enumerate(nodes):
            utils.wait_for_blocks(node, target=latest.height)
            response = node.get_block(latest.hash)
            assert 'result' in response, (ordinal, block)
            block = response['result']
            blocks.append(block)
            bid = cluster.BlockId.from_header(block['header'])
            logger.info(f'Node {ordinal} sees block: {bid}')

        # All blocks should be equal
        for ordinal in range(1, NUM_NODES):
            assert blocks[0] == blocks[ordinal], (ordinal, blocks)

        logger.info('All good')

    finally:
        # `docker stop` takes a few seconds so stop all containers in parallel.
        # atexit we’ll call DockerNode.cleanup method for each node as well and
        # it’ll handle all the other cleanups.
        cids = tuple(filter(None, (node._container_id for node in nodes)))
        if cids:
            logger.info('Stopping containers')
            run(('docker', 'stop') + cids)
        for node in nodes:
            node._container_id = None

        subprocess.check_call(
            ('docker', 'image', 'rm', '-f', _DOCKER_IMAGE_TAG))
Esempio n. 25
0
def process():
    for i in range(100):
        key = bytearray(8)
        key[0] = i % 10
        res = nodes[4].call_function(
            acc_id, 'read_value',
            base64.b64encode(bytes(key)).decode("ascii"))
        res = int.from_bytes(res["result"]["result"], byteorder='little')
        assert res == (i % 10)
    logger.info("all done")
Esempio n. 26
0
def random_transaction(account, i, node_account, max_tps_per_node):
    time.sleep(random.random() * mocknet.NUM_ACCOUNTS / max_tps_per_node / 3)
    choice = random.randint(0, 2)
    if choice == 0:
        logger.info(f'Account {i} transfers')
        send_transfer(account, node_account)
    elif choice == 1:
        function_call_set_delete_state(account, i, node_account)
    elif choice == 2:
        function_call_ft_transfer_call(account, i, node_account)
Esempio n. 27
0
 async def send_binary(self, raw_message, to, fr=None):
     writer = self.get_writer(to, fr)
     if writer is None:
         logger.info(
             f"Writer not known: to={to}, fr={fr}, send={self.send_to_map.keys()}, recv={self.recv_from_map.keys()}"
         )
     else:
         writer.write(struct.pack('I', len(raw_message)))
         writer.write(raw_message)
         await writer.drain()
Esempio n. 28
0
def one_process(ord_, seconds):
    started = time.time()
    sent = 0
    with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
        s.connect(nodes[0].addr())
        while time.time() - started < seconds:
            s.send(struct.pack('I', PACKAGE_LEN))
            s.send(buf)
            sent += PACKAGE_LEN
            logger.info("PROCESS %s SENT %s BYTES" % (ord_, sent))
Esempio n. 29
0
    async def _handle(self, raw_message, *, writer, sender_port_holder,
                      receiver_port_holder, ordinal_to_writer):
        sender_ordinal = port_holder_to_node_ord(sender_port_holder)
        receiver_ordinal = port_holder_to_node_ord(receiver_port_holder)
        try:
            message = BinarySerializer(schema).deserialize(
                raw_message, PeerMessage)
            assert BinarySerializer(schema).serialize(message) == raw_message

            if message.enum == 'Handshake':
                message.Handshake.listen_port += 100
                if sender_port_holder[0] is None:
                    sender_port_holder[0] = message.Handshake.listen_port

            other_ordinal = self.other(sender_ordinal, receiver_ordinal)

            if other_ordinal is not None and not other_ordinal in ordinal_to_writer:
                ordinal_to_writer[other_ordinal] = writer

            decision = await self.handle(message, sender_ordinal,
                                         receiver_ordinal)

            if decision is True and message.enum == 'Handshake':
                decision = message

            if not isinstance(decision, bool):
                decision = BinarySerializer(schema).serialize(decision)

            return decision
        except:
            # TODO: Remove this
            if raw_message[0] == 13:
                # raw_message[0] == 13 is RoutedMessage. Skip leading fields to get to the RoutedMessageBody
                ser = BinarySerializer(schema)
                ser.array = bytearray(raw_message)
                ser.offset = 1
                ser.deserialize_field(PeerIdOrHash)
                ser.deserialize_field(PublicKey)
                ser.deserialize_field(Signature)
                ser.deserialize_field('u8')

                # The next byte is the variant ordinal of the `RoutedMessageBody`.
                # Skip if it's the ordinal of a variant for which the schema is not ported yet
                if raw_message[ser.offset] in [3, 4, 5, 7]:
                    # Allow the handler determine if the message should be passed even when it couldn't be deserialized
                    return await self.handle(None, sender_ordinal,
                                             receiver_ordinal) is not False
                logger.info(f"ERROR 13 {int(raw_message[ser.offset])}")

            else:
                logger.info(f"ERROR {int(raw_message[0])}")

            raise

        return True
Esempio n. 30
0
def init_ft(node_account):
    tx_res = node_account.send_deploy_contract_tx(
        '/home/ubuntu/fungible_token.wasm')
    logger.info(f'ft deployment {tx_res}')
    mocknet_helpers.wait_at_least_one_block()

    s = f'{{"owner_id": "{node_account.key.account_id}", "total_supply": "{10**33}"}}'
    tx_res = node_account.send_call_contract_raw_tx(node_account.key.account_id,
                                                    'new_default_meta',
                                                    s.encode('utf-8'), 0)
    logger.info(f'ft new_default_meta {tx_res}')