From 88d534e4a5edaf90fcbb75e11d10e96d87736810 Mon Sep 17 00:00:00 2001 From: Pavel Murygin Date: Thu, 4 Mar 2021 13:48:01 +0300 Subject: [PATCH] Checking if the particle is sent not to the relay which the client is connected to. If not an error is thrown --- src/api.ts | 2 +- src/api.unstable.ts | 2 +- src/internal/ClientImpl.ts | 2 +- src/internal/RequestFlow.ts | 35 +++++++++++++++++++++++++++-------- 4 files changed, 30 insertions(+), 11 deletions(-) diff --git a/src/api.ts b/src/api.ts index 00503d84..dac22011 100644 --- a/src/api.ts +++ b/src/api.ts @@ -13,7 +13,7 @@ export interface FluenceClient { /** * { string } Gets the base58 representation of the current peer id. Read only */ - readonly relayPeerId: PeerIdB58; + readonly relayPeerId: PeerIdB58 | undefined; /** * { string } Gets the base58 representation of the connected relay's peer id. Read only diff --git a/src/api.unstable.ts b/src/api.unstable.ts index 7b586c21..1f5ec873 100644 --- a/src/api.unstable.ts +++ b/src/api.unstable.ts @@ -17,7 +17,7 @@ export interface FluenceClient { /** * { string } Gets the base58 representation of the current peer id. Read only */ - readonly relayPeerId: PeerIdB58; + readonly relayPeerId: PeerIdB58 | undefined; /** * { string } Gets the base58 representation of the connected relay's peer id. Read only diff --git a/src/internal/ClientImpl.ts b/src/internal/ClientImpl.ts index 9d6d47c7..f35b2c2c 100644 --- a/src/internal/ClientImpl.ts +++ b/src/internal/ClientImpl.ts @@ -133,7 +133,7 @@ export class ClientImpl implements FluenceClient { private async processRequest(request: RequestFlow): Promise { try { this.currentRequestId = request.id; - request.execute(this.interpreter, this.connection); + request.execute(this.interpreter, this.connection, this.relayPeerId); } catch (err) { log.error('particle processing failed: ' + err); } finally { diff --git a/src/internal/RequestFlow.ts b/src/internal/RequestFlow.ts index 16d2fe62..f77f218d 100644 --- a/src/internal/RequestFlow.ts +++ b/src/internal/RequestFlow.ts @@ -2,7 +2,7 @@ import log, { trace } from 'loglevel'; import PeerId from 'peer-id'; import { AquamarineInterpreter } from './aqua/interpreter'; import { AquaCallHandler } from './AquaHandler'; -import { InterpreterOutcome } from './commonTypes'; +import { InterpreterOutcome, PeerIdB58 } from './commonTypes'; import { FluenceConnection } from './FluenceConnection'; import { Particle, genUUID, logParticle } from './particle'; @@ -27,6 +27,7 @@ export class RequestFlow { readonly handler = new AquaCallHandler(); ttl: number = DEFAULT_TTL; + relayPeerId?: PeerIdB58; static createExternal(particle: Particle): RequestFlow { const res = new RequestFlow(true, particle.id, particle.script); @@ -56,7 +57,7 @@ export class RequestFlow { this.onErrorHandlers.push(handler); } - async execute(interpreter: AquamarineInterpreter, connection: FluenceConnection) { + async execute(interpreter: AquamarineInterpreter, connection: FluenceConnection, relayPeerId?: PeerIdB58) { if (this.hasExpired()) { return; } @@ -76,14 +77,32 @@ export class RequestFlow { ); } - // do nothing if there is no `next_peer_pks` or if client isn't connected to the network - if (interpreterOutcome.next_peer_pks.length > 0) { - if (!connection) { - log.error('Cannot send particle: non connected'); - } + const nextPeers = interpreterOutcome.next_peer_pks; - this.sendIntoConnection(connection); + // do nothing if there are no peers to send particle further + if (nextPeers.length === 0) { + return; } + + // we only expect a single possible peer id to send particle further + if (nextPeers.length > 1) { + throw new Error( + 'Particle is expected to be sent to only the single peer (relay which client is connected to)', + ); + } + + // this peer id must be the relay, the client is connected to + if (!relayPeerId || nextPeers[0] !== relayPeerId) { + throw new Error( + 'Particle is expected to be sent to only the single peer (relay which client is connected to)', + ); + } + + if (!connection) { + throw new Error('Cannot send particle: non connected'); + } + + this.sendIntoConnection(connection); } async initState(peerId: PeerId): Promise {