Example #1
0
def parse_csv():
    data = []
    if args.csv is not None:
        with open(args.csv, 'r') as f:
            for row in csv.DictReader(f):
                raw_amount, raw_address = row['funded'].strip(
                ), row['validator address'].strip()
                if raw_address and raw_address.startswith(
                        'one1') and raw_amount:
                    sys.stdout.write(
                        f"\rLoading address: {raw_address} to funding candidate from CSV."
                    )
                    sys.stdout.flush()
                    try:
                        cli.single_call(
                            f"hmy utility bech32-to-addr {raw_address}")
                        data.append({
                            'amount':
                            float(raw_amount.replace(',', '')),
                            'address':
                            raw_address
                        })
                    except Exception as e:  # catch all to not halt script
                        print(
                            f"{util.Typgpy.FAIL}\nError when parsing CSV file (addr `{raw_address}`). {e}{util.Typgpy.ENDC}"
                        )
                        print(
                            f"{util.Typgpy.WARNING}Skipping...{util.Typgpy.ENDC}"
                        )
    return data
Example #2
0
def add_bls_key_to_validator(val_info, bls_pub_keys, passphrase, endpoint):
    print(f"{Typgpy.HEADER}{val_info['validator-addr']} already in list of validators!{Typgpy.ENDC}")
    chain_val_info = json_load(cli.single_call(f"hmy --node={endpoint} blockchain "
                                               f"validator information {val_info['validator-addr']}"))["result"]
    bls_keys = chain_val_info["validator"]["bls-public-keys"]
    directory_lock.acquire()
    for k in bls_pub_keys:
        if k not in bls_keys:  # Add imported BLS key to existing validator if needed
            print(f"{Typgpy.OKBLUE}adding bls key: {k} "
                  f"to validator: {val_info['validator-addr']}{Typgpy.ENDC}")
            os.chdir("/root/bin")
            proc = cli.expect_call(f"hmy --node={endpoint} staking edit-validator "
                                   f"--validator-addr {val_info['validator-addr']} "
                                   f"--add-bls-key {k} --passphrase-file /.wallet_passphrase ")
            proc.expect("Enter the bls passphrase:\r\n")
            proc.sendline(passphrase)
            proc.expect(pexpect.EOF)
            print(f"\n{Typgpy.OKBLUE}Edit-validator transaction response: "
                  f"{Typgpy.OKGREEN}{proc.before.decode()}{Typgpy.ENDC}")
    directory_lock.release()
    new_val_info = json_load(cli.single_call(f"hmy --node={endpoint} blockchain "
                                             f"validator information {val_info['validator-addr']}"))["result"]
    new_bls_keys = new_val_info["validator"]["bls-public-keys"]
    print(f"{Typgpy.OKBLUE}{val_info['validator-addr']} updated bls keys: {new_bls_keys}{Typgpy.ENDC}")
    verify_node_sync(endpoint)
    print()
Example #3
0
 def load(start, end):
     for j, file_name in enumerate(key_paths[start:end]):
         # STRONG assumption about imported key-files.
         if file_name.endswith(".key") or not file_name.startswith("."):
             file_path = f"{keystore_path}/{file_name}"
             account_name = f"{import_account_name_prefix}{name_prefix}{j + start}"
             if not cli.get_address(account_name):
                 cli.remove_account(
                     account_name
                 )  # Just in-case there is a folder with nothing in it.
                 Loggers.general.info(
                     f"Adding key file: ({j + start}) {file_name}")
                 if fast_load:
                     keystore_acc_dir = f"{cli.get_account_keystore_path()}/{account_name}"
                     os.makedirs(keystore_acc_dir, exist_ok=True)
                     shutil.copy(file_path,
                                 f"{keystore_acc_dir}/{file_name}")
                 else:
                     cli.single_call(
                         f"hmy keys import-ks {file_path} {account_name} "
                         f"--passphrase={passphrase}")
             _loaded_passphrase[account_name] = passphrase
             accounts_added.append(account_name)
             _accounts_added.add(account_name)
             account_balances[account_name] = get_balances(account_name)
Example #4
0
def test_update_keystore():
    cli.single_call("hmy keys add test1")
    addrs = cli.get_accounts_keystore()
    assert "test1" in addrs.keys()
    check_addr = addrs["test1"]
    accounts_list = cli.get_accounts(check_addr)
    check_acc = accounts_list[0]
    assert check_acc == "test1"
    raw_cli_keys_list_print = cli.single_call("hmy keys list", timeout=2)
    assert check_addr in raw_cli_keys_list_print
    assert check_acc in raw_cli_keys_list_print
    assert addrs[check_acc] == check_addr
    cli.remove_address(check_addr)
    assert check_addr not in addrs.values()
    assert "test1" not in addrs.keys()
