libp2p / js-libp2p-kad-dht

JavaScript implementation of the DHT for libp2p
https://libp2p.io
Other
141 stars 60 forks source link

Problem with DHT provide using bootstrap nodes #369

Closed amirtgm closed 1 year ago

amirtgm commented 2 years ago

in this code, with all the latest versions I'm trying to provide a simple object using DHT but with everything I tried it always throws Query Aborted.

the Goal I'm trying to achieve is providing a JSON or text with some information. and then from another peer searching for the same data and finding out who provided it and trying to dial to that node.

import { createLibp2p } from 'libp2p';
import { WebRTCStar } from '@libp2p/webrtc-star';
import { TCP } from '@libp2p/tcp';
import logger from 'loglevel';
import { fromString } from 'uint8arrays';

import { WebSockets } from '@libp2p/websockets';
import { Mplex } from '@libp2p/mplex';
import { Noise } from '@chainsafe/libp2p-noise';
import { CID } from 'multiformats/cid';
import multihashes from 'multihashes';
import * as Digest from 'multiformats/hashes/digest';
import { multiaddr } from 'multiaddr';

import { KadDHT } from '@libp2p/kad-dht';
import { Bootstrap } from '@libp2p/bootstrap';
import { DelegatedPeerRouting } from '@libp2p/delegated-peer-routing';
import { DelegatedContentRouting } from '@libp2p/delegated-content-routing';
import { create as ipfsHttpClient } from 'ipfs-http-client';

export async function createNode() {
  const node = await createLibp2p({
    addresses: {
      listen: ['/ip4/0.0.0.0/tcp/0'],
    },

    transports: [new WebSockets(), new TCP()],
    streamMuxers: [new Mplex()],
    connectionEncryption: [new Noise()],
    dht: new KadDHT(),
    connectionManager: {
      autoDial: true,
    },

    peerDiscovery: [
      new Bootstrap({
        list: [
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmNnooDu7bfjPFoTZYxMNLWUQJyrVwtbZg5gBMjTezGAJN',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmbLHAnMoJPWSCR5Zhtx6BHJX9KiKNN6tpvbUcqanj75Nb',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmZa1sAxajnQjVM8WjWXoMbmPd7NsWhfKsPkErzpm9wGkp',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmQCU2EcMqAqQPR2i9bChDtGNJchTbq5TbXJJ16u19uLTa',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmcZf59bWwK5XFi76CZX8cbJ4BhTzzA3gU1ZjYZcYW3dwt',
        ],
      }),
    ],
  });
  console.log('this node peerID', node.peerId.toString());
  node.connectionManager.addEventListener('peer:connect', ({ detail }) => {
    console.log('peer:connect', 'Connection established to:', detail.remotePeer.toString()); 
  });

  node.peerStore.addEventListener('change:multiaddrs', ({ detail: { peerId, multiaddrs } }) => {
    if (peerId.equals(node.peerId)) {
      console.log('address changes', multiaddrs.toString(), peerId.toString());
    }
  });
  return node;
}

(async () => {
  logger.setLevel('debug');
  const node = await createNode();
  await node.start();
  await setTimeout(async () => {
    const LIBP2P_KEY_CODE = 0x0200;
    const buff = JSON.stringify({
      title: 'asdasdas',
    });
    const datas = multihashes.encode(Buffer.from(buff), 'sha2-256');
    const cid = CID.createV1(LIBP2P_KEY_CODE, Digest.create(LIBP2P_KEY_CODE, datas));
    try {
      for await (const data of node.dht.provide(cid)) {
        console.log(data);
      }
    } catch (e) {
      console.log(e);
    }
  }, 10000);
})();
achingbrain commented 1 year ago

Could you provide the stack trace of the error you are seeing?

github-actions[bot] commented 1 year ago

Oops, seems like we needed more information for this issue, please comment with more details or this issue will be closed in 7 days.

achingbrain commented 1 year ago

I think the problem with the example is that CID being created is invalid as the digest content is a digest itself. It can also run the provide before the node has any peers.

I've updated the example to use the latest version of everything, construct the CID correctly and wait for at least one peer before running the provide and it works for me:

import { createLibp2p } from 'libp2p';
import { tcp } from '@libp2p/tcp';
import { mplex } from '@libp2p/mplex';
import { noise } from '@chainsafe/libp2p-noise';
import { CID } from 'multiformats/cid';
import { sha256 } from 'multiformats/hashes/sha2';
import { kadDHT } from '@libp2p/kad-dht';
import { bootstrap } from '@libp2p/bootstrap';
import { encode, code as DAG_JSON_CODEC } from '@ipld/dag-json'

export async function createNode() {
  const node = await createLibp2p({
    addresses: {
      listen: ['/ip4/0.0.0.0/tcp/0'],
    },

    transports: [tcp()],
    streamMuxers: [mplex()],
    connectionEncryption: [noise()],
    dht: kadDHT(),

    peerDiscovery: [
      bootstrap({
        list: [
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmNnooDu7bfjPFoTZYxMNLWUQJyrVwtbZg5gBMjTezGAJN',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmbLHAnMoJPWSCR5Zhtx6BHJX9KiKNN6tpvbUcqanj75Nb',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmZa1sAxajnQjVM8WjWXoMbmPd7NsWhfKsPkErzpm9wGkp',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmQCU2EcMqAqQPR2i9bChDtGNJchTbq5TbXJJ16u19uLTa',
          '/dnsaddr/bootstrap.libp2p.io/p2p/QmcZf59bWwK5XFi76CZX8cbJ4BhTzzA3gU1ZjYZcYW3dwt',
        ],
      }),
    ],
  });
  console.log('this node peerID', node.peerId.toString());
  node.connectionManager.addEventListener('peer:connect', ({ detail }) => {
    console.log('peer:connect', 'Connection established to:', detail.remotePeer.toString());
  });

  node.peerStore.addEventListener('change:multiaddrs', ({ detail: { peerId, multiaddrs } }) => {
    if (peerId.equals(node.peerId)) {
      console.log('address changes', multiaddrs.toString(), peerId.toString());
    }
  });
  return node;
}

(async () => {
  const node = await createNode();
  await node.start();

  const interval = setInterval(async () => {
    const peers = node.getConnections()

    if (peers.length === 0) {
      console.info('no peers yet')
      return
    }

    clearInterval(interval)

    const data = {
      title: 'asdasdas',
    };
    const block = encode(data)
    const digest = await sha256.digest(block);
    const cid = CID.createV1(DAG_JSON_CODEC, digest);

    try {
      for await (const data of node.dht.provide(cid, {
        queryFuncTimeout: 60000 // you may need to tweak this
      })) {
        console.log(data);
      }
    } catch (e) {
      console.log(e);
    }
  }, 5000)
})();
github-actions[bot] commented 1 year ago

Oops, seems like we needed more information for this issue, please comment with more details or this issue will be closed in 7 days.

github-actions[bot] commented 1 year ago

This issue was closed because it is missing author input.