libp2p 0.35.7 → 0.35.9-rc.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (88) hide show
  1. package/dist/src/circuit/auto-relay.d.ts +8 -10
  2. package/dist/src/circuit/auto-relay.d.ts.map +1 -1
  3. package/dist/src/connection-manager/auto-dialler.d.ts +1 -1
  4. package/dist/src/connection-manager/auto-dialler.d.ts.map +1 -1
  5. package/dist/src/connection-manager/index.d.ts +1 -2
  6. package/dist/src/connection-manager/index.d.ts.map +1 -1
  7. package/dist/src/content-routing/utils.d.ts +3 -3
  8. package/dist/src/content-routing/utils.d.ts.map +1 -1
  9. package/dist/src/dht/dht-peer-routing.d.ts.map +1 -1
  10. package/dist/src/dialer/dial-request.d.ts.map +1 -1
  11. package/dist/src/dialer/index.d.ts +5 -5
  12. package/dist/src/dialer/index.d.ts.map +1 -1
  13. package/dist/src/identify/index.d.ts +4 -4
  14. package/dist/src/identify/index.d.ts.map +1 -1
  15. package/dist/src/index.d.ts +6 -6
  16. package/dist/src/index.d.ts.map +1 -1
  17. package/dist/src/metrics/index.d.ts +9 -4
  18. package/dist/src/metrics/index.d.ts.map +1 -1
  19. package/dist/src/metrics/tracked-map.d.ts +6 -1
  20. package/dist/src/metrics/tracked-map.d.ts.map +1 -1
  21. package/dist/src/peer-routing.d.ts +1 -1
  22. package/dist/src/peer-routing.d.ts.map +1 -1
  23. package/dist/src/peer-store/address-book.d.ts +28 -84
  24. package/dist/src/peer-store/address-book.d.ts.map +1 -1
  25. package/dist/src/peer-store/index.d.ts +25 -94
  26. package/dist/src/peer-store/index.d.ts.map +1 -1
  27. package/dist/src/peer-store/key-book.d.ts +31 -15
  28. package/dist/src/peer-store/key-book.d.ts.map +1 -1
  29. package/dist/src/peer-store/metadata-book.d.ts +33 -29
  30. package/dist/src/peer-store/metadata-book.d.ts.map +1 -1
  31. package/dist/src/peer-store/pb/peer.d.ts +222 -0
  32. package/dist/src/peer-store/proto-book.d.ts +27 -28
  33. package/dist/src/peer-store/proto-book.d.ts.map +1 -1
  34. package/dist/src/peer-store/store.d.ts +73 -0
  35. package/dist/src/peer-store/store.d.ts.map +1 -0
  36. package/dist/src/peer-store/types.d.ts +202 -0
  37. package/dist/src/peer-store/types.d.ts.map +1 -0
  38. package/dist/src/ping/index.d.ts.map +1 -1
  39. package/dist/src/record/peer-record/index.d.ts +2 -2
  40. package/dist/src/record/peer-record/index.d.ts.map +1 -1
  41. package/dist/src/registrar.d.ts +5 -5
  42. package/dist/src/registrar.d.ts.map +1 -1
  43. package/dist/src/upgrader.d.ts.map +1 -1
  44. package/package.json +15 -18
  45. package/src/circuit/auto-relay.js +19 -19
  46. package/src/connection-manager/auto-dialler.js +9 -4
  47. package/src/connection-manager/index.js +39 -22
  48. package/src/content-routing/utils.js +4 -4
  49. package/src/dht/dht-peer-routing.js +2 -6
  50. package/src/dialer/dial-request.js +4 -1
  51. package/src/dialer/index.js +22 -10
  52. package/src/identify/index.js +28 -23
  53. package/src/index.js +33 -27
  54. package/src/metrics/index.js +15 -8
  55. package/src/metrics/tracked-map.js +45 -13
  56. package/src/peer-routing.js +4 -1
  57. package/src/peer-store/address-book.js +242 -227
  58. package/src/peer-store/index.js +77 -110
  59. package/src/peer-store/key-book.js +99 -54
  60. package/src/peer-store/metadata-book.js +171 -101
  61. package/src/peer-store/pb/peer.d.ts +222 -0
  62. package/src/peer-store/pb/peer.js +643 -0
  63. package/src/peer-store/pb/peer.proto +31 -0
  64. package/src/peer-store/proto-book.js +171 -105
  65. package/src/peer-store/store.js +250 -0
  66. package/src/peer-store/types.ts +245 -0
  67. package/src/ping/index.js +6 -0
  68. package/src/record/peer-record/index.js +1 -1
  69. package/src/record/utils.js +1 -1
  70. package/src/registrar.js +4 -4
  71. package/src/upgrader.js +3 -1
  72. package/dist/src/peer-store/book.d.ts +0 -81
  73. package/dist/src/peer-store/book.d.ts.map +0 -1
  74. package/dist/src/peer-store/persistent/consts.d.ts +0 -6
  75. package/dist/src/peer-store/persistent/consts.d.ts.map +0 -1
  76. package/dist/src/peer-store/persistent/index.d.ts +0 -129
  77. package/dist/src/peer-store/persistent/index.d.ts.map +0 -1
  78. package/dist/src/peer-store/persistent/pb/address-book.d.ts +0 -198
  79. package/dist/src/peer-store/persistent/pb/proto-book.d.ts +0 -59
  80. package/src/peer-store/book.js +0 -124
  81. package/src/peer-store/persistent/consts.js +0 -15
  82. package/src/peer-store/persistent/index.js +0 -408
  83. package/src/peer-store/persistent/pb/address-book.d.ts +0 -198
  84. package/src/peer-store/persistent/pb/address-book.js +0 -522
  85. package/src/peer-store/persistent/pb/address-book.proto +0 -27
  86. package/src/peer-store/persistent/pb/proto-book.d.ts +0 -59
  87. package/src/peer-store/persistent/pb/proto-book.js +0 -157
  88. package/src/peer-store/persistent/pb/proto-book.proto +0 -5