Example #5
0
def create_account(account_name, exist_ok=True):
    """
    This will create a single account with `account_name`. One can choose to continue
    if the account exists by setting `exist_ok` to true.
    """
    # TODO: add caching
    try:
        cli.single_call(f"hmy keys add {account_name}")
    except RuntimeError as e:
        if not exist_ok:
            raise e
    get_balances(account_name)
    _accounts_added.add(account_name)
    _loaded_passphrase[
        account_name] = ''  # Default passphrase used by the CLI.
    return account_name
Example #6
0
def save_log():
    fund_log["block-height"] = json.loads(
        cli.single_call(
            f"hmy blockchain "
            f"latest-header -n {endpoints[0]}"))["result"]["blockNumber"]
    log_dir = f"{os.path.dirname(os.path.realpath(__file__))}/logs/{os.environ['HMY_PROFILE']}"
    file = f"{log_dir}/funding.json"
    with open(file, 'w') as f:
        json.dump(fund_log, f, indent=4)
Example #7
0
def load_accounts():
    accs_info = []
    assert os.path.isfile(args.config), f"`{args.config}` is not a file"
    with open(args.config, 'r') as f:
        config = json.load(f)
    cli_dir = cli.get_account_keystore_path()
    for j, src_info in enumerate(config):
        sys.stdout.write(f"Key import progress: {j}/{len(config)}   \r")
        sys.stdout.flush()
        # Passphrase parsing
        if "passphrase-file-path" in src_info.keys():
            pw_path = src_info['passphrase-file-path']
            assert os.path.isfile(pw_path), f"`{pw_path}` is not a file."
            with open(pw_path, 'r') as f:
                passphrase = f.read().strip()
        elif "passphrase" in src_info.keys():
            passphrase = src_info['passphrase']
        else:
            passphrase = ''  # CLI default passphrase

        # Load key
        acc_name = f"{prefix}{j}"
        cli.remove_account(acc_name)
        if "keystore-file-path" in src_info.keys():
            ks_path = src_info['keystore-file-path']
            assert os.path.isfile(ks_path), f"`{ks_path}` is not a file."
            os.makedirs(f"{cli_dir}/{acc_name}")
            shutil.copy(ks_path, f"{cli_dir}/{acc_name}")
            address = cli.get_address(acc_name)
            if address is None:
                raise RuntimeError(f"Could not import key for config {j}")
            added_key_names.append(acc_name)
        elif "private-key" in src_info.keys():
            cli.single_call(
                f"hmy keys import-private-key {src_info['private-key']} {acc_name}"
            )
            address = cli.get_address(acc_name)
            if address is None:
                raise RuntimeError(f"Could not import key for config {j}")
        else:
            raise RuntimeError(f"No key to import for config {j}")

        accs_info.append({'address': address, 'passphrase': passphrase})
    return accs_info
 def transfer(self,
              from_address,
              to_address,
              amount,
              from_shard=0,
              to_shard=0):
     cli.set_binary(HmyClient._hmyBinaryDir)
     return cli.single_call(
         f'hmy transfer --node={HmyClient._networkUrl} --from {from_address} --to {to_address} --from-shard {from_shard} --to-shard {to_shard} --amount {amount}'
     )
Example #9
0
def load_log():
    global fund_log
    log_dir = f"{os.path.dirname(os.path.realpath(__file__))}/logs/{os.environ['HMY_PROFILE']}"
    file = f"{log_dir}/funding.json"
    if os.path.isfile(file):
        with open(file, 'r') as f:
            loaded_fund_log = json.load(f)
        curr_height = json.loads(
            cli.single_call(
                f"hmy blockchain "
                f"latest-header -n {endpoints[0]}"))["result"]["blockNumber"]
        if loaded_fund_log['block-height'] <= curr_height:
            fund_log = loaded_fund_log
Example #10
0
def get_balance_from_node_ip(address, endpoint_list):
    """
    Assumes that endpoints provided are ips and that the CLI
    only returns the balances for a specific shard.
    """
    balances = []
    for endpoint in endpoint_list:
        cli_bal = json.loads(
            cli.single_call(f"hmy --node={endpoint} balances {address}"))
        assert len(
            cli_bal
        ) == 1, f"Expect CLI to only return balances for 1 shard. Got: {cli_bal}"
        balances.append(cli_bal[0])
    return balances
