hyperledger-iroha/iroha-javascript

Error while registering a new peer

Closed this issue · 3 comments

I'm experiencing the following error when registering a new peer:

WARN run{listen_addr=irohaex:1394 public_key=ed0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0}:peer_connected{peer=ed0120F39DE80953F2E91569E34DC2C6BE803B2783CD613A643767B473E6CC6EB4A736@@172.18.0.2:53780 conn_id=0 disambiguator=16019490207021036163}: iroha_p2p::network: Peer not present in topology is trying to connect peer_id=ed0120F39DE80953F2E91569E34DC2C6BE803B2783CD613A643767B473E6CC6EB4A736@@172.18.0.2:53780 topology={PeerId { address: SocketAddrHost { host: "iroha0", port: 1337 }, public_key: {digest: ed25519, payload: ed0120BF2E355CAA62293889F48B159154B86C3F1F3F557D48E4761D6544898C9DCC9F} }: false, PeerId { address: SocketAddrHost { host: "irohaex", port: 1394 }, public_key: {digest: ed25519, payload: ed0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0} }: false}

Iroha node version:

INFO iroha: Hyperledgerいろは2にようこそ!(translation) Welcome to Hyperledger Iroha! version=2.0.0-pre-rc.20 git_commit_sha="ca37b7f"

Iroha JS packages:

    "@iroha2/client": "^7.0.0",
    "@iroha2/crypto-core": "^1.1.1",
    "@iroha2/crypto-target-bundler": "^1.1.1",
    "@iroha2/crypto-target-node": "^1.1.1",
    "@iroha2/crypto-target-web": "^1.1.1",
    "@iroha2/data-model": "^7.0.0",

I'm executing the registration using the following API call:

curl --location 'http://localhost:5001/api/iroha/peers/register/' \
--header 'Authorization: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJkYXRhIjp7InVzZXJpZCI6ImFkbWluIn0sImlhdCI6MTcwMzE2NzY3Mn0.chBzP4fM0amuNl5TgmQY6AX9nCKt6p5B4GrShY-4Dyc' \
--header 'Content-Type: application/json' \
--data '{
    "host": "irohaex",
    "port": 1394,
    "public_key": "ed0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0"
   
}'

This is the code being executed:

const registerPeer = async (host, port, payload) => {
  logger.info(`[srv] registerPeer ${host}:${port}...`);

  const {
    IdentifiableBox,
    Peer,
    PeerId,
    PublicKey,
    Algorithm,
    SocketAddr,
    SocketAddrHost,
  } = datamodel;

  const public_key = PublicKey({
    digest_function: Algorithm('Ed25519'),
    payload: Uint8Array.from(Buffer.from(payload, 'hex')),
  });

  const peerId = PeerId({
    address: SocketAddr('Host', SocketAddrHost({ host, port })),
    public_key,
  });

  const identifiableBox = IdentifiableBox('Peer', Peer({ id: peerId }));

  const reg = sugar.instruction.register(identifiableBox);
  const instr = sugar.executable.instructions(reg);

  const { pre, client } = clientFactory();
  try {
    const data = await client.submitExecutable(pre, instr);

    logger.info(`[srv] registerPeer ${host}:${port} completed ...`);
    return {
      data,
    };
  } catch (error) {
    logger.error(error);
    return { error: error.message };
  }
};

This is the topology stated on the error message above:

{
  PeerId{
    address: SocketAddrHost{
      host: "iroha1",
      port: 1338
    },
    public_key: {
      digest: ed25519,
      payload: ed01207060D33AF44FDD003452F04CD45F19F64FE926C252DAD6CC9F956261B0E4198A
    }
  }: false,
  PeerId{
    address: SocketAddrHost{
      host: "iroha2",
      port: 1339
    },
    public_key: {
      digest: ed25519,
      payload: ed01209BE75F396F87CCF61E4245F7121B1AFA37A01D40D33E2AD5F921FE9C3A0B995C
    }
  }: true,
  PeerId{
    address: SocketAddrHost{
      host: "iroha0",
      port: 1337
    },
    public_key: {
      digest: ed25519,
      payload: ed0120BF2E355CAA62293889F48B159154B86C3F1F3F557D48E4761D6544898C9DCC9F
    }
  }: false,
  PeerId{
    address: SocketAddrHost{
      host: "iroha3",
      port: 1340
    },
    public_key: {
      digest: ed25519,
      payload: ed0120F39DE80953F2E91569E34DC2C6BE803B2783CD613A643767B473E6CC6EB4A736
    }
  }: false,
  PeerId{
    address: SocketAddrHost{
      host: "irohaex",
      port: 1394
    },
    public_key: {
      digest: ed25519,
      payload: ed0123ED0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0
    }
  }: true
}

The public key for the node being registered is:

ed0123ED0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0

But that is wrong, it you compare it to the public key used in the API call:

ed0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0

For some reason Iroha is adding "ed123" and turning ed into caps, here is what i mean:

original key:        ed0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0
proccesed key: ed0123ED0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0

Why is Iroha altering the public key? Should it be encoded in a different way when submitting the instruction?

This problem occurs only when submitting via SDK. If I replicate the operation using iroha_client_cli as below, it works fine, and the peer is registered.

iroha_client_cli -c /Users/salimbene/dev/iroha2/files/config-local-adm.json peer register \
    --address irohaex:1394 \
    --key ed0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0

Hello Matias,

I guess the issue is with this code:

const public_key = PublicKey({
    digest_function: Algorithm('Ed25519'),
    payload: Uint8Array.from(Buffer.from(payload, 'hex')),
});

The issue is that your payload is not a payload, but a complete public key in multihash format. Therefore, when you create datamodel.PublicKey, you add again multihash prefix, resulting in duplication.

To handle this in the most proper way, let the crypto library handle the multihash:

import { crypto } from '@iroha2/crypto-target-node'
import { freeScope } from '@iroha2/crypto-core'

const public_key_hex = 'ed0120C69B431324D855E945B64F8DD757BDB5ED10C915C9C33ED6C1B36E06B97046F0'

const public_key = freeScope(() => crypto.PublicKey.fromMultihash(public_key_hex).toDataModel())

@0x009922 Thanks, that makes sense. I tested your solution and it did work with a minor fix.

I needed to add "hex" to fromMultiHash like so:

const public_key = freeScope(() => crypto.PublicKey.fromMultihash('hex', public_key_hex).toDataModel())

Thanks!!

Ah, yes, indeed. Glad it's fixed!