@@ -1,152 +1,119 @@
1
1
  'use strict'
2
2
 
3
- const errcode = require('err-code')
4
-
3
+ const debug = require('debug')
5
4
  const { EventEmitter } = require('events')
6
- const PeerId = require('peer-id')
7
-
8
5
  const AddressBook = require('./address-book')
9
6
  const KeyBook = require('./key-book')
10
7
  const MetadataBook = require('./metadata-book')
11
8
  const ProtoBook = require('./proto-book')
12
-
13
- const {
14
- codes: { ERR_INVALID_PARAMETERS }
15
- } = require('../errors')
9
+ const Store = require('./store')
16
10
 
17
11
  /**
18
- * @typedef {import('./address-book').Address} Address
12
+ * @typedef {import('./types').PeerStore} PeerStore
13
+ * @typedef {import('./types').Peer} Peer
14
+ * @typedef {import('peer-id')} PeerId
19
15
  */
20
16
 
17
+ const log = Object.assign(debug('libp2p:peer-store'), {
18
+ error: debug('libp2p:peer-store:err')
19
+ })
20
+
21
21
  /**
22
- * @extends {EventEmitter}
22
+ * An implementation of PeerStore that stores data in a Datastore
23
23
  *
24
- * @fires PeerStore#peer Emitted when a new peer is added.
25
- * @fires PeerStore#change:protocols Emitted when a known peer supports a different set of protocols.
26
- * @fires PeerStore#change:multiaddrs Emitted when a known peer has a different set of multiaddrs.
27
- * @fires PeerStore#change:pubkey Emitted emitted when a peer's public key is known.
28
- * @fires PeerStore#change:metadata Emitted when the known metadata of a peer change.
24
+ * @implements {PeerStore}
29
25
  */