Example #11
0
    def send(self, endpoint, wait_for_confirm=None, chain_id="testnet"):
        """
        This will send all transactions in the buffer of transaction **sequentially** using the CLI
        with the provided `endpoint` and `chain_id`. One can force EACH transaction to confirm by
        providing a max `wait_for_confirm` time.

        This will return a list of dictionaries that contain transaction information (and possibly errors)
        of all the transactions sent.
        """
        if wait_for_confirm:
            assert isinstance(wait_for_confirm, (int, float))

        if not self._transactions_buffer:
            return []

        with open(self._file_name, 'w') as f:
            json.dump(self._transactions_buffer, f, indent=4)

        command = f"hmy --node={endpoint} transfer --file {self._file_name} --chain-id {chain_id} "
        command += f"--timeout {wait_for_confirm} " if wait_for_confirm else f"--timeout 0 "
        timeout = None if self.size is None else get_config(
        )["TXN_WAIT_TO_CONFIRM"] * self.size
        response = json_load(
            cli.single_call(command, error_ok=True, timeout=timeout))

        for txn, sent_txn in zip(self._transactions_buffer, response):
            info = {  # Cast elements to fit transaction logger convention.
                'from': txn['from'], 'to': txn['to'],
                'from-shard': int(txn['from-shard']), 'to-shard': int(txn['to-shard']),
                'amount': float(txn['amount']),
                'txn-fee': round(float(txn['gas-price']) * 1e-9 * float(txn['gas-limit']), 18),
                'nonce': None, 'error': None, 'hash': None, 'send-time-utc': None,
            }
            if "nonce" in txn.keys():
                info['nonce'] = int(txn['nonce'])
            if "transaction-hash" in sent_txn.keys():
                info['hash'] = sent_txn['transaction-hash']
            if "errors" in sent_txn.keys():
                info['error'] = ', '.join(e for e in sent_txn['errors'])
            if "time-signed-utc" in sent_txn.keys():
                info['send-time-utc'] = sent_txn['time-signed-utc']
            info[
                'batched-extra-info'] = sent_txn  # Keep track of returned info just in case.
            Loggers.transaction.info(json.dumps(info))

        self._transactions_buffer.clear()
        return response
Example #12
0
def consolidate(shard):
    if shard >= len(endpoints):
        return
    transactions = []
    total_amt = 0
    overhead = Decimal(
        args.gas_price * args.gas_limit) * Decimal(1e-18) + Decimal(1e-18)
    max_amount = float('inf') if args.amount is None else Decimal(
        args.amount) + overhead
    print(
        f"{util.Typgpy.HEADER}Consolidating funds for shard {shard} ({len(accounts_info)} transaction(s)){util.Typgpy.ENDC}"
    )
    for acc in accounts_info:
        acc_bal = json.loads(
            cli.single_call(
                f"hmy --node={endpoints[shard]} balances {acc['address']}"))[0]
        assert acc_bal[
            "shard"] == shard, f"balance for shard {shard} does not match endpoint"
        amount = round(
            Decimal(min(acc_bal["amount"], max_amount)) - overhead, 18)
        total_amt += amount
        transactions.append({
            "from": acc['address'],
            "to": args.dest_address,
            "from-shard": str(shard),
            "to-shard": str(shard),
            "gas-price": str(args.gas_price),
            "gas-limit": str(args.gas_limit),
            "passphrase-string": acc['passphrase'],
            "amount": str(amount)
        })
    filename = f"./{prefix}fund{shard}.json"
    with open(filename, 'w') as f:
        json.dump(transactions, f, indent=4)
    command = f"hmy --node={endpoints[shard]} transfer --file {filename} --chain-id {chain_id} --timeout 0"
    print(
        f"{util.Typgpy.HEADER}Transaction for shard {shard}:\n{util.Typgpy.OKGREEN}"
        f"{cli.single_call(command, timeout=int(args.timeout) * len(endpoints) * len(accounts_info))}"
        f"{util.Typgpy.ENDC}")
    return total_amt
