@libp2p/pnet 1.0.1 → 2.0.0-18dd3cb26

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.
@@ -1,8 +1,9 @@
1
1
  import type { Source } from 'it-stream-types';
2
+ import type { Uint8ArrayList } from 'uint8arraylist';
2
3
  /**
3
4
  * Creates a stream iterable to encrypt messages in a private network
4
5
  */
5
- export declare function createBoxStream(nonce: Uint8Array, psk: Uint8Array): (source: Source<Uint8Array>) => AsyncIterable<Uint8Array>;
6
+ export declare function createBoxStream(nonce: Uint8Array, psk: Uint8Array): (source: Source<Uint8Array | Uint8ArrayList>) => AsyncGenerator<Uint8Array | Uint8ArrayList>;
6
7
  /**
7
8
  * Creates a stream iterable to decrypt messages in a private network
8
9
  */
@@ -1 +1 @@
1
- {"version":3,"file":"crypto.d.ts","sourceRoot":"","sources":["../../src/crypto.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAA;AAE7C;;GAEG;AACH,wBAAgB,eAAe,CAAE,KAAK,EAAE,UAAU,EAAE,GAAG,EAAE,UAAU,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,UAAU,CAAC,KAAK,aAAa,CAAC,UAAU,CAAC,CAQ9H;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAAE,KAAK,EAAE,UAAU,EAAE,GAAG,EAAE,UAAU,YACnD,OAAO,UAAU,CAAC,+CAOnC;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAE,SAAS,EAAE,UAAU,GAAG;IAAE,GAAG,EAAE,MAAM,GAAG,SAAS,CAAC;IAAC,SAAS,EAAE,MAAM,GAAG,SAAS,CAAC;IAAC,GAAG,EAAE,UAAU,CAAA;CAAE,CAyB/H"}
1
+ {"version":3,"file":"crypto.d.ts","sourceRoot":"","sources":["../../src/crypto.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAA;AAC7C,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,gBAAgB,CAAA;AAEpD;;GAEG;AACH,wBAAgB,eAAe,CAAE,KAAK,EAAE,UAAU,EAAE,GAAG,EAAE,UAAU,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,UAAU,GAAG,cAAc,CAAC,KAAK,cAAc,CAAC,UAAU,GAAG,cAAc,CAAC,CAQjK;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAAE,KAAK,EAAE,UAAU,EAAE,GAAG,EAAE,UAAU,YACnD,OAAO,UAAU,CAAC,+CAOnC;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAE,SAAS,EAAE,UAAU,GAAG;IAAE,GAAG,EAAE,MAAM,GAAG,SAAS,CAAC;IAAC,SAAS,EAAE,MAAM,GAAG,SAAS,CAAC;IAAC,GAAG,EAAE,UAAU,CAAA;CAAE,CAyB/H"}
@@ -10,7 +10,7 @@ export function createBoxStream(nonce, psk) {
10
10
  const xor = xsalsa20(nonce, psk);
11
11
  return (source) => (async function* () {
12
12
  for await (const chunk of source) {
13
- yield Uint8Array.from(xor.update(chunk.slice()));
13
+ yield Uint8Array.from(xor.update(chunk.subarray()));
14
14
  }
15
15
  })();
16
16
  }
@@ -21,7 +21,7 @@ export function createUnboxStream(nonce, psk) {
21
21
  return (source) => (async function* () {
22
22
  const xor = xsalsa20(nonce, psk);
23
23
  for await (const chunk of source) {
24
- yield Uint8Array.from(xor.update(chunk.slice()));
24
+ yield Uint8Array.from(xor.update(chunk.subarray()));
25
25
  }
26
26
  })();
27
27
  }
@@ -1 +1 @@
1
- {"version":3,"file":"crypto.js","sourceRoot":"","sources":["../../src/crypto.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,IAAI,oBAAoB,EAAE,MAAM,yBAAyB,CAAA;AAC5E,OAAO,EAAE,QAAQ,IAAI,kBAAkB,EAAE,MAAM,uBAAuB,CAAA;AACtE,OAAO,QAAQ,MAAM,UAAU,CAAA;AAC/B,OAAO,KAAK,MAAM,MAAM,aAAa,CAAA;AACrC,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAG/C;;GAEG;AACH,MAAM,UAAU,eAAe,CAAE,KAAiB,EAAE,GAAe;IACjE,MAAM,GAAG,GAAG,QAAQ,CAAC,KAAK,EAAE,GAAG,CAAC,CAAA;IAEhC,OAAO,CAAC,MAA0B,EAAE,EAAE,CAAC,CAAC,KAAK,SAAU,CAAC;QACtD,IAAI,KAAK,EAAE,MAAM,KAAK,IAAI,MAAM,EAAE;YAChC,MAAM,UAAU,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,KAAK,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;SACjD;IACH,CAAC,CAAC,EAAE,CAAA;AACN,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,iBAAiB,CAAE,KAAiB,EAAE,GAAe;IACnE,OAAO,CAAC,MAA0B,EAAE,EAAE,CAAC,CAAC,KAAK,SAAU,CAAC;QACtD,MAAM,GAAG,GAAG,QAAQ,CAAC,KAAK,EAAE,GAAG,CAAC,CAAA;QAEhC,IAAI,KAAK,EAAE,MAAM,KAAK,IAAI,MAAM,EAAE;YAChC,MAAM,UAAU,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,KAAK,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;SACjD;IACH,CAAC,CAAC,EAAE,CAAA;AACN,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,WAAW,CAAE,SAAqB;IAChD,IAAI;QACF,0DAA0D;QAC1D,6DAA6D;QAC7D,yDAAyD;QACzD,2DAA2D;QAC3D,0BAA0B;QAC1B,MAAM,QAAQ,GAAG,kBAAkB,CAAC,SAAS,CAAC,CAAC,KAAK,CAAC,iBAAiB,CAAC,CAAA;QACvE,MAAM,MAAM,GAAG,QAAQ,CAAC,KAAK,EAAE,CAAA;QAC/B,MAAM,KAAK,GAAG,QAAQ,CAAC,KAAK,EAAE,CAAA;QAC9B,MAAM,SAAS,GAAG,QAAQ,CAAC,KAAK,EAAE,CAAA;QAClC,MAAM,GAAG,GAAG,oBAAoB,CAAC,SAAS,IAAI,EAAE,EAAE,QAAQ,CAAC,CAAA;QAE3D,IAAI,GAAG,CAAC,UAAU,KAAK,UAAU,EAAE;YACjC,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,WAAW,CAAC,CAAA;SACpC;QAED,OAAO;YACL,GAAG,EAAE,MAAM;YACX,SAAS,EAAE,KAAK;YAChB,GAAG;SACJ,CAAA;KACF;IAAC,OAAO,GAAQ,EAAE;QACjB,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,WAAW,CAAC,CAAA;KACpC;AACH,CAAC"}
1
+ {"version":3,"file":"crypto.js","sourceRoot":"","sources":["../../src/crypto.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,IAAI,oBAAoB,EAAE,MAAM,yBAAyB,CAAA;AAC5E,OAAO,EAAE,QAAQ,IAAI,kBAAkB,EAAE,MAAM,uBAAuB,CAAA;AACtE,OAAO,QAAQ,MAAM,UAAU,CAAA;AAC/B,OAAO,KAAK,MAAM,MAAM,aAAa,CAAA;AACrC,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAI/C;;GAEG;AACH,MAAM,UAAU,eAAe,CAAE,KAAiB,EAAE,GAAe;IACjE,MAAM,GAAG,GAAG,QAAQ,CAAC,KAAK,EAAE,GAAG,CAAC,CAAA;IAEhC,OAAO,CAAC,MAA2C,EAAE,EAAE,CAAC,CAAC,KAAK,SAAU,CAAC;QACvE,IAAI,KAAK,EAAE,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;YACjC,MAAM,UAAU,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,KAAK,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAA;QACrD,CAAC;IACH,CAAC,CAAC,EAAE,CAAA;AACN,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,iBAAiB,CAAE,KAAiB,EAAE,GAAe;IACnE,OAAO,CAAC,MAA0B,EAAE,EAAE,CAAC,CAAC,KAAK,SAAU,CAAC;QACtD,MAAM,GAAG,GAAG,QAAQ,CAAC,KAAK,EAAE,GAAG,CAAC,CAAA;QAEhC,IAAI,KAAK,EAAE,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;YACjC,MAAM,UAAU,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,KAAK,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAA;QACrD,CAAC;IACH,CAAC,CAAC,EAAE,CAAA;AACN,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,WAAW,CAAE,SAAqB;IAChD,IAAI,CAAC;QACH,0DAA0D;QAC1D,6DAA6D;QAC7D,yDAAyD;QACzD,2DAA2D;QAC3D,0BAA0B;QAC1B,MAAM,QAAQ,GAAG,kBAAkB,CAAC,SAAS,CAAC,CAAC,KAAK,CAAC,iBAAiB,CAAC,CAAA;QACvE,MAAM,MAAM,GAAG,QAAQ,CAAC,KAAK,EAAE,CAAA;QAC/B,MAAM,KAAK,GAAG,QAAQ,CAAC,KAAK,EAAE,CAAA;QAC9B,MAAM,SAAS,GAAG,QAAQ,CAAC,KAAK,EAAE,CAAA;QAClC,MAAM,GAAG,GAAG,oBAAoB,CAAC,SAAS,IAAI,EAAE,EAAE,QAAQ,CAAC,CAAA;QAE3D,IAAI,GAAG,CAAC,UAAU,KAAK,UAAU,EAAE,CAAC;YAClC,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,WAAW,CAAC,CAAA;QACrC,CAAC;QAED,OAAO;YACL,GAAG,EAAE,MAAM;YACX,SAAS,EAAE,KAAK;YAChB,GAAG;SACJ,CAAA;IACH,CAAC;IAAC,OAAO,GAAQ,EAAE,CAAC;QAClB,MAAM,IAAI,KAAK,CAAC,MAAM,CAAC,WAAW,CAAC,CAAA;IACrC,CAAC;AACH,CAAC"}
@@ -3,5 +3,4 @@ export declare const INVALID_PSK = "Your private shared key is invalid";
3
3
  export declare const NO_LOCAL_ID = "No local private key provided";
4
4
  export declare const NO_HANDSHAKE_CONNECTION = "No connection for the handshake provided";
5
5
  export declare const STREAM_ENDED = "Stream ended prematurely";
6
- export declare const ERR_INVALID_PARAMETERS = "ERR_INVALID_PARAMETERS";
7
6
  //# sourceMappingURL=errors.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/errors.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,YAAY,gCAAgC,CAAA;AACzD,eAAO,MAAM,WAAW,uCAAuC,CAAA;AAC/D,eAAO,MAAM,WAAW,kCAAkC,CAAA;AAC1D,eAAO,MAAM,uBAAuB,6CAA6C,CAAA;AACjF,eAAO,MAAM,YAAY,6BAA6B,CAAA;AACtD,eAAO,MAAM,sBAAsB,2BAA2B,CAAA"}
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/errors.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,YAAY,gCAAgC,CAAA;AACzD,eAAO,MAAM,WAAW,uCAAuC,CAAA;AAC/D,eAAO,MAAM,WAAW,kCAAkC,CAAA;AAC1D,eAAO,MAAM,uBAAuB,6CAA6C,CAAA;AACjF,eAAO,MAAM,YAAY,6BAA6B,CAAA"}
@@ -3,5 +3,4 @@ export const INVALID_PSK = 'Your private shared key is invalid';
3
3
  export const NO_LOCAL_ID = 'No local private key provided';
4
4
  export const NO_HANDSHAKE_CONNECTION = 'No connection for the handshake provided';
5
5
  export const STREAM_ENDED = 'Stream ended prematurely';
6
- export const ERR_INVALID_PARAMETERS = 'ERR_INVALID_PARAMETERS';
7
6
  //# sourceMappingURL=errors.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"errors.js","sourceRoot":"","sources":["../../src/errors.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,YAAY,GAAG,6BAA6B,CAAA;AACzD,MAAM,CAAC,MAAM,WAAW,GAAG,oCAAoC,CAAA;AAC/D,MAAM,CAAC,MAAM,WAAW,GAAG,+BAA+B,CAAA;AAC1D,MAAM,CAAC,MAAM,uBAAuB,GAAG,0CAA0C,CAAA;AACjF,MAAM,CAAC,MAAM,YAAY,GAAG,0BAA0B,CAAA;AACtD,MAAM,CAAC,MAAM,sBAAsB,GAAG,wBAAwB,CAAA"}
1
+ {"version":3,"file":"errors.js","sourceRoot":"","sources":["../../src/errors.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,YAAY,GAAG,6BAA6B,CAAA;AACzD,MAAM,CAAC,MAAM,WAAW,GAAG,oCAAoC,CAAA;AAC/D,MAAM,CAAC,MAAM,WAAW,GAAG,+BAA+B,CAAA;AAC1D,MAAM,CAAC,MAAM,uBAAuB,GAAG,0CAA0C,CAAA;AACjF,MAAM,CAAC,MAAM,YAAY,GAAG,0BAA0B,CAAA"}
@@ -45,7 +45,7 @@
45
45
  *
46
46
  * ### Programmatically
47
47
  *
48
- * ```js
48
+ * ```TypeScript
49
49
  * import fs from 'fs'
50
50
  * import { generateKey } from '@libp2p/pnet'
51
51
  *
@@ -55,12 +55,19 @@
55
55
  * fs.writeFileSync('swarm.key', swarmKey)
56
56
  * ```
57
57
  */
58
- import type { ComponentLogger } from '@libp2p/interface';
59
- import type { ConnectionProtector } from '@libp2p/interface/connection';
58
+ import type { ComponentLogger, ConnectionProtector } from '@libp2p/interface';
60
59
  export { generateKey } from './key-generator.js';
61
60
  export interface ProtectorInit {
62
- enabled?: boolean;
61
+ /**
62
+ * A pre-shared key. This must be the same byte value for all peers in the
63
+ * swarm in order for them to communicate.
64
+ */
63
65
  psk: Uint8Array;
66
+ /**
67
+ * The initial nonce exchange must complete within this many milliseconds
68
+ * (default: 1000)
69
+ */
70
+ timeout?: number;
64
71
  }
65
72
  export interface ProtectorComponents {
66
73
  logger: ComponentLogger;
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwDG;AAeH,OAAO,KAAK,EAAE,eAAe,EAAU,MAAM,mBAAmB,CAAA;AAChE,OAAO,KAAK,EAAE,mBAAmB,EAAuB,MAAM,8BAA8B,CAAA;AAE5F,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAA;AAEhD,MAAM,WAAW,aAAa;IAC5B,OAAO,CAAC,EAAE,OAAO,CAAA;IACjB,GAAG,EAAE,UAAU,CAAA;CAChB;AAED,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,eAAe,CAAA;CACxB;AA6ED,wBAAgB,YAAY,CAAE,IAAI,EAAE,aAAa,GAAG,CAAC,UAAU,EAAE,mBAAmB,KAAK,mBAAmB,CAE3G"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwDG;AAcH,OAAO,KAAK,EAAE,eAAe,EAAU,mBAAmB,EAAuB,MAAM,mBAAmB,CAAA;AAG1G,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAA;AAEhD,MAAM,WAAW,aAAa;IAC5B;;;OAGG;IACH,GAAG,EAAE,UAAU,CAAA;IACf;;;OAGG;IACH,OAAO,CAAC,EAAE,MAAM,CAAA;CACjB;AAED,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,eAAe,CAAA;CACxB;AA2ED,wBAAgB,YAAY,CAAE,IAAI,EAAE,aAAa,GAAG,CAAC,UAAU,EAAE,mBAAmB,KAAK,mBAAmB,CAE3G"}
package/dist/src/index.js CHANGED
@@ -45,7 +45,7 @@
45
45
  *
46
46
  * ### Programmatically
47
47
  *
48
- * ```js
48
+ * ```TypeScript
49
49
  * import fs from 'fs'
50
50
  * import { generateKey } from '@libp2p/pnet'
51
51
  *
@@ -56,66 +56,60 @@
56
56
  * ```
57
57
  */
58
58
  import { randomBytes } from '@libp2p/crypto';
59
- import { CodeError } from '@libp2p/interface/errors';
60
- import { handshake } from 'it-handshake';
59
+ import { InvalidParametersError } from '@libp2p/interface';
60
+ import { byteStream } from 'it-byte-stream';
61
61
  import map from 'it-map';
62
62
  import { duplexPair } from 'it-pair/duplex';
63
63
  import { pipe } from 'it-pipe';
64
64
  import { createBoxStream, createUnboxStream, decodeV1PSK } from './crypto.js';
65
- import * as Errors from './errors.js';
66
65
  import { NONCE_LENGTH } from './key-generator.js';
67
66
  export { generateKey } from './key-generator.js';
68
67
  class PreSharedKeyConnectionProtector {
69
68
  tag;
70
69
  log;
71
70
  psk;
72
- enabled;
71
+ timeout;
73
72
  /**
74
73
  * Takes a Private Shared Key (psk) and provides a `protect` method
75
74
  * for wrapping existing connections in a private encryption stream.
76
75
  */
77
76
  constructor(components, init) {
78
77
  this.log = components.logger.forComponent('libp2p:pnet');
79
- this.enabled = init.enabled !== false;
80
- if (this.enabled) {
81
- const decodedPSK = decodeV1PSK(init.psk);
82
- this.psk = decodedPSK.psk;
83
- this.tag = decodedPSK.tag ?? '';
84
- }
85
- else {
86
- this.psk = new Uint8Array();
87
- this.tag = '';
88
- }
78
+ this.timeout = init.timeout ?? 1000;
79
+ const decodedPSK = decodeV1PSK(init.psk);
80
+ this.psk = decodedPSK.psk;
81
+ this.tag = decodedPSK.tag ?? '';
89
82
  }
83
+ [Symbol.toStringTag] = '@libp2p/pnet';
90
84
  /**
91
85
  * Takes a given Connection and creates a private encryption stream
92
86
  * between its two peers from the PSK the Protector instance was
93
87
  * created with.
94
88
  */
95
89
  async protect(connection) {
96
- if (!this.enabled) {
97
- return connection;
98
- }
99
90
  if (connection == null) {
100
- throw new CodeError(Errors.NO_HANDSHAKE_CONNECTION, Errors.ERR_INVALID_PARAMETERS);
91
+ throw new InvalidParametersError('No connection for the handshake provided');
101
92
  }
102
93
  // Exchange nonces
103
94
  this.log('protecting the connection');
104
95
  const localNonce = randomBytes(NONCE_LENGTH);
105
- const shake = handshake(connection);
106
- shake.write(localNonce);
107
- const result = await shake.reader.next(NONCE_LENGTH);
108
- if (result.value == null) {
109
- throw new CodeError(Errors.STREAM_ENDED, Errors.ERR_INVALID_PARAMETERS);
110
- }
111
- const remoteNonce = result.value.slice();
112
- shake.rest();
96
+ const signal = AbortSignal.timeout(this.timeout);
97
+ const bytes = byteStream(connection);
98
+ const [, result] = await Promise.all([
99
+ bytes.write(localNonce, {
100
+ signal
101
+ }),
102
+ bytes.read(NONCE_LENGTH, {
103
+ signal
104
+ })
105
+ ]);
106
+ const remoteNonce = result.subarray();
113
107
  // Create the boxing/unboxing pipe
114
108
  this.log('exchanged nonces');
115
109
  const [internal, external] = duplexPair();
116
110
  pipe(external,
117
111
  // Encrypt all outbound traffic
118
- createBoxStream(localNonce, this.psk), shake.stream, (source) => map(source, (buf) => buf.subarray()),
112
+ createBoxStream(localNonce, this.psk), bytes.unwrap(), (source) => map(source, (buf) => buf.subarray()),
119
113
  // Decrypt all inbound traffic
120
114
  createUnboxStream(remoteNonce, this.psk), external).catch(this.log.error);
121
115
  return {
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"key-generator.js","sourceRoot":"","sources":["../../src/key-generator.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAA;AAC5C,OAAO,EAAE,UAAU,IAAI,oBAAoB,EAAE,MAAM,yBAAyB,CAAA;AAC5E,OAAO,EAAE,QAAQ,IAAI,kBAAkB,EAAE,MAAM,uBAAuB,CAAA;AAEtE;;;;;GAKG;AACH,MAAM,UAAU,WAAW,CAAE,KAAsC;IACjE,MAAM,GAAG,GAAG,kBAAkB,CAAC,WAAW,CAAC,UAAU,CAAC,EAAE,QAAQ,CAAC,CAAA;IACjE,MAAM,GAAG,GAAG,oBAAoB,CAAC,mCAAmC,GAAG,GAAG,CAAC,CAAA;IAE3E,IAAI,KAAK,YAAY,UAAU,EAAE;QAC/B,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,CAAA;KACf;SAAM;QACL,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;KACjB;AACH,CAAC;AAED,MAAM,CAAC,MAAM,YAAY,GAAG,EAAE,CAAA;AAC9B,MAAM,CAAC,MAAM,UAAU,GAAG,EAAE,CAAA"}
1
+ {"version":3,"file":"key-generator.js","sourceRoot":"","sources":["../../src/key-generator.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAA;AAC5C,OAAO,EAAE,UAAU,IAAI,oBAAoB,EAAE,MAAM,yBAAyB,CAAA;AAC5E,OAAO,EAAE,QAAQ,IAAI,kBAAkB,EAAE,MAAM,uBAAuB,CAAA;AAEtE;;;;;GAKG;AACH,MAAM,UAAU,WAAW,CAAE,KAAsC;IACjE,MAAM,GAAG,GAAG,kBAAkB,CAAC,WAAW,CAAC,UAAU,CAAC,EAAE,QAAQ,CAAC,CAAA;IACjE,MAAM,GAAG,GAAG,oBAAoB,CAAC,mCAAmC,GAAG,GAAG,CAAC,CAAA;IAE3E,IAAI,KAAK,YAAY,UAAU,EAAE,CAAC;QAChC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,CAAA;IAChB,CAAC;SAAM,CAAC;QACN,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;IAClB,CAAC;AACH,CAAC;AAED,MAAM,CAAC,MAAM,YAAY,GAAG,EAAE,CAAA;AAC9B,MAAM,CAAC,MAAM,UAAU,GAAG,EAAE,CAAA"}
package/package.json CHANGED
@@ -1,9 +1,9 @@
1
1
  {
2
2
  "name": "@libp2p/pnet",
3
- "version": "1.0.1",
3
+ "version": "2.0.0-18dd3cb26",
4
4
  "description": "Implementation of Connection protection management via a shared secret",
5
5
  "license": "Apache-2.0 OR MIT",
6
- "homepage": "https://github.com/libp2p/js-libp2p/tree/master/packages/pnet#readme",
6
+ "homepage": "https://github.com/libp2p/js-libp2p/tree/main/packages/pnet#readme",
7
7
  "repository": {
8
8
  "type": "git",
9
9
  "url": "git+https://github.com/libp2p/js-libp2p.git"
@@ -11,6 +11,10 @@
11
11
  "bugs": {
12
12
  "url": "https://github.com/libp2p/js-libp2p/issues"
13
13
  },
14
+ "publishConfig": {
15
+ "access": "public",
16
+ "provenance": true
17
+ },
14
18
  "type": "module",
15
19
  "types": "./dist/src/index.d.ts",
16
20
  "files": [
@@ -42,26 +46,29 @@
42
46
  "test:firefox": "aegir test -t browser -- --browser firefox",
43
47
  "test:firefox-webworker": "aegir test -t webworker -- --browser firefox",
44
48
  "test:node": "aegir test -t node --cov",
45
- "dep-check": "aegir dep-check"
49
+ "dep-check": "aegir dep-check",
50
+ "doc-check": "aegir doc-check"
46
51
  },
47
52
  "dependencies": {
48
- "@libp2p/crypto": "^2.0.5",
49
- "@libp2p/interface": "^0.1.3",
50
- "it-handshake": "^4.1.3",
51
- "it-map": "^3.0.4",
53
+ "@libp2p/crypto": "5.0.0-18dd3cb26",
54
+ "@libp2p/interface": "2.0.0-18dd3cb26",
55
+ "it-byte-stream": "^1.0.10",
56
+ "it-map": "^3.1.0",
52
57
  "it-pair": "^2.0.6",
53
58
  "it-pipe": "^3.0.1",
54
59
  "it-stream-types": "^2.0.1",
55
- "uint8arrays": "^4.0.6",
56
- "xsalsa20": "^1.1.0"
60
+ "uint8arraylist": "^2.4.8",
61
+ "uint8arrays": "^5.1.0",
62
+ "xsalsa20": "^1.2.0"
57
63
  },
58
64
  "devDependencies": {
59
- "@libp2p/interface-compliance-tests": "^4.1.1",
60
- "@libp2p/logger": "^3.1.0",
61
- "@libp2p/peer-id-factory": "^3.0.5",
62
- "@multiformats/multiaddr": "^12.1.10",
63
- "@types/xsalsa20": "^1.1.0",
64
- "aegir": "^41.0.2",
65
- "it-all": "^3.0.3"
66
- }
65
+ "@libp2p/interface-compliance-tests": "6.0.0-18dd3cb26",
66
+ "@libp2p/logger": "5.0.0-18dd3cb26",
67
+ "@libp2p/peer-id": "5.0.0-18dd3cb26",
68
+ "@multiformats/multiaddr": "^12.2.3",
69
+ "@types/xsalsa20": "^1.1.3",
70
+ "aegir": "^44.0.1",
71
+ "it-all": "^3.0.6"
72
+ },
73
+ "sideEffects": false
67
74
  }
package/src/crypto.ts CHANGED
@@ -4,16 +4,17 @@ import xsalsa20 from 'xsalsa20'
4
4
  import * as Errors from './errors.js'
5
5
  import { KEY_LENGTH } from './key-generator.js'
6
6
  import type { Source } from 'it-stream-types'
7
+ import type { Uint8ArrayList } from 'uint8arraylist'
7
8
 
8
9
  /**
9
10
  * Creates a stream iterable to encrypt messages in a private network
10
11
  */
11
- export function createBoxStream (nonce: Uint8Array, psk: Uint8Array): (source: Source<Uint8Array>) => AsyncIterable<Uint8Array> {
12
+ export function createBoxStream (nonce: Uint8Array, psk: Uint8Array): (source: Source<Uint8Array | Uint8ArrayList>) => AsyncGenerator<Uint8Array | Uint8ArrayList> {
12
13
  const xor = xsalsa20(nonce, psk)
13
14
 
14
- return (source: Source<Uint8Array>) => (async function * () {
15
+ return (source: Source<Uint8Array | Uint8ArrayList>) => (async function * () {
15
16
  for await (const chunk of source) {
16
- yield Uint8Array.from(xor.update(chunk.slice()))
17
+ yield Uint8Array.from(xor.update(chunk.subarray()))
17
18
  }
18
19
  })()
19
20
  }
@@ -26,7 +27,7 @@ export function createUnboxStream (nonce: Uint8Array, psk: Uint8Array) {
26
27
  const xor = xsalsa20(nonce, psk)
27
28
 
28
29
  for await (const chunk of source) {
29
- yield Uint8Array.from(xor.update(chunk.slice()))
30
+ yield Uint8Array.from(xor.update(chunk.subarray()))
30
31
  }
31
32
  })()
32
33
  }
package/src/errors.ts CHANGED
@@ -3,4 +3,3 @@ export const INVALID_PSK = 'Your private shared key is invalid'
3
3
  export const NO_LOCAL_ID = 'No local private key provided'
4
4
  export const NO_HANDSHAKE_CONNECTION = 'No connection for the handshake provided'
5
5
  export const STREAM_ENDED = 'Stream ended prematurely'
6
- export const ERR_INVALID_PARAMETERS = 'ERR_INVALID_PARAMETERS'
package/src/index.ts CHANGED
@@ -45,7 +45,7 @@
45
45
  *
46
46
  * ### Programmatically
47
47
  *
48
- * ```js
48
+ * ```TypeScript
49
49
  * import fs from 'fs'
50
50
  * import { generateKey } from '@libp2p/pnet'
51
51
  *
@@ -57,8 +57,8 @@
57
57
  */
58
58
 
59
59
  import { randomBytes } from '@libp2p/crypto'
60
- import { CodeError } from '@libp2p/interface/errors'
61
- import { handshake } from 'it-handshake'
60
+ import { InvalidParametersError } from '@libp2p/interface'
61
+ import { byteStream } from 'it-byte-stream'
62
62
  import map from 'it-map'
63
63
  import { duplexPair } from 'it-pair/duplex'
64
64
  import { pipe } from 'it-pipe'
@@ -67,16 +67,23 @@ import {
67
67
  createUnboxStream,
68
68
  decodeV1PSK
69
69
  } from './crypto.js'
70
- import * as Errors from './errors.js'
71
70
  import { NONCE_LENGTH } from './key-generator.js'
72
- import type { ComponentLogger, Logger } from '@libp2p/interface'
73
- import type { ConnectionProtector, MultiaddrConnection } from '@libp2p/interface/connection'
71
+ import type { ComponentLogger, Logger, ConnectionProtector, MultiaddrConnection } from '@libp2p/interface'
72
+ import type { Uint8ArrayList } from 'uint8arraylist'
74
73
 
75
74
  export { generateKey } from './key-generator.js'
76
75
 
77
76
  export interface ProtectorInit {
78
- enabled?: boolean
77
+ /**
78
+ * A pre-shared key. This must be the same byte value for all peers in the
79
+ * swarm in order for them to communicate.
80
+ */
79
81
  psk: Uint8Array
82
+ /**
83
+ * The initial nonce exchange must complete within this many milliseconds
84
+ * (default: 1000)
85
+ */
86
+ timeout?: number
80
87
  }
81
88
 
82
89
  export interface ProtectorComponents {
@@ -87,7 +94,7 @@ class PreSharedKeyConnectionProtector implements ConnectionProtector {
87
94
  public tag: string
88
95
  private readonly log: Logger
89
96
  private readonly psk: Uint8Array
90
- private readonly enabled: boolean
97
+ private readonly timeout: number
91
98
 
92
99
  /**
93
100
  * Takes a Private Shared Key (psk) and provides a `protect` method
@@ -95,56 +102,54 @@ class PreSharedKeyConnectionProtector implements ConnectionProtector {
95
102
  */
96
103
  constructor (components: ProtectorComponents, init: ProtectorInit) {
97
104
  this.log = components.logger.forComponent('libp2p:pnet')
98
- this.enabled = init.enabled !== false
99
-
100
- if (this.enabled) {
101
- const decodedPSK = decodeV1PSK(init.psk)
102
- this.psk = decodedPSK.psk
103
- this.tag = decodedPSK.tag ?? ''
104
- } else {
105
- this.psk = new Uint8Array()
106
- this.tag = ''
107
- }
105
+ this.timeout = init.timeout ?? 1000
106
+
107
+ const decodedPSK = decodeV1PSK(init.psk)
108
+ this.psk = decodedPSK.psk
109
+ this.tag = decodedPSK.tag ?? ''
108
110
  }
109
111
 
112
+ readonly [Symbol.toStringTag] = '@libp2p/pnet'
113
+
110
114
  /**
111
115
  * Takes a given Connection and creates a private encryption stream
112
116
  * between its two peers from the PSK the Protector instance was
113
117
  * created with.
114
118
  */
115
119
  async protect (connection: MultiaddrConnection): Promise<MultiaddrConnection> {
116
- if (!this.enabled) {
117
- return connection
118
- }
119
-
120
120
  if (connection == null) {
121
- throw new CodeError(Errors.NO_HANDSHAKE_CONNECTION, Errors.ERR_INVALID_PARAMETERS)
121
+ throw new InvalidParametersError('No connection for the handshake provided')
122
122
  }
123
123
 
124
124
  // Exchange nonces
125
125
  this.log('protecting the connection')
126
126
  const localNonce = randomBytes(NONCE_LENGTH)
127
127
 
128
- const shake = handshake(connection)
129
- shake.write(localNonce)
128
+ const signal = AbortSignal.timeout(this.timeout)
130
129
 
131
- const result = await shake.reader.next(NONCE_LENGTH)
130
+ const bytes = byteStream(connection)
132
131
 
133
- if (result.value == null) {
134
- throw new CodeError(Errors.STREAM_ENDED, Errors.ERR_INVALID_PARAMETERS)
135
- }
132
+ const [
133
+ , result
134
+ ] = await Promise.all([
135
+ bytes.write(localNonce, {
136
+ signal
137
+ }),
138
+ bytes.read(NONCE_LENGTH, {
139
+ signal
140
+ })
141
+ ])
136
142
 
137
- const remoteNonce = result.value.slice()
138
- shake.rest()
143
+ const remoteNonce = result.subarray()
139
144
 
140
145
  // Create the boxing/unboxing pipe
141
146
  this.log('exchanged nonces')
142
- const [internal, external] = duplexPair<Uint8Array>()
147
+ const [internal, external] = duplexPair<Uint8Array | Uint8ArrayList>()
143
148
  pipe(
144
149
  external,
145
150
  // Encrypt all outbound traffic
146
151
  createBoxStream(localNonce, this.psk),
147
- shake.stream,
152
+ bytes.unwrap(),
148
153
  (source) => map(source, (buf) => buf.subarray()),
149
154
  // Decrypt all inbound traffic
150
155
  createUnboxStream(remoteNonce, this.psk),