30
- class PeerStore extends EventEmitter {
26
+ class DefaultPeerStore extends EventEmitter {
31
27
  /**
32
- * Peer object
33
- *
34
- * @typedef {Object} Peer
35
- * @property {PeerId} id peer's peer-id instance.
36
- * @property {Address[]} addresses peer's addresses containing its multiaddrs and metadata.
37
- * @property {string[]} protocols peer's supported protocols.
38
- * @property {Map<string, Uint8Array>|undefined} metadata peer's metadata map.
28
+ * @param {object} properties
29
+ * @param {PeerId} properties.peerId
30
+ * @param {import('interface-datastore').Datastore} properties.datastore
39
31
  */
40
-
41
- /**
42
- * Responsible for managing known peers, as well as their addresses, protocols and metadata.
43
- *
44
- * @param {object} options
45
- * @param {PeerId} options.peerId
46
- * @class
47
- */
48
- constructor ({ peerId }) {
32
+ constructor ({ peerId, datastore }) {
49
33
  super()
50
34
 
51
35
  this._peerId = peerId
36
+ this._store = new Store(datastore)
52
37
 
53
- /**
54
- * AddressBook containing a map of peerIdStr to Address.
55
- */
56
- this.addressBook = new AddressBook(this)
57
-
58
- /**
59
- * KeyBook containing a map of peerIdStr to their PeerId with public keys.
60
- */
61
- this.keyBook = new KeyBook(this)
62
-
63
- /**
64
- * MetadataBook containing a map of peerIdStr to their metadata Map.
65
- */
66
- this.metadataBook = new MetadataBook(this)
67
-
68
- /**
69
- * ProtoBook containing a map of peerIdStr to supported protocols.
70
- */
71
- this.protoBook = new ProtoBook(this)
38
+ this.addressBook = new AddressBook(this.emit.bind(this), this._store)
39
+ this.keyBook = new KeyBook(this.emit.bind(this), this._store)
40
+ this.metadataBook = new MetadataBook(this.emit.bind(this), this._store)
41
+ this.protoBook = new ProtoBook(this.emit.bind(this), this._store)
72
42
  }
73
43
 
74
- /**
75
- * Start the PeerStore.
76
- */
77
- start () {}
78
-
79
- /**
80
- * Stop the PeerStore.
81
- */
82
- stop () {}
44
+ async * getPeers () {
45
+ log('getPeers await read lock')
46
+ const release = await this._store.lock.readLock()
47
+ log('getPeers got read lock')
48
+
49
+ try {
50
+ for await (const peer of this._store.all()) {
51
+ if (peer.id.toB58String() === this._peerId.toB58String()) {
52
+ // Remove self peer if present
53
+ continue
54
+ }
55
+
56
+ yield peer
57
+ }
58
+ } finally {
59
+ log('getPeers release read lock')
60
+ release()
61
+ }
62
+ }
83
63
 
84
64
  /**
85
- * Get all the stored information of every peer known.
65
+ * Delete the information of the given peer in every book
86
66
  *
87
- * @returns {Map<string, Peer>}
67
+ * @param {PeerId} peerId
88
68
  */
89
- get peers () {
90
- const storedPeers = new Set([
91
- ...this.addressBook.data.keys(),
92
- ...this.keyBook.data.keys(),
93
- ...this.protoBook.data.keys(),
94
- ...this.metadataBook.data.keys()
95
- ])
96
-
97
- // Remove self peer if present
98
- this._peerId && storedPeers.delete(this._peerId.toB58String())
99
-
100
- const peersData = new Map()
101
- storedPeers.forEach((idStr) => {
102
- peersData.set(idStr, this.get(PeerId.createFromB58String(idStr)))
103
- })
104
-
105
- return peersData
69
+ async delete (peerId) {
70
+ log('delete await write lock')
71
+ const release = await this._store.lock.writeLock()
72
+ log('delete got write lock')
73
+
74
+ try {
75
+ await this._store.delete(peerId)
76
+ } finally {
77
+ log('delete release write lock')
78
+ release()
79
+ }
106
80
  }
107
81
 
108
82
  /**
109
- * Delete the information of the given peer in every book.
83
+ * Get the stored information of a given peer
110
84
  *
111
85
  * @param {PeerId} peerId
112
- * @returns {boolean} true if found and removed
113
86
  */
114
- delete (peerId) {
115
- const addressesDeleted = this.addressBook.delete(peerId)
116
- const keyDeleted = this.keyBook.delete(peerId)
117
- const protocolsDeleted = this.protoBook.delete(peerId)
118
- const metadataDeleted = this.metadataBook.delete(peerId)
119
-
120
- return addressesDeleted || keyDeleted || protocolsDeleted || metadataDeleted
87
+ async get (peerId) {
88
+ log('get await read lock')
89
+ const release = await this._store.lock.readLock()
90
+ log('get got read lock')
91
+
92
+ try {
93
+ return this._store.load(peerId)
94
+ } finally {
95
+ log('get release read lock')
96
+ release()
97
+ }
121
98
  }
122
99
 
123
100
  /**
124
- * Get the stored information of a given peer.
101
+ * Returns true if we have a record of the peer
125
102
  *
126
103
  * @param {PeerId} peerId
127
- * @returns {Peer|undefined}
128
104
  */
129
- get (peerId) {
130
- if (!PeerId.isPeerId(peerId)) {
131
- throw errcode(new Error('peerId must be an instance of peer-id'), ERR_INVALID_PARAMETERS)
132
- }
133
-
134
- const id = this.keyBook.data.get(peerId.toB58String())
135
- const addresses = this.addressBook.get(peerId)
136
- const metadata = this.metadataBook.get(peerId)
137
- const protocols = this.protoBook.get(peerId)
138
-
139
- if (!id && !addresses && !metadata && !protocols) {
140
- return undefined
141
- }
142
-
143
- return {
144
- id: id || peerId,
145
- addresses: addresses || [],
146
- protocols: protocols || [],
147
- metadata: metadata
105
+ async has (peerId) {
106
+ log('has await read lock')
107
+ const release = await this._store.lock.readLock()
108
+ log('has got read lock')
109
+
110
+ try {
111
+ return this._store.has(peerId)
112
+ } finally {
113
+ log('has release read lock')
114
+ release()
148
115
  }
149
116
  }
150
117
  }
151
118
 
152
- module.exports = PeerStore
119
+ module.exports = DefaultPeerStore
@@ -1,96 +1,141 @@
1
1
  'use strict'
2
2
 
3
3
  const debug = require('debug')
4
- const log = Object.assign(debug('libp2p:peer-store:key-book'), {
5
- error: debug('libp2p:peer-store:key-book:err')
6
- })
7
4
  const errcode = require('err-code')
8
-
5
+ const { codes } = require('../errors')
9
6
  const PeerId = require('peer-id')
10
-
11
- const Book = require('./book')
12
-
13
- const {
14
- codes: { ERR_INVALID_PARAMETERS }
15
- } = require('../errors')
7
+ const { equals: uint8arrayEquals } = require('uint8arrays/equals')
16
8
 
17
9
  /**
18
- * @typedef {import('./')} PeerStore
19
- * @typedef {import('libp2p-crypto').PublicKey} PublicKey
10
+ * @typedef {import('./types').PeerStore} PeerStore
11
+ * @typedef {import('./types').KeyBook} KeyBook
12
+ * @typedef {import('libp2p-interfaces/src/keys/types').PublicKey} PublicKey
20
13
  */
21
14
 
15
+ const log = Object.assign(debug('libp2p:peer-store:key-book'), {
16
+ error: debug('libp2p:peer-store:key-book:err')
17
+ })
18
+
19
+ const EVENT_NAME = 'change:pubkey'
20
+
22
21
  /**
23
- * @extends {Book}
22
+ * @implements {KeyBook}
24
23
  */
25
- class KeyBook extends Book {
24
+ class PeerStoreKeyBook {
26
25
  /**
27
26
  * The KeyBook is responsible for keeping the known public keys of a peer.
28
27
  *
29
- * @class
30
- * @param {PeerStore} peerStore
28
+ * @param {PeerStore["emit"]} emit
29
+ * @param {import('./types').Store} store
31
30
  */
32
- constructor (peerStore) {
33
- super({
34
- peerStore,
35
- eventName: 'change:pubkey',
36
- eventProperty: 'pubkey',
37
- eventTransformer: (data) => data.pubKey
38
- })
39
-
40
- /**
41
- * Map known peers to their known Public Key.
42
- *
43
- * @type {Map<string, PeerId>}
44
- */
45
- this.data = new Map()
31
+ constructor (emit, store) {
32
+ this._emit = emit
33
+ this._store = store
46
34
  }
47
35
 
48
36
  /**
49
- * Set the Peer public key.
37
+ * Set the Peer public key
50
38
  *
51
- * @override
52
39
  * @param {PeerId} peerId
53
40
  * @param {PublicKey} publicKey
54
- * @returns {KeyBook}
55
41
  */
56
- set (peerId, publicKey) {
42
+ async set (peerId, publicKey) {
57
43
  if (!PeerId.isPeerId(peerId)) {
58
44
  log.error('peerId must be an instance of peer-id to store data')
59
- throw errcode(new Error('peerId must be an instance of peer-id'), ERR_INVALID_PARAMETERS)
45
+ throw errcode(new Error('peerId must be an instance of peer-id'), codes.ERR_INVALID_PARAMETERS)
60
46
  }
61
47
 
62
- const id = peerId.toB58String()
63
- const recPeerId = this.data.get(id)
64
-
65
- // If no record available, and this is valid
66
- if (!recPeerId && publicKey) {
67
- // This might be unecessary, but we want to store the PeerId
68
- // to avoid an async operation when reconstructing the PeerId
69
- peerId.pubKey = publicKey
48
+ if (!publicKey) {
49
+ log.error('publicKey must be an instance of PublicKey to store data')
50
+ throw errcode(new Error('publicKey must be an instance of PublicKey'), codes.ERR_INVALID_PARAMETERS)
51
+ }
70
52
 
71
- this._setData(peerId, peerId)
72
- log(`stored provided public key for ${id}`)
53
+ log('set await write lock')
54
+ const release = await this._store.lock.writeLock()
55
+ log('set got write lock')
56
+
57
+ let updatedKey = false
58
+
59
+ try {
60
+ try {
61
+ const existing = await this._store.load(peerId)
62
+
63
+ if (existing.pubKey && uint8arrayEquals(existing.pubKey.bytes, publicKey.bytes)) {
64
+ return
65
+ }
66
+ } catch (/** @type {any} */ err) {
67
+ if (err.code !== codes.ERR_NOT_FOUND) {
68
+ throw err
69
+ }
70
+ }
71
+
72
+ await this._store.patchOrCreate(peerId, {
73
+ pubKey: publicKey
74
+ })
75
+ updatedKey = true
76
+ } finally {
77
+ log('set release write lock')
78
+ release()
73
79
  }
74
80
 
75
- return this
81
+ if (updatedKey) {
82
+ this._emit(EVENT_NAME, { peerId, pubKey: publicKey })
83
+ }
76
84
  }
77
85
 
78
86
  /**
79
- * Get Public key of the given PeerId, if stored.
87
+ * Get Public key of the given PeerId, if stored
80
88
  *
81
- * @override
82
89
  * @param {PeerId} peerId
83
- * @returns {PublicKey | undefined}
84
90
  */
85
- get (peerId) {
91
+ async get (peerId) {
86
92
  if (!PeerId.isPeerId(peerId)) {
87
- throw errcode(new Error('peerId must be an instance of peer-id'), ERR_INVALID_PARAMETERS)
93
+ log.error('peerId must be an instance of peer-id to store data')
94
+ throw errcode(new Error('peerId must be an instance of peer-id'), codes.ERR_INVALID_PARAMETERS)
88
95
  }
89
96
 
90
- const rec = this.data.get(peerId.toB58String())
97
+ log('get await write lock')
98
+ const release = await this._store.lock.readLock()
99
+ log('get got write lock')
100
+
101
+ try {
102
+ const peer = await this._store.load(peerId)
103
+
104
+ return peer.pubKey
105
+ } catch (/** @type {any} */ err) {
106
+ if (err.code !== codes.ERR_NOT_FOUND) {
107
+ throw err
108
+ }
109
+ } finally {
110
+ log('get release write lock')
111
+ release()
112
+ }
113
+ }
114
+
115
+ /**
116
+ * @param {PeerId} peerId
117
+ */
118
+ async delete (peerId) {
119
+ if (!PeerId.isPeerId(peerId)) {
120
+ log.error('peerId must be an instance of peer-id to store data')
121
+ throw errcode(new Error('peerId must be an instance of peer-id'), codes.ERR_INVALID_PARAMETERS)
122
+ }
123
+
124
+ log('delete await write lock')
125
+ const release = await this._store.lock.writeLock()
126
+ log('delete got write lock')
127
+
128
+ try {
129
+ await this._store.patchOrCreate(peerId, {
130
+ pubKey: undefined
131
+ })
132
+ } finally {
133
+ log('delete release write lock')
134
+ release()
135
+ }
91
136
 
92
- return rec ? rec.pubKey : undefined
137
+ this._emit(EVENT_NAME, { peerId, pubKey: undefined })
93
138
  }
94
139
  }
95
140
 
96
- module.exports = KeyBook
141
+ module.exports = PeerStoreKeyBook