@streamr/dht 102.0.0-beta.1 → 102.0.0-beta.3

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 (211) hide show
  1. package/dist/generated/google/protobuf/any.d.ts +180 -0
  2. package/dist/generated/google/protobuf/any.js +155 -0
  3. package/dist/generated/google/protobuf/any.js.map +1 -0
  4. package/dist/generated/google/protobuf/empty.d.ts +31 -0
  5. package/dist/generated/google/protobuf/empty.js +32 -0
  6. package/dist/generated/google/protobuf/empty.js.map +1 -0
  7. package/dist/generated/google/protobuf/timestamp.d.ts +155 -0
  8. package/dist/generated/google/protobuf/timestamp.js +136 -0
  9. package/dist/generated/google/protobuf/timestamp.js.map +1 -0
  10. package/dist/generated/packages/dht/protos/DhtRpc.client.d.ts +361 -0
  11. package/dist/generated/packages/dht/protos/DhtRpc.client.js +285 -0
  12. package/dist/generated/packages/dht/protos/DhtRpc.client.js.map +1 -0
  13. package/dist/generated/packages/dht/protos/DhtRpc.d.ts +999 -0
  14. package/dist/generated/packages/dht/protos/DhtRpc.js +677 -0
  15. package/dist/generated/packages/dht/protos/DhtRpc.js.map +1 -0
  16. package/dist/generated/packages/dht/protos/DhtRpc.server.d.ts +162 -0
  17. package/dist/generated/packages/dht/protos/DhtRpc.server.js +3 -0
  18. package/dist/generated/packages/dht/protos/DhtRpc.server.js.map +1 -0
  19. package/dist/generated/packages/proto-rpc/protos/ProtoRpc.d.ts +87 -0
  20. package/dist/generated/packages/proto-rpc/protos/ProtoRpc.js +66 -0
  21. package/dist/generated/packages/proto-rpc/protos/ProtoRpc.js.map +1 -0
  22. package/dist/package.json +7 -7
  23. package/package.json +7 -7
  24. package/eslint.config.mjs +0 -12
  25. package/src/connection/Connection.ts +0 -28
  26. package/src/connection/ConnectionLockRpcLocal.ts +0 -78
  27. package/src/connection/ConnectionLockRpcRemote.ts +0 -64
  28. package/src/connection/ConnectionLockStates.ts +0 -131
  29. package/src/connection/ConnectionManager.ts +0 -661
  30. package/src/connection/ConnectionsView.ts +0 -8
  31. package/src/connection/ConnectorFacade.ts +0 -217
  32. package/src/connection/Handshaker.ts +0 -209
  33. package/src/connection/IConnection.ts +0 -40
  34. package/src/connection/ManagedConnection.ts +0 -113
  35. package/src/connection/OutputBuffer.ts +0 -28
  36. package/src/connection/PendingConnection.ts +0 -68
  37. package/src/connection/connectivityChecker.ts +0 -108
  38. package/src/connection/connectivityRequestHandler.ts +0 -116
  39. package/src/connection/simulator/Simulator.ts +0 -369
  40. package/src/connection/simulator/SimulatorConnection.ts +0 -137
  41. package/src/connection/simulator/SimulatorConnector.ts +0 -98
  42. package/src/connection/simulator/SimulatorTransport.ts +0 -15
  43. package/src/connection/simulator/pings.ts +0 -42
  44. package/src/connection/webrtc/BrowserWebrtcConnection.ts +0 -242
  45. package/src/connection/webrtc/IWebrtcConnection.ts +0 -24
  46. package/src/connection/webrtc/NodeWebrtcConnection.ts +0 -245
  47. package/src/connection/webrtc/WebrtcConnector.ts +0 -234
  48. package/src/connection/webrtc/WebrtcConnectorRpcLocal.ts +0 -108
  49. package/src/connection/webrtc/WebrtcConnectorRpcRemote.ts +0 -60
  50. package/src/connection/webrtc/iceServerAsString.ts +0 -15
  51. package/src/connection/websocket/AbstractWebsocketClientConnection.ts +0 -122
  52. package/src/connection/websocket/AutoCertifierClientFacade.ts +0 -89
  53. package/src/connection/websocket/BrowserWebsocketClientConnection.ts +0 -44
  54. package/src/connection/websocket/NodeWebsocketClientConnection.ts +0 -39
  55. package/src/connection/websocket/WebsocketClientConnector.ts +0 -119
  56. package/src/connection/websocket/WebsocketClientConnectorRpcLocal.ts +0 -38
  57. package/src/connection/websocket/WebsocketClientConnectorRpcRemote.ts +0 -19
  58. package/src/connection/websocket/WebsocketServer.ts +0 -164
  59. package/src/connection/websocket/WebsocketServerConnection.ts +0 -109
  60. package/src/connection/websocket/WebsocketServerConnector.ts +0 -290
  61. package/src/dht/DhtNode.ts +0 -683
  62. package/src/dht/DhtNodeRpcLocal.ts +0 -84
  63. package/src/dht/DhtNodeRpcRemote.ts +0 -107
  64. package/src/dht/ExternalApiRpcLocal.ts +0 -58
  65. package/src/dht/ExternalApiRpcRemote.ts +0 -41
  66. package/src/dht/PeerManager.ts +0 -305
  67. package/src/dht/contact/Contact.ts +0 -19
  68. package/src/dht/contact/ContactList.ts +0 -43
  69. package/src/dht/contact/RandomContactList.ts +0 -56
  70. package/src/dht/contact/RingContactList.ts +0 -143
  71. package/src/dht/contact/RpcRemote.ts +0 -72
  72. package/src/dht/contact/SortedContactList.ts +0 -173
  73. package/src/dht/contact/getClosestNodes.ts +0 -24
  74. package/src/dht/contact/ringIdentifiers.ts +0 -62
  75. package/src/dht/discovery/DiscoverySession.ts +0 -129
  76. package/src/dht/discovery/PeerDiscovery.ts +0 -244
  77. package/src/dht/discovery/RingDiscoverySession.ts +0 -148
  78. package/src/dht/recursive-operation/RecursiveOperationManager.ts +0 -251
  79. package/src/dht/recursive-operation/RecursiveOperationRpcLocal.ts +0 -34
  80. package/src/dht/recursive-operation/RecursiveOperationRpcRemote.ts +0 -43
  81. package/src/dht/recursive-operation/RecursiveOperationSession.ts +0 -231
  82. package/src/dht/recursive-operation/RecursiveOperationSessionRpcLocal.ts +0 -35
  83. package/src/dht/recursive-operation/RecursiveOperationSessionRpcRemote.ts +0 -30
  84. package/src/dht/routing/DuplicateDetector.ts +0 -34
  85. package/src/dht/routing/Router.ts +0 -246
  86. package/src/dht/routing/RouterRpcLocal.ts +0 -78
  87. package/src/dht/routing/RouterRpcRemote.ts +0 -80
  88. package/src/dht/routing/RoutingSession.ts +0 -243
  89. package/src/dht/routing/RoutingTablesCache.ts +0 -60
  90. package/src/dht/routing/getPreviousPeer.ts +0 -6
  91. package/src/dht/store/LocalDataStore.ts +0 -84
  92. package/src/dht/store/StoreManager.ts +0 -170
  93. package/src/dht/store/StoreRpcLocal.ts +0 -89
  94. package/src/dht/store/StoreRpcRemote.ts +0 -32
  95. package/src/exports.ts +0 -33
  96. package/src/helpers/AddressTools.ts +0 -28
  97. package/src/helpers/Connectivity.ts +0 -19
  98. package/src/helpers/browser/isBrowserEnvironment.ts +0 -1
  99. package/src/helpers/browser/isBrowserEnvironment_override.ts +0 -3
  100. package/src/helpers/createPeerDescriptor.ts +0 -57
  101. package/src/helpers/createPeerDescriptorSignaturePayload.ts +0 -28
  102. package/src/helpers/debugHelpers.ts +0 -9
  103. package/src/helpers/errors.ts +0 -49
  104. package/src/helpers/offering.ts +0 -15
  105. package/src/helpers/protoClasses.ts +0 -57
  106. package/src/helpers/protoToString.ts +0 -21
  107. package/src/helpers/version.ts +0 -32
  108. package/src/identifiers.ts +0 -29
  109. package/src/rpc-protocol/DhtCallContext.ts +0 -14
  110. package/src/rpc-protocol/DhtRpcOptions.ts +0 -10
  111. package/src/transport/ITransport.ts +0 -37
  112. package/src/transport/ListeningRpcCommunicator.ts +0 -32
  113. package/src/transport/RoutingRpcCommunicator.ts +0 -66
  114. package/src/types/ServiceID.ts +0 -1
  115. package/src/types/textencoding.d.ts +0 -6
  116. package/test/benchmark/Find.test.ts +0 -72
  117. package/test/benchmark/KademliaCorrectness.test.ts +0 -114
  118. package/test/benchmark/RingCorrectness.test.ts +0 -157
  119. package/test/benchmark/SortedContactListBenchmark.test.ts +0 -108
  120. package/test/benchmark/WebsocketServerMemoryLeak.test.ts +0 -41
  121. package/test/benchmark/hybrid-network-simulation/RingContactList.test.ts +0 -71
  122. package/test/end-to-end/GeoIpLayer0.test.ts +0 -55
  123. package/test/end-to-end/Layer0-Layer1.test.ts +0 -93
  124. package/test/end-to-end/Layer0.test.ts +0 -76
  125. package/test/end-to-end/Layer0MixedConnectionTypes.test.ts +0 -110
  126. package/test/end-to-end/Layer0Webrtc-Layer1.test.ts +0 -137
  127. package/test/end-to-end/Layer0Webrtc.test.ts +0 -85
  128. package/test/end-to-end/Layer1-Scale-WebSocket.test.ts +0 -82
  129. package/test/end-to-end/Layer1-Scale-Webrtc.test.ts +0 -76
  130. package/test/end-to-end/RecoveryFromFailedAutoCertification.test.ts +0 -52
  131. package/test/end-to-end/WebsocketConnectionRequest.test.ts +0 -69
  132. package/test/end-to-end/memory-leak.test.ts +0 -80
  133. package/test/integration/ConnectionLocking.test.ts +0 -192
  134. package/test/integration/ConnectionManager.test.ts +0 -528
  135. package/test/integration/ConnectivityChecking.test.ts +0 -53
  136. package/test/integration/DhtJoinPeerDiscovery.test.ts +0 -49
  137. package/test/integration/DhtNode.test.ts +0 -66
  138. package/test/integration/DhtNodeExternalAPI.test.ts +0 -48
  139. package/test/integration/DhtNodeRpcRemote.test.ts +0 -66
  140. package/test/integration/DhtRpc.test.ts +0 -121
  141. package/test/integration/Find.test.ts +0 -45
  142. package/test/integration/GeoIpConnectivityChecking.test.ts +0 -72
  143. package/test/integration/Layer1-scale.test.ts +0 -189
  144. package/test/integration/Mock-Layer1-Layer0.test.ts +0 -85
  145. package/test/integration/MultipleEntryPointJoining.test.ts +0 -105
  146. package/test/integration/ReplicateData.test.ts +0 -104
  147. package/test/integration/RouteMessage.test.ts +0 -230
  148. package/test/integration/RouterRpcRemote.test.ts +0 -77
  149. package/test/integration/SimultaneousConnections.test.ts +0 -316
  150. package/test/integration/Store.test.ts +0 -85
  151. package/test/integration/StoreAndDelete.test.ts +0 -77
  152. package/test/integration/StoreOnDhtWithThreeNodes.test.ts +0 -59
  153. package/test/integration/StoreOnDhtWithTwoNodes.test.ts +0 -51
  154. package/test/integration/StoreRpcRemote.test.ts +0 -54
  155. package/test/integration/WebrtcConnectionManagement.test.ts +0 -191
  156. package/test/integration/WebrtcConnectorRpc.test.ts +0 -125
  157. package/test/integration/Websocket.test.ts +0 -65
  158. package/test/integration/WebsocketClientConnectorRpc.test.ts +0 -69
  159. package/test/integration/WebsocketConnectionManagement.test.ts +0 -191
  160. package/test/integration/rpc-connections-over-webrtc.test.ts +0 -123
  161. package/test/kademlia-simulation/data/nodeids.json +0 -13002
  162. package/test/kademlia-simulation/data/orderedneighbors.json +0 -1001
  163. package/test/types/global.d.ts +0 -1
  164. package/test/unit/AddressTools.test.ts +0 -44
  165. package/test/unit/AutoCertifierClientFacade.test.ts +0 -58
  166. package/test/unit/ConnectionManager.test.ts +0 -65
  167. package/test/unit/ConnectivityHelpers.test.ts +0 -61
  168. package/test/unit/DiscoverySession.test.ts +0 -87
  169. package/test/unit/DuplicateDetector.test.ts +0 -31
  170. package/test/unit/Handshaker.test.ts +0 -169
  171. package/test/unit/ListeningRpcCommunicator.test.ts +0 -52
  172. package/test/unit/LocalDataStore.test.ts +0 -108
  173. package/test/unit/ManagedConnection.test.ts +0 -58
  174. package/test/unit/PeerManager.test.ts +0 -93
  175. package/test/unit/PendingConnection.test.ts +0 -57
  176. package/test/unit/ProtobufMessage.test.ts +0 -21
  177. package/test/unit/RandomContactList.test.ts +0 -58
  178. package/test/unit/RecursiveOperationManager.test.ts +0 -161
  179. package/test/unit/RecursiveOperationSession.test.ts +0 -68
  180. package/test/unit/Router.test.ts +0 -137
  181. package/test/unit/RoutingSession.test.ts +0 -86
  182. package/test/unit/SortedContactList.test.ts +0 -115
  183. package/test/unit/StoreManager.test.ts +0 -146
  184. package/test/unit/StoreRpcLocal.test.ts +0 -167
  185. package/test/unit/WebrtcConnection.test.ts +0 -29
  186. package/test/unit/WebrtcConnector.test.ts +0 -56
  187. package/test/unit/WebsocketClientConnector.test.ts +0 -101
  188. package/test/unit/WebsocketServer.test.ts +0 -66
  189. package/test/unit/WebsocketServerConnector.test.ts +0 -102
  190. package/test/unit/connectivityRequestHandler.test.ts +0 -104
  191. package/test/unit/createPeerDescriptor.test.ts +0 -69
  192. package/test/unit/customMatchers.test.ts +0 -34
  193. package/test/unit/getClosestNodes.test.ts +0 -30
  194. package/test/unit/version.test.ts +0 -18
  195. package/test/unit/webrtcReplaceInternalIpWithExternalIp.test.ts +0 -18
  196. package/test/utils/FakeConnectorFacade.ts +0 -41
  197. package/test/utils/FakeRpcCommunicator.ts +0 -23
  198. package/test/utils/FakeTransport.ts +0 -79
  199. package/test/utils/customMatchers.ts +0 -71
  200. package/test/utils/mock/MockConnection.ts +0 -26
  201. package/test/utils/mock/MockConnectionsView.ts +0 -18
  202. package/test/utils/mock/MockRouter.ts +0 -62
  203. package/test/utils/mock/MockRpcCommunicator.ts +0 -7
  204. package/test/utils/mock/MockTransport.ts +0 -26
  205. package/test/utils/mock/mockDataEntry.ts +0 -38
  206. package/test/utils/topology.ts +0 -79
  207. package/test/utils/utils.ts +0 -268
  208. package/tsconfig.browser.json +0 -17
  209. package/tsconfig.jest.json +0 -25
  210. package/tsconfig.json +0 -3
  211. package/tsconfig.node.json +0 -24