Example #13
0
def get_balances(account_name):
    """
    This gets the balances for the address associated with the `account_name`
    (aka wallet-name) in the CLI's keystore.
    """
    config = get_config()
    address = cli.get_address(account_name)
    if not address:
        return {}
    response = cli.single_call(
        f"hmy balances {address} --node={config['ENDPOINTS'][0]}", timeout=60)
    balances = eval(
        response
    )  # There is a chance that the CLI returns a malformed json array.
    info = {
        'address': address,
        'balances': balances,
        'time-utc': str(datetime.datetime.utcnow())
    }
    Loggers.balance.info(json.dumps(info))
    account_balances[account_name] = balances
    return balances
Example #14
0
def remove_accounts(accounts, backup=False):
    """
    This will remove all `accounts`, where `accounts` is an iterable of accounts name.
    One can specify `backup` if one wishes to log the private keys of all removed accounts.
    """
    for acc in accounts:
        address = cli.get_address(acc)
        private_key = ""
        if backup:
            try:
                private_key = cli.single_call(
                    f"hmy keys export-private-key {address}").strip()
            except RuntimeError:
                Loggers.general.error(
                    f"{address} ({acc}) was not imported via CLI, cannot backup"
                )
                private_key = "NOT-IMPORTED-USING-CLI"
        cli.remove_account(acc)
        if acc in _accounts_added:
            _accounts_added.remove(acc)
        if acc in _loaded_passphrase:
            del _loaded_passphrase[acc]
        removed_account = {"address": address, "private-key": private_key}
        Loggers.general.info(f"Removed Account: {removed_account}")
Example #15
0
def export_private_key(name):
    return cli.single_call(f"hmy keys export-private-key {cli.get_address(name)}")
Example #16
0
 def regiterNewUser(self, telegram_user_id):
     cli.set_binary(HmyClient._hmyBinaryDir)
     return cli.single_call(f'hmy keys add {telegram_user_id}')
Example #17
0
    item.split(".")[0] for item in os.listdir(
        "/root/go/src/github.com/harmony-one/harmony/.hmy/keystore")
]
for key in keys:
    balance = account.get_balance(key)
    print("There are %d one in %s" % (balance, key))

#current block number
cur_block_num = blockchain.get_block_number()

#get balance at certain block
account.get_balance_by_block(keys[-1], cur_block_num)

#get balance on all shards
account.get_balance_on_all_shards(keys[-1])

#restore keys[-1] from keystore by cli
cli.single_call(
    "hmy keys import-ks /root/go/src/github.com/harmony-one/harmony/.hmy/keystore/%s.key"
    % key)
balance_before = account.get_balance(keys[-1])

#send 2 one from keys[-1] to local_test_address
cli.single_call(
    "hmy transfer --from %s --to %s --amount %d --from-shard %s --to-shard %s"
    % (key, local_test_address, 2, 0, 0))
balance_after = account.get_balance(keys[-1])

diff = balance_before - balance_after
print("The difference between before and after is %d" % (diff))
Example #18
0
def load_from_priv_keys():
    for i, private_key in enumerate(import_keys):
        acc_name = f"LOAD_NET_IMPORTED_PRIVATE_{i}"
        cli.remove_account(acc_name)
        cli.single_call(f"hmy keys import-private-key {private_key} {acc_name}")
        tx_gen.account_balances[acc_name] = tx_gen.get_balances(acc_name)  # Manually update the tx_gen acc bal
Example #19
0
env = cli.download("./bin/test", replace=False)
cli.environment.update(env)
new_path = os.getcwd() + "/bin/test"
cli.set_binary(new_path)
print("The binary path is %s"%(cli.get_binary_path()))

#get a dict of account names
name_dict = cli.get_accounts_keystore()
print(name_dict)

#get keystore path
print("Your accounts are store in %s"%(cli.get_account_keystore_path()))

if "difeng" not in name_dict.keys():
    #create a user
    cli.single_call("hmy keys add difeng")
    print("difeng has been successfully created")

if "dfxx" not in name_dict.keys():
    #create a user
    cli.single_call("hmy keys add dfxx")
    print("dfxx has been successfully created")

if "test1" not in name_dict.keys():
    #create a user
    cli.single_call("hmy keys add test1")


#get address of account
difeng_address = cli.get_address("difeng")
dfxx_address = cli.get_address("dfxx")
Example #20
0
def check_min_bal_on_s0(address, amount, endpoint=default_endpoint):
    balances = json_load(cli.single_call(f"hmy --node={endpoint} balances {address}"))
    for bal in balances:
        if bal['shard'] == 0:
            return bal['amount'] >= amount