@@ -1,84 +0,0 @@
1
- import { ServerCallContext } from '@protobuf-ts/runtime-rpc'
2
- import { Logger } from '@streamr/utils'
3
- import { DhtAddress, toDhtAddress, toNodeId } from '../identifiers'
4
- import { Empty } from '../../generated/google/protobuf/empty'
5
- import {
6
- ClosestPeersRequest,
7
- ClosestPeersResponse,
8
- ClosestRingPeersRequest,
9
- ClosestRingPeersResponse,
10
- PeerDescriptor,
11
- PingRequest,
12
- PingResponse
13
- } from '../../generated/packages/dht/protos/DhtRpc'
14
- import { IDhtNodeRpc } from '../../generated/packages/dht/protos/DhtRpc.server'
15
- import { DhtCallContext } from '../rpc-protocol/DhtCallContext'
16
- import { RingContacts } from './contact/RingContactList'
17
- import { getClosestNodes } from './contact/getClosestNodes'
18
- import { RingIdRaw } from './contact/ringIdentifiers'
19
-
20
- interface DhtNodeRpcLocalOptions {
21
- peerDiscoveryQueryBatchSize: number
22
- getNeighbors: () => readonly PeerDescriptor[]
23
- getClosestRingContactsTo: (id: RingIdRaw, limit: number) => RingContacts
24
- addContact: (contact: PeerDescriptor) => void
25
- removeContact: (nodeId: DhtAddress) => void
26
- }
27
-
28
- const logger = new Logger(module)
29
-
30
- export class DhtNodeRpcLocal implements IDhtNodeRpc {
31
-
32
- private readonly options: DhtNodeRpcLocalOptions
33
-
34
- constructor(options: DhtNodeRpcLocalOptions) {
35
- this.options = options
36
- }
37
-
38
- // TODO rename to getClosestNeighbors (breaking change)
39
- async getClosestPeers(request: ClosestPeersRequest, context: ServerCallContext): Promise<ClosestPeersResponse> {
40
- this.options.addContact((context as DhtCallContext).incomingSourceDescriptor!)
41
- const peers = getClosestNodes(
42
- toDhtAddress(request.nodeId),
43
- this.options.getNeighbors(),
44
- { maxCount: this.options.peerDiscoveryQueryBatchSize }
45
- )
46
- const response = {
47
- peers,
48
- requestId: request.requestId
49
- }
50
- return response
51
- }
52
-
53
- // TODO rename to getClosestRingContacts (breaking change)
54
- async getClosestRingPeers(request: ClosestRingPeersRequest, context: ServerCallContext): Promise<ClosestRingPeersResponse> {
55
- this.options.addContact((context as DhtCallContext).incomingSourceDescriptor!)
56
- const closestContacts = this.options.getClosestRingContactsTo(request.ringId as RingIdRaw, this.options.peerDiscoveryQueryBatchSize)
57
- const response = {
58
- leftPeers: closestContacts.left,
59
- rightPeers: closestContacts.right,
60
- requestId: request.requestId
61
- }
62
- return response
63
- }
64
-
65
- async ping(request: PingRequest, context: ServerCallContext): Promise<PingResponse> {
66
- logger.trace('received ping request: ' + toNodeId((context as DhtCallContext).incomingSourceDescriptor!))
67
- setImmediate(() => {
68
- this.options.addContact((context as DhtCallContext).incomingSourceDescriptor!)
69
- })
70
- const response: PingResponse = {
71
- requestId: request.requestId
72
- }
73
- return response
74
- }
75
-
76
- async leaveNotice(context: ServerCallContext): Promise<Empty> {
77
- // TODO check signature??
78
- const sender = (context as DhtCallContext).incomingSourceDescriptor!
79
- const senderNodeId = toNodeId(sender)
80
- logger.trace('received leave notice: ' + senderNodeId)
81
- this.options.removeContact(senderNodeId)
82
- return {}
83
- }
84
- }
@@ -1,107 +0,0 @@
1
- import { RpcCommunicator } from '@streamr/proto-rpc'
2
- import { Logger } from '@streamr/utils'
3
- import { v4 } from 'uuid'
4
- import { DhtAddress, DhtAddressRaw, toNodeId, toDhtAddressRaw } from '../identifiers'
5
- import {
6
- ClosestPeersRequest,
7
- ClosestRingPeersRequest,
8
- PeerDescriptor,
9
- PingRequest
10
- } from '../../generated/packages/dht/protos/DhtRpc'
11
- import { DhtNodeRpcClient } from '../../generated/packages/dht/protos/DhtRpc.client'
12
- import { ServiceID } from '../types/ServiceID'
13
- import { RpcRemote } from './contact/RpcRemote'
14
- import { DhtCallContext } from '../rpc-protocol/DhtCallContext'
15
- import { RingIdRaw } from './contact/ringIdentifiers'
16
- import { RingContacts } from './contact/RingContactList'
17
-
18
- const logger = new Logger(module)
19
-
20
- // Fields required by objects stored in the k-bucket library
21
- export interface KBucketContact {
22
- id: DhtAddressRaw
23
- vectorClock: number
24
- }
25
-
26
- export class DhtNodeRpcRemote extends RpcRemote<DhtNodeRpcClient> implements KBucketContact {
27
-
28
- private static counter = 0
29
- public vectorClock: number
30
- public readonly id: DhtAddressRaw
31
- private readonly serviceId: ServiceID
32
-
33
- constructor(
34
- localPeerDescriptor: PeerDescriptor,
35
- peerDescriptor: PeerDescriptor,
36
- serviceId: ServiceID,
37
- rpcCommunicator: RpcCommunicator<DhtCallContext>,
38
- rpcRequestTimeout?: number
39
- ) {
40
- super(localPeerDescriptor, peerDescriptor, rpcCommunicator, DhtNodeRpcClient, rpcRequestTimeout)
41
- this.id = this.getPeerDescriptor().nodeId
42
- this.vectorClock = DhtNodeRpcRemote.counter++
43
- this.serviceId = serviceId
44
- }
45
-
46
- async getClosestPeers(nodeId: DhtAddress): Promise<PeerDescriptor[]> {
47
- logger.trace(`Requesting getClosestPeers on ${this.serviceId} from ${this.getNodeId()}`)
48
- const request: ClosestPeersRequest = {
49
- nodeId: toDhtAddressRaw(nodeId),
50
- requestId: v4()
51
- }
52
- try {
53
- const peers = await this.getClient().getClosestPeers(request, this.formDhtRpcOptions())
54
- return peers.peers
55
- } catch (err) {
56
- logger.trace(`getClosestPeers error ${this.serviceId}`, { err })
57
- throw err
58
- }
59
- }
60
-
61
- // TODO rename to getClosestRingContacts (breaking change)
62
- async getClosestRingPeers(ringIdRaw: RingIdRaw): Promise<RingContacts> {
63
- logger.trace(`Requesting getClosestRingPeers on ${this.serviceId} from ${this.getNodeId()}`)
64
- const request: ClosestRingPeersRequest = {
65
- ringId: ringIdRaw,
66
- requestId: v4()
67
- }
68
- try {
69
- const response = await this.getClient().getClosestRingPeers(request, this.formDhtRpcOptions())
70
- return { left: response.leftPeers ?? [], right: response.rightPeers ?? [] }
71
- } catch (err) {
72
- logger.trace(`getClosestRingPeers error ${this.serviceId}`, { err })
73
- throw err
74
- }
75
- }
76
-
77
- async ping(): Promise<boolean> {
78
- logger.trace(`Requesting ping on ${this.serviceId} from ${this.getNodeId()}`)
79
- const request: PingRequest = {
80
- requestId: v4()
81
- }
82
- const options = this.formDhtRpcOptions()
83
- try {
84
- const pong = await this.getClient().ping(request, options)
85
- if (pong.requestId === request.requestId) {
86
- return true
87
- }
88
- } catch (err) {
89
- logger.trace(`ping failed on ${this.serviceId} to ${this.getNodeId()}`, { err })
90
- }
91
- return false
92
- }
93
-
94
- leaveNotice(): void {
95
- logger.trace(`Sending leaveNotice on ${this.serviceId} from ${this.getNodeId()}`)
96
- const options = this.formDhtRpcOptions({
97
- notification: true
98
- })
99
- this.getClient().leaveNotice({}, options).catch((e) => {
100
- logger.trace('Failed to send leaveNotice' + e)
101
- })
102
- }
103
-
104
- getNodeId(): DhtAddress {
105
- return toNodeId(this.getPeerDescriptor())
106
- }
107
- }
@@ -1,58 +0,0 @@
1
- import { IExternalApiRpc } from '../../generated/packages/dht/protos/DhtRpc.server'
2
- import {
3
- ExternalFetchDataRequest,
4
- ExternalFetchDataResponse,
5
- ExternalStoreDataRequest,
6
- ExternalStoreDataResponse,
7
- RecursiveOperation,
8
- PeerDescriptor
9
- } from '../../generated/packages/dht/protos/DhtRpc'
10
- import { ServerCallContext } from '@protobuf-ts/runtime-rpc'
11
- import { DhtCallContext } from '../rpc-protocol/DhtCallContext'
12
- import { RecursiveOperationResult } from './recursive-operation/RecursiveOperationManager'
13
- import { Any } from '../../generated/google/protobuf/any'
14
- import { DhtAddress, toNodeId, toDhtAddress } from '../identifiers'
15
-
16
- interface ExternalApiRpcLocalOptions {
17
- executeRecursiveOperation: (
18
- targetId: DhtAddress,
19
- operation: RecursiveOperation,
20
- excludedPeer: DhtAddress
21
- ) => Promise<RecursiveOperationResult>
22
- storeDataToDht: (
23
- key: DhtAddress,
24
- data: Any,
25
- creator: DhtAddress
26
- ) => Promise<PeerDescriptor[]>
27
- }
28
-
29
- export class ExternalApiRpcLocal implements IExternalApiRpc {
30
-
31
- private readonly options: ExternalApiRpcLocalOptions
32
-
33
- constructor(options: ExternalApiRpcLocalOptions) {
34
- this.options = options
35
- }
36
-
37
- async externalFetchData(request: ExternalFetchDataRequest, context: ServerCallContext): Promise<ExternalFetchDataResponse> {
38
- const senderPeerDescriptor = (context as DhtCallContext).incomingSourceDescriptor!
39
- const result = await this.options.executeRecursiveOperation(
40
- toDhtAddress(request.key),
41
- RecursiveOperation.FETCH_DATA,
42
- toNodeId(senderPeerDescriptor)
43
- )
44
- return ExternalFetchDataResponse.create({ entries: result.dataEntries ?? [] })
45
- }
46
-
47
- async externalStoreData(request: ExternalStoreDataRequest, context: ServerCallContext): Promise<ExternalStoreDataResponse> {
48
- const senderPeerDescriptor = (context as DhtCallContext).incomingSourceDescriptor!
49
- const result = await this.options.storeDataToDht(
50
- toDhtAddress(request.key),
51
- request.data!,
52
- toNodeId(senderPeerDescriptor)
53
- )
54
- return ExternalStoreDataResponse.create({
55
- storers: result
56
- })
57
- }
58
- }
@@ -1,41 +0,0 @@
1
- import { DhtAddress, toDhtAddressRaw } from '../identifiers'
2
- import { Any } from '../../generated/google/protobuf/any'
3
- import { DataEntry, ExternalFetchDataRequest, ExternalStoreDataRequest, PeerDescriptor } from '../../generated/packages/dht/protos/DhtRpc'
4
- import { ExternalApiRpcClient } from '../../generated/packages/dht/protos/DhtRpc.client'
5
- import { RpcRemote } from './contact/RpcRemote'
6
-
7
- export class ExternalApiRpcRemote extends RpcRemote<ExternalApiRpcClient> {
8
-
9
- async externalFetchData(key: DhtAddress): Promise<DataEntry[]> {
10
- const request: ExternalFetchDataRequest = {
11
- key: toDhtAddressRaw(key)
12
- }
13
- const options = this.formDhtRpcOptions({
14
- // TODO use options option or named constant?
15
- timeout: 10000
16
- })
17
- try {
18
- const data = await this.getClient().externalFetchData(request, options)
19
- return data.entries
20
- } catch {
21
- return []
22
- }
23
- }
24
-
25
- async storeData(key: DhtAddress, data: Any): Promise<PeerDescriptor[]> {
26
- const request: ExternalStoreDataRequest = {
27
- key: toDhtAddressRaw(key),
28
- data
29
- }
30
- const options = this.formDhtRpcOptions({
31
- // TODO use options option or named constant?
32
- timeout: 10000
33
- })
34
- try {
35
- const response = await this.getClient().externalStoreData(request, options)
36
- return response.storers
37
- } catch {
38
- return []
39
- }
40
- }
41
- }
@@ -1,305 +0,0 @@
1
- import {
2
- Logger
3
- } from '@streamr/utils'
4
- import EventEmitter from 'eventemitter3'
5
- import KBucket from 'k-bucket'
6
- import { LockID } from '../connection/ConnectionLockStates'
7
- import { ConnectionLocker } from '../connection/ConnectionManager'
8
- import { DhtAddress, DhtAddressRaw, toNodeId, toDhtAddressRaw } from '../identifiers'
9
- import {
10
- PeerDescriptor
11
- } from '../../generated/packages/dht/protos/DhtRpc'
12
- import { DhtNodeRpcRemote } from './DhtNodeRpcRemote'
13
- import { RandomContactList } from './contact/RandomContactList'
14
- import { RingContactList } from './contact/RingContactList'
15
- import { ReadonlySortedContactList, SortedContactList } from './contact/SortedContactList'
16
- import { RingIdRaw, getRingIdRawFromPeerDescriptor } from './contact/ringIdentifiers'
17
-
18
- const logger = new Logger(module)
19
-
20
- interface PeerManagerOptions {
21
- numberOfNodesPerKBucket: number
22
- maxContactCount: number
23
- localNodeId: DhtAddress
24
- localPeerDescriptor: PeerDescriptor
25
- connectionLocker?: ConnectionLocker
26
- neighborPingLimit?: number
27
- lockId: LockID
28
- createDhtNodeRpcRemote: (peerDescriptor: PeerDescriptor) => DhtNodeRpcRemote
29
- hasConnection: (nodeId: DhtAddress) => boolean
30
- }
31
-
32
- // Returns all offline nodes, sets contacts as active if they are online
33
- const pingNodes = async (nodes: DhtNodeRpcRemote[], activeContacts: Set<DhtAddress>): Promise<PeerDescriptor[]> => {
34
- const offlineNeighbors: PeerDescriptor[] = []
35
- await Promise.allSettled(nodes.map(async (contact) => {
36
- const isOnline = await contact.ping()
37
- if (!isOnline) {
38
- activeContacts.delete(contact.getNodeId())
39
- offlineNeighbors.push(contact.getPeerDescriptor())
40
- } else {
41
- activeContacts.add(contact.getNodeId())
42
- }
43
- }))
44
- return offlineNeighbors
45
- }
46
-
47
- export interface PeerManagerEvents {
48
- nearbyContactAdded: (peerDescriptor: PeerDescriptor) => void
49
- nearbyContactRemoved: (peerDescriptor: PeerDescriptor) => void
50
- randomContactAdded: (peerDescriptor: PeerDescriptor) => void
51
- randomContactRemoved: (peerDescriptor: PeerDescriptor) => void
52
- ringContactAdded: (peerDescriptor: PeerDescriptor) => void
53
- ringContactRemoved: (peerDescriptor: PeerDescriptor) => void
54
- kBucketEmpty: () => void
55
- }
56
-
57
- export const getDistance = (nodeIdOrDataKeyRaw1: DhtAddressRaw, nodeIdOrDataKeyRaw2: DhtAddressRaw): number => {
58
- return KBucket.distance(nodeIdOrDataKeyRaw1, nodeIdOrDataKeyRaw2)
59
- }
60
-
61
- export class PeerManager extends EventEmitter<PeerManagerEvents> {
62
-
63
- // Glossary:
64
- // * 'neighbors' are the nodes that are our neighbors according to
65
- // the protocol of the layer we are in
66
- // * 'connections' are the nodes that are connected to this node on Layer0
67
- // * 'contacts' are all non-unresponsive nodes that we know about
68
-
69
- private neighbors: KBucket<DhtNodeRpcRemote>
70
- private nearbyContacts: SortedContactList<DhtNodeRpcRemote>
71
- private activeContacts: Set<DhtAddress>
72
- private ringContacts: RingContactList<DhtNodeRpcRemote>
73
- private randomContacts: RandomContactList<DhtNodeRpcRemote>
74
- private stopped: boolean = false
75
- private readonly options: PeerManagerOptions
76
-
77
- constructor(options: PeerManagerOptions) {
78
- super()
79
- this.options = options
80
- this.neighbors = new KBucket<DhtNodeRpcRemote>({
81
- localNodeId: toDhtAddressRaw(this.options.localNodeId),
82
- numberOfNodesPerKBucket: this.options.numberOfNodesPerKBucket,
83
- numberOfNodesToPing: this.options.numberOfNodesPerKBucket
84
- })
85
- this.ringContacts = new RingContactList<DhtNodeRpcRemote>(getRingIdRawFromPeerDescriptor(this.options.localPeerDescriptor))
86
- this.ringContacts.on('contactAdded', (contact: DhtNodeRpcRemote) => {
87
- this.emit('ringContactAdded', contact.getPeerDescriptor())
88
- })
89
- this.ringContacts.on('contactRemoved', (contact: DhtNodeRpcRemote) => {
90
- this.emit('ringContactRemoved', contact.getPeerDescriptor())
91
- })
92
- this.neighbors.on('ping', (oldContacts: DhtNodeRpcRemote[], newContact: DhtNodeRpcRemote) => this.onKBucketPing(oldContacts, newContact))
93
- this.neighbors.on('removed', (contact: DhtNodeRpcRemote) => this.onKBucketRemoved(toNodeId(contact.getPeerDescriptor())))
94
- this.neighbors.on('added', (contact: DhtNodeRpcRemote) => this.onKBucketAdded(contact))
95
- this.neighbors.on('updated', () => {
96
- // TODO: Update contact info to the connection manager and reconnect
97
- })
98
- this.nearbyContacts = new SortedContactList({
99
- referenceId: this.options.localNodeId,
100
- maxSize: this.options.maxContactCount,
101
- allowToContainReferenceId: false
102
- })
103
- this.nearbyContacts.on('contactRemoved', (contact: DhtNodeRpcRemote) => {
104
- if (this.stopped) {
105
- return
106
- }
107
- this.emit('nearbyContactRemoved', contact.getPeerDescriptor())
108
- this.randomContacts.addContact(this.options.createDhtNodeRpcRemote(contact.getPeerDescriptor()))
109
- })
110
- this.nearbyContacts.on('contactAdded', (contact: DhtNodeRpcRemote) =>
111
- this.emit('nearbyContactAdded', contact.getPeerDescriptor())
112
- )
113
- this.activeContacts = new Set()
114
- this.randomContacts = new RandomContactList(this.options.localNodeId, this.options.maxContactCount)
115
- this.randomContacts.on('contactRemoved', (removedContact: DhtNodeRpcRemote) =>
116
- this.emit('randomContactRemoved', removedContact.getPeerDescriptor())
117
- )
118
- this.randomContacts.on('contactAdded', (contactAdded: DhtNodeRpcRemote) =>
119
- this.emit('randomContactAdded', contactAdded.getPeerDescriptor())
120
- )
121
- }
122
-
123
- private onKBucketPing(oldContacts: DhtNodeRpcRemote[], newContact: DhtNodeRpcRemote): void {
124
- if (this.stopped) {
125
- return
126
- }
127
- const sortingList: SortedContactList<DhtNodeRpcRemote> = new SortedContactList({
128
- referenceId: this.options.localNodeId,
129
- allowToContainReferenceId: false
130
- })
131
- sortingList.addContacts(oldContacts)
132
- const removableNodeId = sortingList.getFurthestContacts(1)[0].getNodeId()
133
- this.options.connectionLocker?.weakUnlockConnection(removableNodeId, this.options.lockId)
134
- this.neighbors.remove(toDhtAddressRaw(removableNodeId))
135
- this.neighbors.add(newContact)
136
- }
137
-
138
- private onKBucketRemoved(nodeId: DhtAddress): void {
139
- if (this.stopped) {
140
- return
141
- }
142
- this.options.connectionLocker?.weakUnlockConnection(nodeId, this.options.lockId)
143
- logger.trace(`Removed contact ${nodeId}`)
144
- if (this.neighbors.count() === 0) {
145
- this.emit('kBucketEmpty')
146
- }
147
- }
148
-
149
- private onKBucketAdded(contact: DhtNodeRpcRemote): void {
150
- if (this.stopped) {
151
- return
152
- }
153
- if (contact.getNodeId() !== this.options.localNodeId) {
154
- const peerDescriptor = contact.getPeerDescriptor()
155
- const nodeId = toNodeId(peerDescriptor)
156
- // Important to lock here, before the ping result is known
157
- this.options.connectionLocker?.weakLockConnection(nodeId, this.options.lockId)
158
- if (this.options.hasConnection(contact.getNodeId())
159
- || (this.options.neighborPingLimit !== undefined && this.neighbors.count() > this.options.neighborPingLimit)) {
160
- logger.trace(`Added new contact ${nodeId}`)
161
- } else { // open connection by pinging
162
- logger.trace('starting ping ' + nodeId)
163
- contact.ping().then((result) => {
164
- if (result) {
165
- logger.trace(`Added new contact ${nodeId}`)
166
- } else {
167
- logger.trace('ping failed ' + nodeId)
168
- this.options.connectionLocker?.weakUnlockConnection(nodeId, this.options.lockId)
169
- this.removeContact(nodeId)
170
- this.addNearbyContactToNeighbors()
171
- }
172
- }).catch((_e) => {
173
- this.options.connectionLocker?.weakUnlockConnection(nodeId, this.options.lockId)
174
- this.removeContact(nodeId)
175
- this.addNearbyContactToNeighbors()
176
- })
177
- }
178
- }
179
- }
180
-
181
- private addNearbyContactToNeighbors(): void {
182
- if (this.stopped) {
183
- return
184
- }
185
- const closest = this.getNearbyActiveContactNotInNeighbors()
186
- if (closest) {
187
- this.addContact(closest.getPeerDescriptor())
188
- }
189
- }
190
-
191
- private getNearbyActiveContactNotInNeighbors(): DhtNodeRpcRemote | undefined {
192
- for (const contactId of this.nearbyContacts.getContactIds()) {
193
- if (!this.neighbors.get(toDhtAddressRaw(contactId)) && this.activeContacts.has(contactId)) {
194
- return this.nearbyContacts.getContact(contactId)!
195
- }
196
- }
197
- return undefined
198
- }
199
-
200
- removeContact(nodeId: DhtAddress): void {
201
- if (this.stopped) {
202
- return
203
- }
204
- logger.trace(`Removing contact ${nodeId}`)
205
- this.ringContacts.removeContact(this.nearbyContacts.getContact(nodeId))
206
- this.neighbors.remove(toDhtAddressRaw(nodeId))
207
- this.nearbyContacts.removeContact(nodeId)
208
- this.activeContacts.delete(nodeId)
209
- this.randomContacts.removeContact(nodeId)
210
- }
211
-
212
- removeNeighbor(nodeId: DhtAddress): void {
213
- this.neighbors.remove(toDhtAddressRaw(nodeId))
214
- }
215
-
216
- async pruneOfflineNodes(nodes: DhtNodeRpcRemote[]): Promise<void> {
217
- logger.trace('Pruning offline nodes', { nodes: nodes.length })
218
- const offlineNeighbors = await pingNodes(nodes, this.activeContacts)
219
- offlineNeighbors.forEach((offlineNeighbor) => {
220
- logger.trace('Removing offline node', { node: toNodeId(offlineNeighbor) })
221
- this.removeContact(toNodeId(offlineNeighbor))
222
- })
223
- }
224
-
225
- stop(): void {
226
- this.stopped = true
227
- this.neighbors.toArray().forEach((rpcRemote: DhtNodeRpcRemote) => {
228
- rpcRemote.leaveNotice()
229
- this.neighbors.remove(rpcRemote.id)
230
- })
231
- this.neighbors.removeAllListeners()
232
- this.ringContacts.getAllContacts().forEach((rpcRemote) => {
233
- rpcRemote.leaveNotice()
234
- this.ringContacts.removeContact(rpcRemote)
235
- })
236
- this.nearbyContacts.stop()
237
- this.randomContacts.stop()
238
- }
239
-
240
- getNearbyContacts(): ReadonlySortedContactList<DhtNodeRpcRemote> {
241
- return this.nearbyContacts
242
- }
243
-
244
- getClosestRingContactsTo(
245
- ringIdRaw: RingIdRaw,
246
- limit?: number,
247
- excludedIds?: Set<DhtAddress>
248
- ): { left: DhtNodeRpcRemote[], right: DhtNodeRpcRemote[] } {
249
- const closest = new RingContactList<DhtNodeRpcRemote>(ringIdRaw, excludedIds)
250
- this.ringContacts.getAllContacts().map((contact) => closest.addContact(contact))
251
- // TODO use options option or named constant?
252
- return closest.getClosestContacts(limit ?? 8)
253
- }
254
-
255
- getRandomContacts(): RandomContactList<DhtNodeRpcRemote> {
256
- return this.randomContacts
257
- }
258
-
259
- getRingContacts(): RingContactList<DhtNodeRpcRemote> {
260
- return this.ringContacts
261
- }
262
-
263
- getNearbyContactCount(excludedNodeIds?: Set<DhtAddress>): number {
264
- return this.nearbyContacts.getSize(excludedNodeIds)
265
- }
266
-
267
- getNeighborCount(): number {
268
- return this.neighbors.count()
269
- }
270
-
271
- getNeighbors(): readonly DhtNodeRpcRemote[] {
272
- return this.neighbors.toArray()
273
- }
274
-
275
- setContactActive(nodeId: DhtAddress): void {
276
- this.activeContacts.add(nodeId)
277
- }
278
-
279
- addContact(peerDescriptor: PeerDescriptor): void {
280
- if (this.stopped) {
281
- return
282
- }
283
- const nodeId = toNodeId(peerDescriptor)
284
- if (nodeId !== this.options.localNodeId) {
285
- logger.trace(`Adding new contact ${nodeId}`)
286
- const remote = this.options.createDhtNodeRpcRemote(peerDescriptor)
287
- const isInNeighbors = (this.neighbors.get(peerDescriptor.nodeId) !== null)
288
- const isInNearbyContacts = (this.nearbyContacts.getContact(nodeId) !== undefined)
289
- const isInRingContacts = this.ringContacts.getContact(peerDescriptor) !== undefined
290
-
291
- if (isInNeighbors || isInNearbyContacts) {
292
- this.randomContacts.addContact(remote)
293
- }
294
- if (!isInNeighbors) {
295
- this.neighbors.add(remote)
296
- }
297
- if (!isInNearbyContacts) {
298
- this.nearbyContacts.addContact(remote)
299
- }
300
- if (!isInRingContacts) {
301
- this.ringContacts.addContact(remote)
302
- }
303
- }
304
- }
305
- }
@@ -1,19 +0,0 @@
1
- import { PeerDescriptor } from '../../../generated/packages/dht/protos/DhtRpc'
2
- import { DhtAddress, toNodeId } from '../../identifiers'
3
-
4
- export class Contact {
5
-
6
- private peerDescriptor: PeerDescriptor
7
-
8
- constructor(peerDescriptor: PeerDescriptor) {
9
- this.peerDescriptor = peerDescriptor
10
- }
11
-
12
- public getPeerDescriptor(): PeerDescriptor {
13
- return this.peerDescriptor
14
- }
15
-
16
- public getNodeId(): DhtAddress {
17
- return toNodeId(this.peerDescriptor)
18
- }
19
- }
@@ -1,43 +0,0 @@
1
- import EventEmitter from 'eventemitter3'
2
- import { DhtAddress } from '../../identifiers'
3
-
4
- export interface Events<C> {
5
- contactRemoved: (removedContact: C) => void
6
- contactAdded: (contactAdded: C) => void
7
- }
8
-
9
- export class ContactList<C extends { getNodeId: () => DhtAddress }> extends EventEmitter<Events<C>> {
10
-
11
- protected contactsById: Map<DhtAddress, C> = new Map()
12
- // TODO move this to SortedContactList
13
- protected contactIds: DhtAddress[] = []
14
- protected localNodeId: DhtAddress
15
- protected maxSize: number
16
-
17
- constructor(
18
- localNodeId: DhtAddress,
19
- maxSize: number
20
- ) {
21
- super()
22
- this.localNodeId = localNodeId
23
- this.maxSize = maxSize
24
- }
25
-
26
- public getContact(id: DhtAddress): C | undefined {
27
- return this.contactsById.get(id)
28
- }
29
-
30
- public getSize(): number {
31
- return this.contactIds.length
32
- }
33
-
34
- public clear(): void {
35
- this.contactsById.clear()
36
- this.contactIds = []
37
- }
38
-
39
- public stop(): void {
40
- this.removeAllListeners()
41
- this.clear()
42
- }
43
- }