fix: replace node buffers with uint8arrays (#730)

* fix: replace node buffers with uint8arrays

Upgrades all deps and replaces all use of node Buffers with Uint8Arrays

BREAKING CHANGES:

- All deps used by this module now use Uint8Arrays in place of node Buffers

* chore: browser fixes

* chore: remove .only

* chore: stringify uint8array before parsing

* chore: update interop suite

* chore: remove ts from build command

* chore: update deps

* fix: update records to use uint8array

* chore: fix lint

* chore: update deps

Co-authored-by: Jacob Heun <jacobheun@gmail.com>
This commit is contained in:
Alex Potsides 2020-08-24 11:58:02 +01:00 committed by GitHub
parent 02b6248aa3
commit 507f8c441c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
46 changed files with 283 additions and 270 deletions

View File

@ -49,5 +49,11 @@ module.exports = {
hooks: { hooks: {
pre: before, pre: before,
post: after post: after
},
webpack: {
node: {
// needed by bcrypto
Buffer: true
}
} }
} }

View File

@ -585,7 +585,7 @@ Writes a value to a key in the DHT.
| Name | Type | Description | | Name | Type | Description |
|------|------|-------------| |------|------|-------------|
| key | `string` | key to add to the dht | | key | `string` | key to add to the dht |
| value | `Buffer` | value to add to the dht | | value | `Uint8Array` | value to add to the dht |
| [options] | `object` | put options | | [options] | `object` | put options |
| [options.minPeers] | `number` | minimum number of peers required to successfully put (default: closestPeers.length) | | [options.minPeers] | `number` | minimum number of peers required to successfully put (default: closestPeers.length) |
@ -600,7 +600,7 @@ Writes a value to a key in the DHT.
```js ```js
// ... // ...
const key = '/key' const key = '/key'
const value = Buffer.from('oh hello there') const value = uint8ArrayFromString('oh hello there')
await libp2p.contentRouting.put(key, value) await libp2p.contentRouting.put(key, value)
``` ```
@ -623,7 +623,7 @@ Queries the DHT for a value stored for a given key.
| Type | Description | | Type | Description |
|------|-------------| |------|-------------|
| `Promise<Buffer>` | Value obtained from the DHT | | `Promise<Uint8Array>` | Value obtained from the DHT |
#### Example #### Example
@ -653,7 +653,7 @@ Queries the DHT for the n values stored for the given key (without sorting).
| Type | Description | | Type | Description |
|------|-------------| |------|-------------|
| `Promise<Array<{from: PeerId, val: Buffer}>>` | Array of records obtained from the DHT | | `Promise<Array<{from: PeerId, val: Uint8Array}>>` | Array of records obtained from the DHT |
#### Example #### Example
@ -970,7 +970,7 @@ Delete the provided peer from the book.
```js ```js
peerStore.metadataBook.delete(peerId) peerStore.metadataBook.delete(peerId)
// false // false
peerStore.metadataBook.set(peerId, 'nickname', Buffer.from('homePeer')) peerStore.metadataBook.set(peerId, 'nickname', uint8ArrayFromString('homePeer'))
peerStore.metadataBook.delete(peerId) peerStore.metadataBook.delete(peerId)
// true // true
``` ```
@ -999,7 +999,7 @@ Deletes the provided peer metadata key-value pair from the book.
```js ```js
peerStore.metadataBook.deleteValue(peerId, 'location') peerStore.metadataBook.deleteValue(peerId, 'location')
// false // false
peerStore.metadataBook.set(peerId, 'location', Buffer.from('Berlin')) peerStore.metadataBook.set(peerId, 'location', uint8ArrayFromString('Berlin'))
peerStore.metadataBook.deleteValue(peerId, 'location') peerStore.metadataBook.deleteValue(peerId, 'location')
// true // true
``` ```
@ -1020,14 +1020,14 @@ Get the known metadata of a provided peer.
| Type | Description | | Type | Description |
|------|-------------| |------|-------------|
| `Map<string, Buffer>` | Peer Metadata | | `Map<string, Uint8Array>` | Peer Metadata |
#### Example #### Example
```js ```js
peerStore.metadataBook.get(peerId) peerStore.metadataBook.get(peerId)
// undefined // undefined
peerStore.metadataBook.set(peerId, 'location', Buffer.from('Berlin')) peerStore.metadataBook.set(peerId, 'location', uint8ArrayFromString('Berlin'))
peerStore.metadataBook.get(peerId) peerStore.metadataBook.get(peerId)
// Metadata Map // Metadata Map
``` ```
@ -1049,14 +1049,14 @@ Get specific metadata of a provided peer.
| Type | Description | | Type | Description |
|------|-------------| |------|-------------|
| `Map<string, Buffer>` | Peer Metadata | | `Map<string, Uint8Array>` | Peer Metadata |
#### Example #### Example
```js ```js
peerStore.metadataBook.getValue(peerId, 'location') peerStore.metadataBook.getValue(peerId, 'location')
// undefined // undefined
peerStore.metadataBook.set(peerId, 'location', Buffer.from('Berlin')) peerStore.metadataBook.set(peerId, 'location', uint8ArrayFromString('Berlin'))
peerStore.metadataBook.getValue(peerId, 'location') peerStore.metadataBook.getValue(peerId, 'location')
// Metadata Map // Metadata Map
``` ```
@ -1073,7 +1073,7 @@ Set known metadata of a given `peerId`.
|------|------|-------------| |------|------|-------------|
| peerId | [`PeerId`][peer-id] | peerId to set | | peerId | [`PeerId`][peer-id] | peerId to set |
| key | `string` | key of the metadata value to store | | key | `string` | key of the metadata value to store |
| value | `Buffer` | metadata value to store | | value | `Uint8Array` | metadata value to store |
#### Returns #### Returns
@ -1084,7 +1084,7 @@ Set known metadata of a given `peerId`.
#### Example #### Example
```js ```js
peerStore.metadataBook.set(peerId, 'location', Buffer.from('Berlin')) peerStore.metadataBook.set(peerId, 'location', uint8ArrayFromString('Berlin'))
``` ```
### peerStore.protoBook.delete ### peerStore.protoBook.delete
@ -1308,7 +1308,7 @@ Publishes messages to the given topics.
| Name | Type | Description | | Name | Type | Description |
|------|------|-------------| |------|------|-------------|
| topic | `string` | topic to publish | | topic | `string` | topic to publish |
| data | `Buffer` | data to publish | | data | `Uint8Array` | data to publish |
#### Returns #### Returns
@ -1320,7 +1320,7 @@ Publishes messages to the given topics.
```js ```js
const topic = 'topic' const topic = 'topic'
const data = Buffer.from('data') const data = uint8ArrayFromString('data')
await libp2p.pubsub.publish(topic, data) await libp2p.pubsub.publish(topic, data)
``` ```
@ -1336,7 +1336,7 @@ Subscribes the given handler to a pubsub topic.
| Name | Type | Description | | Name | Type | Description |
|------|------|-------------| |------|------|-------------|
| topic | `string` | topic to subscribe | | topic | `string` | topic to subscribe |
| handler | `function({ from: string, data: Buffer, seqno: Buffer, topicIDs: Array<string>, signature: Buffer, key: Buffer })` | handler for new data on topic | | handler | `function({ from: string, data: Uint8Array, seqno: Uint8Array, topicIDs: Array<string>, signature: Uint8Array, key: Uint8Array })` | handler for new data on topic |
#### Returns #### Returns
@ -1679,19 +1679,19 @@ Encrypt protected data using the Cryptographic Message Syntax (CMS).
| Name | Type | Description | | Name | Type | Description |
|------|------|-------------| |------|------|-------------|
| name | `string` | The local key name. | | name | `string` | The local key name. |
| data | `Buffer` | The data to encrypt. | | data | `Uint8Array` | The data to encrypt. |
#### Returns #### Returns
| Type | Description | | Type | Description |
|------|-------------| |------|-------------|
| `Promise<Buffer>` | Encrypted data as a PKCS #7 message in DER. | | `Promise<Uint8Array>` | Encrypted data as a PKCS #7 message in DER. |
#### Example #### Example
```js ```js
const keyInfo = await libp2p.keychain.createKey('keyTest', 'rsa', 4096) const keyInfo = await libp2p.keychain.createKey('keyTest', 'rsa', 4096)
const enc = await libp2p.keychain.cms.encrypt('keyTest', Buffer.from('data')) const enc = await libp2p.keychain.cms.encrypt('keyTest', uint8ArrayFromString('data'))
``` ```
### keychain.cms.decrypt ### keychain.cms.decrypt
@ -1711,13 +1711,13 @@ The keychain must contain one of the keys used to encrypt the data. If none of
| Type | Description | | Type | Description |
|------|-------------| |------|-------------|
| `Promise<Buffer>` | Decrypted data. | | `Promise<Uint8Array>` | Decrypted data. |
#### Example #### Example
```js ```js
const keyInfo = await libp2p.keychain.createKey('keyTest', 'rsa', 4096) const keyInfo = await libp2p.keychain.createKey('keyTest', 'rsa', 4096)
const enc = await libp2p.keychain.cms.encrypt('keyTest', Buffer.from('data')) const enc = await libp2p.keychain.cms.encrypt('keyTest', uint8ArrayFromString('data'))
const decData = await libp2p.keychain.cms.decrypt(enc) const decData = await libp2p.keychain.cms.decrypt(enc)
``` ```

View File

@ -3,6 +3,7 @@
const pipe = require('it-pipe') const pipe = require('it-pipe')
const lp = require('it-length-prefixed') const lp = require('it-length-prefixed')
const uint8ArrayToString = require('uint8arrays/to-string')
function stdinToStream(stream) { function stdinToStream(stream) {
// Read utf-8 from stdin // Read utf-8 from stdin
@ -28,7 +29,7 @@ function streamToConsole(stream) {
// For each chunk of data // For each chunk of data
for await (const msg of source) { for await (const msg of source) {
// Output the data as a utf8 string // Output the data as a utf8 string
console.log('> ' + msg.toString('utf8').replace('\n', '')) console.log('> ' + uint8ArrayToString(msg).replace('\n', ''))
} }
} }
) )

View File

@ -1,18 +1,17 @@
/* eslint no-console: ["off"] */ /* eslint no-console: ["off"] */
'use strict' 'use strict'
const { Buffer } = require('buffer')
const { generate } = require('libp2p/src/pnet') const { generate } = require('libp2p/src/pnet')
const privateLibp2pNode = require('./libp2p-node') const privateLibp2pNode = require('./libp2p-node')
const pipe = require('it-pipe') const pipe = require('it-pipe')
// Create a buffer and write the swarm key to it // Create a Uint8Array and write the swarm key to it
const swarmKey = Buffer.alloc(95) const swarmKey = new Uint8Array(95)
generate(swarmKey) generate(swarmKey)
// This key is for testing a different key not working // This key is for testing a different key not working
const otherSwarmKey = Buffer.alloc(95) const otherSwarmKey = new Uint8Array(95)
generate(otherSwarmKey) generate(otherSwarmKey)
;(async () => { ;(async () => {

View File

@ -11,7 +11,7 @@ const Protector = require('libp2p/src/pnet')
* privateLibp2pNode returns a libp2p node function that will use the swarm * privateLibp2pNode returns a libp2p node function that will use the swarm
* key with the given `swarmKey` to create the Protector * key with the given `swarmKey` to create the Protector
* *
* @param {Buffer} swarmKey * @param {Uint8Array} swarmKey
* @returns {Promise<libp2p>} Returns a libp2pNode function for use in IPFS creation * @returns {Promise<libp2p>} Returns a libp2pNode function for use in IPFS creation
*/ */
const privateLibp2pNode = async (swarmKey) => { const privateLibp2pNode = async (swarmKey) => {

View File

@ -1,13 +1,13 @@
/* eslint-disable no-console */ /* eslint-disable no-console */
'use strict' 'use strict'
const { Buffer } = require('buffer')
const Libp2p = require('../../') const Libp2p = require('../../')
const TCP = require('libp2p-tcp') const TCP = require('libp2p-tcp')
const Mplex = require('libp2p-mplex') const Mplex = require('libp2p-mplex')
const { NOISE } = require('libp2p-noise') const { NOISE } = require('libp2p-noise')
const SECIO = require('libp2p-secio') const SECIO = require('libp2p-secio')
const Gossipsub = require('libp2p-gossipsub') const Gossipsub = require('libp2p-gossipsub')
const uint8ArrayFromString = require('uint8arrays/from-string')
const createNode = async () => { const createNode = async () => {
const node = await Libp2p.create({ const node = await Libp2p.create({
@ -48,6 +48,6 @@ const createNode = async () => {
// node2 publishes "news" every second // node2 publishes "news" every second
setInterval(() => { setInterval(() => {
node2.pubsub.publish(topic, Buffer.from('Bird bird bird, bird is the word!')) node2.pubsub.publish(topic, uint8ArrayFromString('Bird bird bird, bird is the word!'))
}, 1000) }, 1000)
})() })()

View File

@ -57,7 +57,7 @@ await node2.pubsub.subscribe(topic, (msg) => {
// node2 publishes "news" every second // node2 publishes "news" every second
setInterval(() => { setInterval(() => {
node2.pubsub.publish(topic, Buffer.from('Bird bird bird, bird is the word!')) node2.pubsub.publish(topic, uint8ArrayFromString('Bird bird bird, bird is the word!'))
}, 1000) }, 1000)
``` ```

View File

@ -1,13 +1,13 @@
/* eslint-disable no-console */ /* eslint-disable no-console */
'use strict' 'use strict'
const { Buffer } = require('buffer')
const Libp2p = require('../../../') const Libp2p = require('../../../')
const TCP = require('libp2p-tcp') const TCP = require('libp2p-tcp')
const Mplex = require('libp2p-mplex') const Mplex = require('libp2p-mplex')
const { NOISE } = require('libp2p-noise') const { NOISE } = require('libp2p-noise')
const SECIO = require('libp2p-secio') const SECIO = require('libp2p-secio')
const Gossipsub = require('libp2p-gossipsub') const Gossipsub = require('libp2p-gossipsub')
const uint8ArrayFromString = require('uint8arrays/from-string')
const createNode = async () => { const createNode = async () => {
const node = await Libp2p.create({ const node = await Libp2p.create({
@ -73,7 +73,7 @@ const createNode = async () => {
// car is not a fruit ! // car is not a fruit !
setInterval(() => { setInterval(() => {
console.log('############## fruit ' + myFruits[count] + ' ##############') console.log('############## fruit ' + myFruits[count] + ' ##############')
node1.pubsub.publish(topic, Buffer.from(myFruits[count])) node1.pubsub.publish(topic, uint8ArrayFromString(myFruits[count]))
count++ count++
if (count == myFruits.length) { if (count == myFruits.length) {
count = 0 count = 0

View File

@ -79,7 +79,7 @@ const myFruits = ['banana', 'apple', 'car', 'orange'];
setInterval(() => { setInterval(() => {
console.log('############## fruit ' + myFruits[count] + ' ##############') console.log('############## fruit ' + myFruits[count] + ' ##############')
node1.pubsub.publish(topic, Buffer.from(myFruits[count])) node1.pubsub.publish(topic, new TextEncoder().encode(myFruits[count]))
count++ count++
if (count == myFruits.length) { if (count == myFruits.length) {
count = 0 count = 0

View File

@ -50,7 +50,7 @@
"err-code": "^2.0.0", "err-code": "^2.0.0",
"events": "^3.1.0", "events": "^3.1.0",
"hashlru": "^2.3.0", "hashlru": "^2.3.0",
"interface-datastore": "^1.0.4", "interface-datastore": "^2.0.0",
"ipfs-utils": "^2.2.0", "ipfs-utils": "^2.2.0",
"it-all": "^1.0.1", "it-all": "^1.0.1",
"it-buffer": "^0.1.2", "it-buffer": "^0.1.2",
@ -58,69 +58,67 @@
"it-length-prefixed": "^3.0.1", "it-length-prefixed": "^3.0.1",
"it-pipe": "^1.1.0", "it-pipe": "^1.1.0",
"it-protocol-buffers": "^0.2.0", "it-protocol-buffers": "^0.2.0",
"libp2p-crypto": "^0.17.9", "libp2p-crypto": "^0.18.0",
"libp2p-interfaces": "^0.3.1", "libp2p-interfaces": "^0.5.0",
"libp2p-utils": "^0.1.2", "libp2p-utils": "^0.2.0",
"mafmt": "^7.0.0", "mafmt": "^8.0.0",
"merge-options": "^2.0.0", "merge-options": "^2.0.0",
"moving-average": "^1.0.0", "moving-average": "^1.0.0",
"multiaddr": "^7.4.3", "multiaddr": "^8.0.0",
"multicodec": "^1.0.2", "multicodec": "^1.0.2",
"multistream-select": "^0.15.0", "multistream-select": "^1.0.0",
"mutable-proxy": "^1.0.0", "mutable-proxy": "^1.0.0",
"node-forge": "^0.9.1", "node-forge": "^0.9.1",
"p-any": "^3.0.0", "p-any": "^3.0.0",
"p-fifo": "^1.0.0", "p-fifo": "^1.0.0",
"p-settle": "^4.0.1", "p-settle": "^4.0.1",
"peer-id": "^0.13.11", "peer-id": "^0.14.0",
"protons": "^1.0.1", "protons": "^2.0.0",
"retimer": "^2.0.0", "retimer": "^2.0.0",
"sanitize-filename": "^1.6.3", "sanitize-filename": "^1.6.3",
"streaming-iterables": "^4.1.0", "streaming-iterables": "^5.0.2",
"timeout-abort-controller": "^1.0.0", "timeout-abort-controller": "^1.1.1",
"varint": "^5.0.0", "varint": "^5.0.0",
"xsalsa20": "^1.0.2" "xsalsa20": "^1.0.2"
}, },
"devDependencies": { "devDependencies": {
"@nodeutils/defaults-deep": "^1.1.0", "@nodeutils/defaults-deep": "^1.1.0",
"abortable-iterator": "^3.0.0", "abortable-iterator": "^3.0.0",
"aegir": "^22.0.0", "aegir": "^26.0.0",
"chai": "^4.2.0", "chai": "^4.2.0",
"chai-as-promised": "^7.1.1", "chai-as-promised": "^7.1.1",
"chai-bytes": "^0.1.2", "chai-bytes": "^0.1.2",
"chai-string": "^1.5.0", "chai-string": "^1.5.0",
"cids": "^0.8.0", "cids": "^1.0.0",
"datastore-fs": "^1.1.0",
"datastore-level": "^1.1.0",
"delay": "^4.3.0", "delay": "^4.3.0",
"dirty-chai": "^2.0.1", "dirty-chai": "^2.0.1",
"interop-libp2p": "^0.1.0", "interop-libp2p": "^0.2.0",
"ipfs-http-client": "^44.0.0", "ipfs-http-client": "^46.0.0",
"it-concat": "^1.0.0", "it-concat": "^1.0.0",
"it-pair": "^1.0.0", "it-pair": "^1.0.0",
"it-pushable": "^1.4.0", "it-pushable": "^1.4.0",
"level": "^6.0.1", "libp2p-bootstrap": "^0.12.0",
"libp2p-bootstrap": "^0.11.0", "libp2p-delegated-content-routing": "^0.6.0",
"libp2p-delegated-content-routing": "^0.5.0", "libp2p-delegated-peer-routing": "^0.6.0",
"libp2p-delegated-peer-routing": "^0.5.0", "libp2p-floodsub": "^0.22.0",
"libp2p-floodsub": "^0.21.0", "libp2p-gossipsub": "^0.5.0",
"libp2p-gossipsub": "^0.4.6", "libp2p-kad-dht": "^0.20.0",
"libp2p-kad-dht": "^0.19.1", "libp2p-mdns": "^0.15.0",
"libp2p-mdns": "^0.14.1", "libp2p-mplex": "^0.10.0",
"libp2p-mplex": "^0.9.5", "libp2p-noise": "^2.0.0",
"libp2p-noise": "^1.1.1", "libp2p-secio": "^0.13.1",
"libp2p-secio": "^0.12.4", "libp2p-tcp": "^0.15.1",
"libp2p-tcp": "^0.14.1", "libp2p-webrtc-star": "^0.19.0",
"libp2p-webrtc-star": "^0.18.0", "libp2p-websockets": "^0.14.0",
"libp2p-websockets": "^0.13.1", "multihashes": "^3.0.1",
"multihashes": "^0.4.19", "nock": "^13.0.3",
"nock": "^12.0.3",
"p-defer": "^3.0.0", "p-defer": "^3.0.0",
"p-times": "^3.0.0", "p-times": "^3.0.0",
"p-wait-for": "^3.1.0", "p-wait-for": "^3.1.0",
"promisify-es6": "^1.0.3", "promisify-es6": "^1.0.3",
"rimraf": "^3.0.2", "rimraf": "^3.0.2",
"sinon": "^9.0.2" "sinon": "^9.0.2",
"uint8arrays": "^1.1.0"
}, },
"contributors": [ "contributors": [
"David Dias <daviddias.p@gmail.com>", "David Dias <daviddias.p@gmail.com>",

View File

@ -122,11 +122,11 @@ class Circuit {
type: CircuitPB.Type.HOP, type: CircuitPB.Type.HOP,
srcPeer: { srcPeer: {
id: this.peerId.toBytes(), id: this.peerId.toBytes(),
addrs: this._libp2p.multiaddrs.map(addr => addr.buffer) addrs: this._libp2p.multiaddrs.map(addr => addr.bytes)
}, },
dstPeer: { dstPeer: {
id: destinationPeer.toBytes(), id: destinationPeer.toBytes(),
addrs: [multiaddr(destinationAddr).buffer] addrs: [multiaddr(destinationAddr).bytes]
} }
} }
}) })

View File

@ -64,8 +64,8 @@ module.exports = (node) => {
/** /**
* Store the given key/value pair in the DHT. * Store the given key/value pair in the DHT.
* @param {Buffer} key * @param {Uint8Array} key
* @param {Buffer} value * @param {Uint8Array} value
* @param {Object} [options] - put options * @param {Object} [options] - put options
* @param {number} [options.minPeers] - minimum number of peers required to successfully put * @param {number} [options.minPeers] - minimum number of peers required to successfully put
* @returns {Promise<void>} * @returns {Promise<void>}
@ -81,10 +81,10 @@ module.exports = (node) => {
/** /**
* Get the value to the given key. * Get the value to the given key.
* Times out after 1 minute by default. * Times out after 1 minute by default.
* @param {Buffer} key * @param {Uint8Array} key
* @param {Object} [options] - get options * @param {Object} [options] - get options
* @param {number} [options.timeout] - optional timeout (default: 60000) * @param {number} [options.timeout] - optional timeout (default: 60000)
* @returns {Promise<{from: PeerId, val: Buffer}>} * @returns {Promise<{from: PeerId, val: Uint8Array}>}
*/ */
async get (key, options) { // eslint-disable-line require-await async get (key, options) { // eslint-disable-line require-await
if (!node.isStarted() || !dht.isStarted) { if (!node.isStarted() || !dht.isStarted) {
@ -96,11 +96,11 @@ module.exports = (node) => {
/** /**
* Get the `n` values to the given key without sorting. * Get the `n` values to the given key without sorting.
* @param {Buffer} key * @param {Uint8Array} key
* @param {number} nVals * @param {number} nVals
* @param {Object} [options] - get options * @param {Object} [options] - get options
* @param {number} [options.timeout] - optional timeout (default: 60000) * @param {number} [options.timeout] - optional timeout (default: 60000)
* @returns {Promise<Array<{from: PeerId, val: Buffer}>>} * @returns {Promise<Array<{from: PeerId, val: Uint8Array}>>}
*/ */
async getMany (key, nVals, options) { // eslint-disable-line require-await async getMany (key, nVals, options) { // eslint-disable-line require-await
if (!node.isStarted() || !dht.isStarted) { if (!node.isStarted() || !dht.isStarted) {

View File

@ -5,11 +5,11 @@ const log = debug('libp2p:identify')
log.error = debug('libp2p:identify:error') log.error = debug('libp2p:identify:error')
const errCode = require('err-code') const errCode = require('err-code')
const { Buffer } = require('buffer')
const pb = require('it-protocol-buffers') const pb = require('it-protocol-buffers')
const lp = require('it-length-prefixed') const lp = require('it-length-prefixed')
const pipe = require('it-pipe') const pipe = require('it-pipe')
const { collect, take, consume } = require('streaming-iterables') const { collect, take, consume } = require('streaming-iterables')
const uint8ArrayFromString = require('uint8arrays/from-string')
const PeerId = require('peer-id') const PeerId = require('peer-id')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
@ -32,7 +32,7 @@ const { codes } = require('../errors')
class IdentifyService { class IdentifyService {
/** /**
* Takes the `addr` and converts it to a Multiaddr if possible * Takes the `addr` and converts it to a Multiaddr if possible
* @param {Buffer|String} addr * @param {Uint8Array|String} addr
* @returns {Multiaddr|null} * @returns {Multiaddr|null}
*/ */
static getCleanMultiaddr (addr) { static getCleanMultiaddr (addr) {
@ -91,7 +91,7 @@ class IdentifyService {
*/ */
async push (connections) { async push (connections) {
const signedPeerRecord = await this._getSelfPeerRecord() const signedPeerRecord = await this._getSelfPeerRecord()
const listenAddrs = this._libp2p.multiaddrs.map((ma) => ma.buffer) const listenAddrs = this._libp2p.multiaddrs.map((ma) => ma.bytes)
const protocols = Array.from(this._protocols.keys()) const protocols = Array.from(this._protocols.keys())
const pushes = connections.map(async connection => { const pushes = connections.map(async connection => {
@ -199,7 +199,7 @@ class IdentifyService {
} }
this.peerStore.protoBook.set(id, protocols) this.peerStore.protoBook.set(id, protocols)
this.peerStore.metadataBook.set(id, 'AgentVersion', Buffer.from(message.agentVersion)) this.peerStore.metadataBook.set(id, 'AgentVersion', uint8ArrayFromString(message.agentVersion))
// TODO: Track our observed address so that we can score it // TODO: Track our observed address so that we can score it
log('received observed address of %s', observedAddr) log('received observed address of %s', observedAddr)
@ -234,7 +234,7 @@ class IdentifyService {
* @param {Connection} options.connection * @param {Connection} options.connection
*/ */
async _handleIdentify ({ connection, stream }) { async _handleIdentify ({ connection, stream }) {
let publicKey = Buffer.alloc(0) let publicKey = new Uint8Array(0)
if (this.peerId.pubKey) { if (this.peerId.pubKey) {
publicKey = this.peerId.pubKey.bytes publicKey = this.peerId.pubKey.bytes
} }
@ -245,9 +245,9 @@ class IdentifyService {
protocolVersion: PROTOCOL_VERSION, protocolVersion: PROTOCOL_VERSION,
agentVersion: AGENT_VERSION, agentVersion: AGENT_VERSION,
publicKey, publicKey,
listenAddrs: this._libp2p.multiaddrs.map((ma) => ma.buffer), listenAddrs: this._libp2p.multiaddrs.map((ma) => ma.bytes),
signedPeerRecord, signedPeerRecord,
observedAddr: connection.remoteAddr.buffer, observedAddr: connection.remoteAddr.bytes,
protocols: Array.from(this._protocols.keys()) protocols: Array.from(this._protocols.keys())
}) })
@ -311,7 +311,7 @@ class IdentifyService {
/** /**
* Get self signed peer record raw envelope. * Get self signed peer record raw envelope.
* @return {Buffer} * @return {Uint8Array}
*/ */
async _getSelfPeerRecord () { async _getSelfPeerRecord () {
const selfSignedPeerRecord = this.peerStore.addressBook.getRawEnvelope(this.peerId) const selfSignedPeerRecord = this.peerStore.addressBook.getRawEnvelope(this.peerId)

View File

@ -5,6 +5,8 @@ require('node-forge/lib/pbe')
const forge = require('node-forge/lib/forge') const forge = require('node-forge/lib/forge')
const { certificateForKey, findAsync } = require('./util') const { certificateForKey, findAsync } = require('./util')
const errcode = require('err-code') const errcode = require('err-code')
const uint8ArrayFromString = require('uint8arrays/from-string')
const uint8ArrayToString = require('uint8arrays/to-string')
/** /**
* Cryptographic Message Syntax (aka PKCS #7) * Cryptographic Message Syntax (aka PKCS #7)
@ -32,15 +34,15 @@ class CMS {
/** /**
* Creates some protected data. * Creates some protected data.
* *
* The output Buffer contains the PKCS #7 message in DER. * The output Uint8Array contains the PKCS #7 message in DER.
* *
* @param {string} name - The local key name. * @param {string} name - The local key name.
* @param {Buffer} plain - The data to encrypt. * @param {Uint8Array} plain - The data to encrypt.
* @returns {undefined} * @returns {undefined}
*/ */
async encrypt (name, plain) { async encrypt (name, plain) {
if (!Buffer.isBuffer(plain)) { if (!(plain instanceof Uint8Array)) {
throw errcode(new Error('Plain data must be a Buffer'), 'ERR_INVALID_PARAMS') throw errcode(new Error('Plain data must be a Uint8Array'), 'ERR_INVALID_PARAMS')
} }
const key = await this.keychain.findKeyByName(name) const key = await this.keychain.findKeyByName(name)
@ -56,7 +58,7 @@ class CMS {
// convert message to DER // convert message to DER
const der = forge.asn1.toDer(p7.toAsn1()).getBytes() const der = forge.asn1.toDer(p7.toAsn1()).getBytes()
return Buffer.from(der, 'binary') return uint8ArrayFromString(der, 'ascii')
} }
/** /**
@ -65,17 +67,17 @@ class CMS {
* The keychain must contain one of the keys used to encrypt the data. If none of the keys * The keychain must contain one of the keys used to encrypt the data. If none of the keys
* exists, an Error is returned with the property 'missingKeys'. It is array of key ids. * exists, an Error is returned with the property 'missingKeys'. It is array of key ids.
* *
* @param {Buffer} cmsData - The CMS encrypted data to decrypt. * @param {Uint8Array} cmsData - The CMS encrypted data to decrypt.
* @returns {undefined} * @returns {undefined}
*/ */
async decrypt (cmsData) { async decrypt (cmsData) {
if (!Buffer.isBuffer(cmsData)) { if (!(cmsData instanceof Uint8Array)) {
throw errcode(new Error('CMS data is required'), 'ERR_INVALID_PARAMS') throw errcode(new Error('CMS data is required'), 'ERR_INVALID_PARAMS')
} }
let cms let cms
try { try {
const buf = forge.util.createBuffer(cmsData.toString('binary')) const buf = forge.util.createBuffer(uint8ArrayToString(cmsData, 'ascii'))
const obj = forge.asn1.fromDer(buf) const obj = forge.asn1.fromDer(buf)
cms = forge.pkcs7.messageFromAsn1(obj) cms = forge.pkcs7.messageFromAsn1(obj)
} catch (err) { } catch (err) {
@ -115,7 +117,7 @@ class CMS {
const pem = await this.keychain._getPrivateKey(key.name) const pem = await this.keychain._getPrivateKey(key.name)
const privateKey = forge.pki.decryptRsaPrivateKey(pem, this.keychain._()) const privateKey = forge.pki.decryptRsaPrivateKey(pem, this.keychain._())
cms.decrypt(r.recipient, privateKey) cms.decrypt(r.recipient, privateKey)
return Buffer.from(cms.content.getBytes(), 'binary') return uint8ArrayFromString(cms.content.getBytes(), 'ascii')
} }
} }

View File

@ -8,6 +8,8 @@ const DS = require('interface-datastore')
const CMS = require('./cms') const CMS = require('./cms')
const errcode = require('err-code') const errcode = require('err-code')
const { Number } = require('ipfs-utils/src/globalthis') const { Number } = require('ipfs-utils/src/globalthis')
const uint8ArrayToString = require('uint8arrays/to-string')
const uint8ArrayFromString = require('uint8arrays/from-string')
require('node-forge/lib/sha512') require('node-forge/lib/sha512')
@ -155,7 +157,7 @@ class Keychain {
static generateOptions () { static generateOptions () {
const options = Object.assign({}, defaultOptions) const options = Object.assign({}, defaultOptions)
const saltLength = Math.ceil(NIST.minSaltLength / 3) * 3 // no base64 padding const saltLength = Math.ceil(NIST.minSaltLength / 3) * 3 // no base64 padding
options.dek.salt = crypto.randomBytes(saltLength).toString('base64') options.dek.salt = uint8ArrayToString(crypto.randomBytes(saltLength), 'base64')
return options return options
} }
@ -212,8 +214,8 @@ class Keychain {
id: kid id: kid
} }
const batch = self.store.batch() const batch = self.store.batch()
batch.put(dsname, pem) batch.put(dsname, uint8ArrayFromString(pem))
batch.put(DsInfoName(name), JSON.stringify(keyInfo)) batch.put(DsInfoName(name), uint8ArrayFromString(JSON.stringify(keyInfo)))
await batch.commit() await batch.commit()
} catch (err) { } catch (err) {
@ -236,7 +238,7 @@ class Keychain {
const info = [] const info = []
for await (const value of self.store.query(query)) { for await (const value of self.store.query(query)) {
info.push(JSON.parse(value.value)) info.push(JSON.parse(uint8ArrayToString(value.value)))
} }
return info return info
@ -271,7 +273,7 @@ class Keychain {
const dsname = DsInfoName(name) const dsname = DsInfoName(name)
try { try {
const res = await this.store.get(dsname) const res = await this.store.get(dsname)
return JSON.parse(res.toString()) return JSON.parse(uint8ArrayToString(res))
} catch (err) { } catch (err) {
return throwDelayed(errcode(new Error(`Key '${name}' does not exist. ${err.message}`), 'ERR_KEY_NOT_FOUND')) return throwDelayed(errcode(new Error(`Key '${name}' does not exist. ${err.message}`), 'ERR_KEY_NOT_FOUND'))
} }
@ -321,15 +323,14 @@ class Keychain {
if (exists) return throwDelayed(errcode(new Error(`Key '${newName}' already exists`), 'ERR_KEY_ALREADY_EXISTS')) if (exists) return throwDelayed(errcode(new Error(`Key '${newName}' already exists`), 'ERR_KEY_ALREADY_EXISTS'))
try { try {
let res = await this.store.get(oldDsname) const pem = await self.store.get(oldDsname)
const pem = res.toString() const res = await self.store.get(oldInfoName)
res = await self.store.get(oldInfoName)
const keyInfo = JSON.parse(res.toString()) const keyInfo = JSON.parse(uint8ArrayToString(res))
keyInfo.name = newName keyInfo.name = newName
const batch = self.store.batch() const batch = self.store.batch()
batch.put(newDsname, pem) batch.put(newDsname, pem)
batch.put(newInfoName, JSON.stringify(keyInfo)) batch.put(newInfoName, uint8ArrayFromString(JSON.stringify(keyInfo)))
batch.delete(oldDsname) batch.delete(oldDsname)
batch.delete(oldInfoName) batch.delete(oldInfoName)
await batch.commit() await batch.commit()
@ -357,7 +358,7 @@ class Keychain {
const dsname = DsName(name) const dsname = DsName(name)
try { try {
const res = await this.store.get(dsname) const res = await this.store.get(dsname)
const pem = res.toString() const pem = uint8ArrayToString(res)
const privateKey = await crypto.keys.import(pem, this._()) const privateKey = await crypto.keys.import(pem, this._())
return privateKey.export(password) return privateKey.export(password)
} catch (err) { } catch (err) {
@ -405,8 +406,8 @@ class Keychain {
id: kid id: kid
} }
const batch = self.store.batch() const batch = self.store.batch()
batch.put(dsname, pem) batch.put(dsname, uint8ArrayFromString(pem))
batch.put(DsInfoName(name), JSON.stringify(keyInfo)) batch.put(DsInfoName(name), uint8ArrayFromString(JSON.stringify(keyInfo)))
await batch.commit() await batch.commit()
return keyInfo return keyInfo
@ -434,8 +435,8 @@ class Keychain {
id: kid id: kid
} }
const batch = self.store.batch() const batch = self.store.batch()
batch.put(dsname, pem) batch.put(dsname, uint8ArrayFromString(pem))
batch.put(DsInfoName(name), JSON.stringify(keyInfo)) batch.put(DsInfoName(name), uint8ArrayFromString(JSON.stringify(keyInfo)))
await batch.commit() await batch.commit()
return keyInfo return keyInfo
} catch (err) { } catch (err) {
@ -458,7 +459,7 @@ class Keychain {
try { try {
const dsname = DsName(name) const dsname = DsName(name)
const res = await this.store.get(dsname) const res = await this.store.get(dsname)
return res.toString() return uint8ArrayToString(res)
} catch (err) { } catch (err) {
return throwDelayed(errcode(new Error(`Key '${name}' does not exist. ${err.message}`), 'ERR_KEY_NOT_FOUND')) return throwDelayed(errcode(new Error(`Key '${name}' does not exist. ${err.message}`), 'ERR_KEY_NOT_FOUND'))
} }

View File

@ -8,13 +8,13 @@ exports = module.exports
/** /**
* Gets a self-signed X.509 certificate for the key. * Gets a self-signed X.509 certificate for the key.
* *
* The output Buffer contains the PKCS #7 message in DER. * The output Uint8Array contains the PKCS #7 message in DER.
* *
* TODO: move to libp2p-crypto package * TODO: move to libp2p-crypto package
* *
* @param {KeyInfo} key - The id and name of the key * @param {KeyInfo} key - The id and name of the key
* @param {RsaPrivateKey} privateKey - The naked key * @param {RsaPrivateKey} privateKey - The naked key
* @returns {undefined} * @returns {Uint8Array}
*/ */
exports.certificateForKey = (key, privateKey) => { exports.certificateForKey = (key, privateKey) => {
const publicKey = pki.setRsaPublicKey(privateKey.n, privateKey.e) const publicKey = pki.setRsaPublicKey(privateKey.n, privateKey.e)

View File

@ -75,9 +75,9 @@ A `peerId.toB58String()` identifier mapping to a `Set` of protocol identifier st
#### Metadata Book #### Metadata Book
The `metadataBook` keeps track of the known metadata of a peer. Its metadata is stored in a key value fashion, where a key identifier (`string`) represents a metadata value (`Buffer`). The `metadataBook` keeps track of the known metadata of a peer. Its metadata is stored in a key value fashion, where a key identifier (`string`) represents a metadata value (`Uint8Array`).
`Map<string, Map<string, Buffer>>` `Map<string, Map<string, Uint8Array>>`
A `peerId.toB58String()` identifier mapping to the peer metadata Map. A `peerId.toB58String()` identifier mapping to the peer metadata Map.

View File

@ -31,7 +31,7 @@ class AddressBook extends Book {
/** /**
* CertifiedRecord object * CertifiedRecord object
* @typedef {Object} CertifiedRecord * @typedef {Object} CertifiedRecord
* @property {Buffer} raw raw envelope. * @property {Uint8Array} raw raw envelope.
* @property {number} seqNumber seq counter. * @property {number} seqNumber seq counter.
*/ */
@ -128,7 +128,7 @@ class AddressBook extends Book {
* Get the raw Envelope for a peer. Returns * Get the raw Envelope for a peer. Returns
* undefined if no Envelope is found. * undefined if no Envelope is found.
* @param {PeerId} peerId * @param {PeerId} peerId
* @return {Buffer|undefined} * @return {Uint8Array|undefined}
*/ */
getRawEnvelope (peerId) { getRawEnvelope (peerId) {
const entry = this.data.get(peerId.toB58String()) const entry = this.data.get(peerId.toB58String())

View File

@ -4,8 +4,7 @@ const errcode = require('err-code')
const debug = require('debug') const debug = require('debug')
const log = debug('libp2p:peer-store:proto-book') const log = debug('libp2p:peer-store:proto-book')
log.error = debug('libp2p:peer-store:proto-book:error') log.error = debug('libp2p:peer-store:proto-book:error')
const uint8ArrayEquals = require('uint8arrays/equals')
const { Buffer } = require('buffer')
const PeerId = require('peer-id') const PeerId = require('peer-id')
@ -38,7 +37,7 @@ class MetadataBook extends Book {
/** /**
* Map known peers to their known protocols. * Map known peers to their known protocols.
* @type {Map<string, Map<string, Buffer>>} * @type {Map<string, Map<string, Uint8Array>>}
*/ */
this.data = new Map() this.data = new Map()
} }
@ -48,7 +47,7 @@ class MetadataBook extends Book {
* @override * @override
* @param {PeerId} peerId * @param {PeerId} peerId
* @param {string} key metadata key * @param {string} key metadata key
* @param {Buffer} value metadata value * @param {Uint8Array} value metadata value
* @returns {ProtoBook} * @returns {ProtoBook}
*/ */
set (peerId, key, value) { set (peerId, key, value) {
@ -57,7 +56,7 @@ class MetadataBook extends Book {
throw errcode(new Error('peerId must be an instance of peer-id'), ERR_INVALID_PARAMETERS) throw errcode(new Error('peerId must be an instance of peer-id'), ERR_INVALID_PARAMETERS)
} }
if (typeof key !== 'string' || !Buffer.isBuffer(value)) { if (typeof key !== 'string' || !(value instanceof Uint8Array)) {
log.error('valid key and value must be provided to store data') log.error('valid key and value must be provided to store data')
throw errcode(new Error('valid key and value must be provided'), ERR_INVALID_PARAMETERS) throw errcode(new Error('valid key and value must be provided'), ERR_INVALID_PARAMETERS)
} }
@ -77,7 +76,7 @@ class MetadataBook extends Book {
const recMap = rec.get(key) const recMap = rec.get(key)
// Already exists and is equal // Already exists and is equal
if (recMap && value.equals(recMap)) { if (recMap && uint8ArrayEquals(value, recMap)) {
log(`the metadata provided to store is equal to the already stored for ${id} on ${key}`) log(`the metadata provided to store is equal to the already stored for ${id} on ${key}`)
return return
} }
@ -91,7 +90,7 @@ class MetadataBook extends Book {
/** /**
* Get the known data of a provided peer. * Get the known data of a provided peer.
* @param {PeerId} peerId * @param {PeerId} peerId
* @returns {Map<string, Buffer>} * @returns {Map<string, Uint8Array>}
*/ */
get (peerId) { get (peerId) {
if (!PeerId.isPeerId(peerId)) { if (!PeerId.isPeerId(peerId)) {
@ -105,7 +104,7 @@ class MetadataBook extends Book {
* Get specific metadata value, if it exists * Get specific metadata value, if it exists
* @param {PeerId} peerId * @param {PeerId} peerId
* @param {string} key * @param {string} key
* @returns {Buffer} * @returns {Uint8Array}
*/ */
getValue (peerId, key) { getValue (peerId, key) {
if (!PeerId.isPeerId(peerId)) { if (!PeerId.isPeerId(peerId)) {

View File

@ -189,7 +189,7 @@ class PersistentPeerStore extends PeerStore {
const encodedData = Addresses.encode({ const encodedData = Addresses.encode({
addrs: entry.addresses.map((address) => ({ addrs: entry.addresses.map((address) => ({
multiaddr: address.multiaddr.buffer, multiaddr: address.multiaddr.bytes,
isCertified: address.isCertified isCertified: address.isCertified
})), })),
certified_record: entry.record ? { certified_record: entry.record ? {
@ -287,7 +287,7 @@ class PersistentPeerStore extends PeerStore {
* @private * @private
* @param {Object} params * @param {Object} params
* @param {Key} params.key datastore key * @param {Key} params.key datastore key
* @param {Buffer} params.value datastore value stored * @param {Uint8Array} params.value datastore value stored
* @return {Promise<void>} * @return {Promise<void>}
*/ */
async _processDatastoreEntry ({ key, value }) { async _processDatastoreEntry ({ key, value }) {

View File

@ -64,7 +64,7 @@ node -e "require('libp2p/src/pnet').generate(process.stdout)" > swarm.key
```js ```js
const writeKey = require('libp2p/src/pnet').generate const writeKey = require('libp2p/src/pnet').generate
const swarmKey = Buffer.alloc(95) const swarmKey = new Uint8Array(95)
writeKey(swarmKey) writeKey(swarmKey)
fs.writeFileSync('swarm.key', swarmKey) fs.writeFileSync('swarm.key', swarmKey)
``` ```

View File

@ -1,10 +1,11 @@
'use strict' 'use strict'
const { Buffer } = require('buffer')
const debug = require('debug') const debug = require('debug')
const Errors = require('./errors') const Errors = require('./errors')
const xsalsa20 = require('xsalsa20') const xsalsa20 = require('xsalsa20')
const KEY_LENGTH = require('./key-generator').KEY_LENGTH const KEY_LENGTH = require('./key-generator').KEY_LENGTH
const uint8ArrayFromString = require('uint8arrays/from-string')
const uint8ArrayToString = require('uint8arrays/to-string')
const log = debug('libp2p:pnet') const log = debug('libp2p:pnet')
log.trace = debug('libp2p:pnet:trace') log.trace = debug('libp2p:pnet:trace')
@ -13,15 +14,15 @@ log.error = debug('libp2p:pnet:err')
/** /**
* Creates a stream iterable to encrypt messages in a private network * Creates a stream iterable to encrypt messages in a private network
* *
* @param {Buffer} nonce The nonce to use in encryption * @param {Uint8Array} nonce The nonce to use in encryption
* @param {Buffer} psk The private shared key to use in encryption * @param {Uint8Array} psk The private shared key to use in encryption
* @returns {*} a through iterable * @returns {*} a through iterable
*/ */
module.exports.createBoxStream = (nonce, psk) => { module.exports.createBoxStream = (nonce, psk) => {
const xor = xsalsa20(nonce, psk) const xor = xsalsa20(nonce, psk)
return (source) => (async function * () { return (source) => (async function * () {
for await (const chunk of source) { for await (const chunk of source) {
yield Buffer.from(xor.update(chunk.slice())) yield Uint8Array.from(xor.update(chunk.slice()))
} }
})() })()
} }
@ -29,8 +30,8 @@ module.exports.createBoxStream = (nonce, psk) => {
/** /**
* Creates a stream iterable to decrypt messages in a private network * Creates a stream iterable to decrypt messages in a private network
* *
* @param {Buffer} nonce The nonce of the remote peer * @param {Uint8Array} nonce The nonce of the remote peer
* @param {Buffer} psk The private shared key to use in decryption * @param {Uint8Array} psk The private shared key to use in decryption
* @returns {*} a through iterable * @returns {*} a through iterable
*/ */
module.exports.createUnboxStream = (nonce, psk) => { module.exports.createUnboxStream = (nonce, psk) => {
@ -39,15 +40,15 @@ module.exports.createUnboxStream = (nonce, psk) => {
log.trace('Decryption enabled') log.trace('Decryption enabled')
for await (const chunk of source) { for await (const chunk of source) {
yield Buffer.from(xor.update(chunk.slice())) yield Uint8Array.from(xor.update(chunk.slice()))
} }
})() })()
} }
/** /**
* Decode the version 1 psk from the given Buffer * Decode the version 1 psk from the given Uint8Array
* *
* @param {Buffer} pskBuffer * @param {Uint8Array} pskBuffer
* @throws {INVALID_PSK} * @throws {INVALID_PSK}
* @returns {Object} The PSK metadata (tag, codecName, psk) * @returns {Object} The PSK metadata (tag, codecName, psk)
*/ */
@ -58,10 +59,10 @@ module.exports.decodeV1PSK = (pskBuffer) => {
// from the buffer line by line to evaluate the next line // from the buffer line by line to evaluate the next line
// programmatically instead of making assumptions about the // programmatically instead of making assumptions about the
// encodings of each line. // encodings of each line.
const metadata = pskBuffer.toString().split(/(?:\r\n|\r|\n)/g) const metadata = uint8ArrayToString(pskBuffer).split(/(?:\r\n|\r|\n)/g)
const pskTag = metadata.shift() const pskTag = metadata.shift()
const codec = metadata.shift() const codec = metadata.shift()
const psk = Buffer.from(metadata.shift(), 'hex') const psk = uint8ArrayFromString(metadata.shift(), 'base16')
if (psk.byteLength !== KEY_LENGTH) { if (psk.byteLength !== KEY_LENGTH) {
throw new Error(Errors.INVALID_PSK) throw new Error(Errors.INVALID_PSK)

View File

@ -25,7 +25,7 @@ log.error = debug('libp2p:pnet:err')
*/ */
class Protector { class Protector {
/** /**
* @param {Buffer} keyBuffer The private shared key buffer * @param {Uint8Array} keyBuffer The private shared key buffer
* @constructor * @constructor
*/ */
constructor (keyBuffer) { constructor (keyBuffer) {

View File

@ -2,15 +2,19 @@
const crypto = require('libp2p-crypto') const crypto = require('libp2p-crypto')
const KEY_LENGTH = 32 const KEY_LENGTH = 32
const uint8ArrayToString = require('uint8arrays/to-string')
const uint8ArrayFromString = require('uint8arrays/from-string')
/** /**
* Generates a PSK that can be used in a libp2p-pnet private network * Generates a PSK that can be used in a libp2p-pnet private network
* @param {Writer} writer An object containing a `write` method * @param {Uint8Array} bytes An object to write the psk into
* @returns {void} * @returns {void}
*/ */
function generate (writer) { function generate (bytes) {
const psk = crypto.randomBytes(KEY_LENGTH).toString('hex') const psk = uint8ArrayToString(crypto.randomBytes(KEY_LENGTH), 'base16')
writer.write('/key/swarm/psk/1.0.0/\n/base16/\n' + psk) const key = uint8ArrayFromString('/key/swarm/psk/1.0.0/\n/base16/\n' + psk)
bytes.set(key)
} }
module.exports = generate module.exports = generate

View File

@ -1,8 +1,8 @@
'use strict' 'use strict'
const { Buffer } = require('buffer')
const errCode = require('err-code') const errCode = require('err-code')
const { messages, codes } = require('./errors') const { messages, codes } = require('./errors')
const uint8ArrayFromString = require('uint8arrays/from-string')
module.exports = (node, Pubsub, config) => { module.exports = (node, Pubsub, config) => {
const pubsub = new Pubsub(node.peerId, node.registrar, config) const pubsub = new Pubsub(node.peerId, node.registrar, config)
@ -50,7 +50,7 @@ module.exports = (node, Pubsub, config) => {
/** /**
* Publish messages to the given topics. * Publish messages to the given topics.
* @param {Array<string>|string} topic * @param {Array<string>|string} topic
* @param {Buffer} data * @param {Uint8Array} data
* @returns {Promise<void>} * @returns {Promise<void>}
*/ */
publish: (topic, data) => { publish: (topic, data) => {
@ -58,10 +58,14 @@ module.exports = (node, Pubsub, config) => {
throw errCode(new Error(messages.NOT_STARTED_YET), codes.PUBSUB_NOT_STARTED) throw errCode(new Error(messages.NOT_STARTED_YET), codes.PUBSUB_NOT_STARTED)
} }
if (typeof data === 'string' || data instanceof String) {
data = uint8ArrayFromString(data)
}
try { try {
data = Buffer.from(data) data = Uint8Array.from(data)
} catch (err) { } catch (err) {
throw errCode(new Error('data must be convertible to a Buffer'), 'ERR_DATA_IS_NOT_VALID') throw errCode(new Error('data must be convertible to a Uint8Array'), 'ERR_DATA_IS_NOT_VALID')
} }
return pubsub.publish(topic, data) return pubsub.publish(topic, data)

View File

@ -17,10 +17,11 @@ You can read further about the envelope in [libp2p/specs#217](https://github.com
```js ```js
// interface-record implementation example with the "libp2p-example" namespace // interface-record implementation example with the "libp2p-example" namespace
const Record = require('libp2p-interfaces/src/record') const Record = require('libp2p-interfaces/src/record')
const fromString = require('uint8arrays/from-string')
class ExampleRecord extends Record { class ExampleRecord extends Record {
constructor () { constructor () {
super ('libp2p-example', Buffer.from('0302', 'hex')) super ('libp2p-example', fromString('0302', 'hex'))
} }
marshal () {} marshal () {}

View File

@ -4,12 +4,12 @@ const debug = require('debug')
const log = debug('libp2p:envelope') const log = debug('libp2p:envelope')
log.error = debug('libp2p:envelope:error') log.error = debug('libp2p:envelope:error')
const errCode = require('err-code') const errCode = require('err-code')
const uint8arraysConcat = require('uint8arrays/concat')
const { Buffer } = require('buffer') const uint8arraysFromString = require('uint8arrays/from-string')
const cryptoKeys = require('libp2p-crypto/src/keys')
const crypto = require('libp2p-crypto')
const PeerId = require('peer-id') const PeerId = require('peer-id')
const varint = require('varint') const varint = require('varint')
const uint8arraysEquals = require('uint8arrays/equals')
const { codes } = require('../../errors') const { codes } = require('../../errors')
const Protobuf = require('./envelope.proto') const Protobuf = require('./envelope.proto')
@ -23,9 +23,9 @@ class Envelope {
* @constructor * @constructor
* @param {object} params * @param {object} params
* @param {PeerId} params.peerId * @param {PeerId} params.peerId
* @param {Buffer} params.payloadType * @param {Uint8Array} params.payloadType
* @param {Buffer} params.payload marshaled record * @param {Uint8Array} params.payload marshaled record
* @param {Buffer} params.signature signature of the domain string :: type hint :: payload. * @param {Uint8Array} params.signature signature of the domain string :: type hint :: payload.
*/ */
constructor ({ peerId, payloadType, payload, signature }) { constructor ({ peerId, payloadType, payload, signature }) {
this.peerId = peerId this.peerId = peerId
@ -39,14 +39,14 @@ class Envelope {
/** /**
* Marshal the envelope content. * Marshal the envelope content.
* @return {Buffer} * @return {Uint8Array}
*/ */
marshal () { marshal () {
if (this._marshal) { if (this._marshal) {
return this._marshal return this._marshal
} }
const publicKey = crypto.keys.marshalPublicKey(this.peerId.pubKey) const publicKey = cryptoKeys.marshalPublicKey(this.peerId.pubKey)
this._marshal = Protobuf.encode({ this._marshal = Protobuf.encode({
public_key: publicKey, public_key: publicKey,
@ -64,10 +64,10 @@ class Envelope {
* @return {boolean} * @return {boolean}
*/ */
equals (other) { equals (other) {
return this.peerId.pubKey.bytes.equals(other.peerId.pubKey.bytes) && return uint8arraysEquals(this.peerId.pubKey.bytes, other.peerId.pubKey.bytes) &&
this.payloadType.equals(other.payloadType) && uint8arraysEquals(this.payloadType, other.payloadType) &&
this.payload.equals(other.payload) && uint8arraysEquals(this.payload, other.payload) &&
this.signature.equals(other.signature) uint8arraysEquals(this.signature, other.signature)
} }
/** /**
@ -83,14 +83,14 @@ class Envelope {
} }
/** /**
* Helper function that prepares a buffer to sign or verify a signature. * Helper function that prepares a Uint8Array to sign or verify a signature.
* @param {string} domain * @param {string} domain
* @param {Buffer} payloadType * @param {Uint8Array} payloadType
* @param {Buffer} payload * @param {Uint8Array} payload
* @return {Buffer} * @return {Uint8Array}
*/ */
const formatSignaturePayload = (domain, payloadType, payload) => { const formatSignaturePayload = (domain, payloadType, payload) => {
// When signing, a peer will prepare a buffer by concatenating the following: // When signing, a peer will prepare a Uint8Array by concatenating the following:
// - The length of the domain separation string string in bytes // - The length of the domain separation string string in bytes
// - The domain separation string, encoded as UTF-8 // - The domain separation string, encoded as UTF-8
// - The length of the payload_type field in bytes // - The length of the payload_type field in bytes
@ -98,23 +98,24 @@ const formatSignaturePayload = (domain, payloadType, payload) => {
// - The length of the payload field in bytes // - The length of the payload field in bytes
// - The value of the payload field // - The value of the payload field
const domainLength = varint.encode(Buffer.byteLength(domain)) domain = uint8arraysFromString(domain)
const domainLength = varint.encode(domain.byteLength)
const payloadTypeLength = varint.encode(payloadType.length) const payloadTypeLength = varint.encode(payloadType.length)
const payloadLength = varint.encode(payload.length) const payloadLength = varint.encode(payload.length)
return Buffer.concat([ return uint8arraysConcat([
Buffer.from(domainLength), new Uint8Array(domainLength),
Buffer.from(domain), domain,
Buffer.from(payloadTypeLength), new Uint8Array(payloadTypeLength),
payloadType, payloadType,
Buffer.from(payloadLength), new Uint8Array(payloadLength),
payload payload
]) ])
} }
/** /**
* Unmarshal a serialized Envelope protobuf message. * Unmarshal a serialized Envelope protobuf message.
* @param {Buffer} data * @param {Uint8Array} data
* @return {Promise<Envelope>} * @return {Promise<Envelope>}
*/ */
Envelope.createFromProtobuf = async (data) => { Envelope.createFromProtobuf = async (data) => {
@ -139,7 +140,7 @@ Envelope.createFromProtobuf = async (data) => {
*/ */
Envelope.seal = async (record, peerId) => { Envelope.seal = async (record, peerId) => {
const domain = record.domain const domain = record.domain
const payloadType = Buffer.from(record.codec) const payloadType = uint8arraysFromString(record.codec)
const payload = record.marshal() const payload = record.marshal()
const signData = formatSignaturePayload(domain, payloadType, payload) const signData = formatSignaturePayload(domain, payloadType, payload)
@ -156,7 +157,7 @@ Envelope.seal = async (record, peerId) => {
/** /**
* Open and certify a given marshalled envelope. * Open and certify a given marshalled envelope.
* Data is unmarshalled and the signature validated for the given domain. * Data is unmarshalled and the signature validated for the given domain.
* @param {Buffer} data * @param {Uint8Array} data
* @param {string} domain * @param {string} domain
* @return {Envelope} * @return {Envelope}
*/ */

View File

@ -36,7 +36,7 @@ class PeerRecord extends Record {
/** /**
* Marshal a record to be used in an envelope. * Marshal a record to be used in an envelope.
* @return {Buffer} * @return {Uint8Array}
*/ */
marshal () { marshal () {
if (this._marshal) { if (this._marshal) {
@ -47,7 +47,7 @@ class PeerRecord extends Record {
peer_id: this.peerId.toBytes(), peer_id: this.peerId.toBytes(),
seq: this.seqNumber, seq: this.seqNumber,
addresses: this.multiaddrs.map((m) => ({ addresses: this.multiaddrs.map((m) => ({
multiaddr: m.buffer multiaddr: m.bytes
})) }))
}) })
@ -81,7 +81,7 @@ class PeerRecord extends Record {
/** /**
* Unmarshal Peer Record Protobuf. * Unmarshal Peer Record Protobuf.
* @param {Buffer} buf marshaled peer record. * @param {Uint8Array} buf marshaled peer record.
* @return {PeerRecord} * @return {PeerRecord}
*/ */
PeerRecord.createFromProtobuf = (buf) => { PeerRecord.createFromProtobuf = (buf) => {

View File

@ -3,6 +3,7 @@
const chai = require('chai') const chai = require('chai')
chai.use(require('dirty-chai')) chai.use(require('dirty-chai'))
chai.use(require('chai-as-promised'))
const { expect } = chai const { expect } = chai
const nock = require('nock') const nock = require('nock')
const sinon = require('sinon') const sinon = require('sinon')
@ -96,7 +97,7 @@ describe('content-routing', () => {
let delegate let delegate
beforeEach(async () => { beforeEach(async () => {
const [peerId] = await peerUtils.createPeerId({ fixture: false }) const [peerId] = await peerUtils.createPeerId({ fixture: true })
delegate = new DelegatedContentRouter(peerId, { delegate = new DelegatedContentRouter(peerId, {
host: '0.0.0.0', host: '0.0.0.0',
@ -227,7 +228,7 @@ describe('content-routing', () => {
let delegate let delegate
beforeEach(async () => { beforeEach(async () => {
const [peerId] = await peerUtils.createPeerId({ fixture: false }) const [peerId] = await peerUtils.createPeerId({ fixture: true })
delegate = new DelegatedContentRouter(peerId, { delegate = new DelegatedContentRouter(peerId, {
host: '0.0.0.0', host: '0.0.0.0',

View File

@ -1,14 +1,12 @@
'use strict' 'use strict'
/* eslint-env mocha */ /* eslint-env mocha */
const { Buffer } = require('buffer') const { expect } = require('aegir/utils/chai')
const chai = require('chai')
chai.use(require('dirty-chai'))
const { expect } = chai
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
const pWaitFor = require('p-wait-for') const pWaitFor = require('p-wait-for')
const mergeOptions = require('merge-options') const mergeOptions = require('merge-options')
const uint8ArrayFromString = require('uint8arrays/from-string')
const { create } = require('../../../src') const { create } = require('../../../src')
const { subsystemOptions, subsystemMulticodecs } = require('./utils') const { subsystemOptions, subsystemMulticodecs } = require('./utils')
@ -68,8 +66,8 @@ describe('DHT subsystem operates correctly', () => {
}) })
it('should put on a peer and get from the other', async () => { it('should put on a peer and get from the other', async () => {
const key = Buffer.from('hello') const key = uint8ArrayFromString('hello')
const value = Buffer.from('world') const value = uint8ArrayFromString('world')
await libp2p.dialProtocol(remAddr, subsystemMulticodecs) await libp2p.dialProtocol(remAddr, subsystemMulticodecs)
await Promise.all([ await Promise.all([
@ -131,8 +129,8 @@ describe('DHT subsystem operates correctly', () => {
it('should put on a peer and get from the other', async () => { it('should put on a peer and get from the other', async () => {
await libp2p.dial(remAddr) await libp2p.dial(remAddr)
const key = Buffer.from('hello') const key = uint8ArrayFromString('hello')
const value = Buffer.from('world') const value = uint8ArrayFromString('world')
await remoteLibp2p._dht.start() await remoteLibp2p._dht.start()
await pWaitFor(() => libp2p._dht.routingTable.size === 1) await pWaitFor(() => libp2p._dht.routingTable.size === 1)

View File

@ -1,11 +1,7 @@
'use strict' 'use strict'
/* eslint-env mocha */ /* eslint-env mocha */
const { Buffer } = require('buffer') const { expect } = require('aegir/utils/chai')
const chai = require('chai')
chai.use(require('dirty-chai'))
chai.use(require('chai-as-promised'))
const { expect } = chai
const sinon = require('sinon') const sinon = require('sinon')
const Transport = require('libp2p-tcp') const Transport = require('libp2p-tcp')
const Muxer = require('libp2p-mplex') const Muxer = require('libp2p-mplex')
@ -19,6 +15,7 @@ const pipe = require('it-pipe')
const AggregateError = require('aggregate-error') const AggregateError = require('aggregate-error')
const { Connection } = require('libp2p-interfaces/src/connection') const { Connection } = require('libp2p-interfaces/src/connection')
const { AbortError } = require('libp2p-interfaces/src/transport/errors') const { AbortError } = require('libp2p-interfaces/src/transport/errors')
const uint8ArrayFromString = require('uint8arrays/from-string')
const Libp2p = require('../../src') const Libp2p = require('../../src')
const Dialer = require('../../src/dialer') const Dialer = require('../../src/dialer')
@ -27,7 +24,7 @@ const PeerStore = require('../../src/peer-store')
const TransportManager = require('../../src/transport-manager') const TransportManager = require('../../src/transport-manager')
const { codes: ErrorCodes } = require('../../src/errors') const { codes: ErrorCodes } = require('../../src/errors')
const Protector = require('../../src/pnet') const Protector = require('../../src/pnet')
const swarmKeyBuffer = Buffer.from(require('../fixtures/swarm.key')) const swarmKeyBuffer = uint8ArrayFromString(require('../fixtures/swarm.key'))
const mockUpgrader = require('../utils/mockUpgrader') const mockUpgrader = require('../utils/mockUpgrader')
const createMockConnection = require('../utils/mockConnection') const createMockConnection = require('../utils/mockConnection')

View File

@ -1,7 +1,6 @@
'use strict' 'use strict'
/* eslint-env mocha */ /* eslint-env mocha */
const { Buffer } = require('buffer')
const chai = require('chai') const chai = require('chai')
chai.use(require('dirty-chai')) chai.use(require('dirty-chai'))
chai.use(require('chai-as-promised')) chai.use(require('chai-as-promised'))
@ -13,6 +12,7 @@ const { collect } = require('streaming-iterables')
const pipe = require('it-pipe') const pipe = require('it-pipe')
const AggregateError = require('aggregate-error') const AggregateError = require('aggregate-error')
const PeerId = require('peer-id') const PeerId = require('peer-id')
const uint8ArrayFromString = require('uint8arrays/from-string')
const { createPeerId } = require('../utils/creators/peer') const { createPeerId } = require('../utils/creators/peer')
const baseOptions = require('../utils/base-options') const baseOptions = require('../utils/base-options')
@ -88,7 +88,7 @@ describe('Dialing (via relay, TCP)', () => {
) )
const { stream: echoStream } = await connection.newStream('/echo/1.0.0') const { stream: echoStream } = await connection.newStream('/echo/1.0.0')
const input = Buffer.from('hello') const input = uint8ArrayFromString('hello')
const [output] = await pipe( const [output] = await pipe(
[input], [input],
echoStream, echoStream,
@ -162,7 +162,7 @@ describe('Dialing (via relay, TCP)', () => {
// Tamper with the our multiaddrs for the circuit message // Tamper with the our multiaddrs for the circuit message
sinon.stub(srcLibp2p, 'multiaddrs').value([{ sinon.stub(srcLibp2p, 'multiaddrs').value([{
buffer: Buffer.from('an invalid multiaddr') bytes: uint8ArrayFromString('an invalid multiaddr')
}]) }])
await expect(srcLibp2p.dial(dialAddr)) await expect(srcLibp2p.dial(dialAddr))

View File

@ -13,6 +13,7 @@ const PeerId = require('peer-id')
const duplexPair = require('it-pair/duplex') const duplexPair = require('it-pair/duplex')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
const pWaitFor = require('p-wait-for') const pWaitFor = require('p-wait-for')
const unit8ArrayToString = require('uint8arrays/to-string')
const { codes: Errors } = require('../../src/errors') const { codes: Errors } = require('../../src/errors')
const { IdentifyService, multicodecs } = require('../../src/identify') const { IdentifyService, multicodecs } = require('../../src/identify')
@ -148,7 +149,7 @@ describe('Identify', () => {
const metadataArgs = localIdentify.peerStore.metadataBook.set.firstCall.args const metadataArgs = localIdentify.peerStore.metadataBook.set.firstCall.args
expect(metadataArgs[0].id.bytes).to.equal(remotePeer.bytes) expect(metadataArgs[0].id.bytes).to.equal(remotePeer.bytes)
expect(metadataArgs[1]).to.equal('AgentVersion') expect(metadataArgs[1]).to.equal('AgentVersion')
expect(metadataArgs[2].toString()).to.equal(`js-libp2p/${pkg.version}`) expect(unit8ArrayToString(metadataArgs[2])).to.equal(`js-libp2p/${pkg.version}`)
// Validate the remote peer gets updated in the peer store // Validate the remote peer gets updated in the peer store
const call = localIdentify.peerStore.addressBook.set.firstCall const call = localIdentify.peerStore.addressBook.set.firstCall

View File

@ -1,7 +1,6 @@
'use strict' 'use strict'
/* eslint-env mocha */ /* eslint-env mocha */
const { Buffer } = require('buffer')
const chai = require('chai') const chai = require('chai')
chai.use(require('dirty-chai')) chai.use(require('dirty-chai'))
const { expect } = chai const { expect } = chai
@ -56,7 +55,7 @@ describe('plaintext', () => {
// When we attempt to get the remote peer key, return the wrong peers pub key // When we attempt to get the remote peer key, return the wrong peers pub key
sinon.stub(remotePeer, 'marshalPubKey').callsFake(() => { sinon.stub(remotePeer, 'marshalPubKey').callsFake(() => {
return Buffer.alloc(0) return new Uint8Array(0)
}) })
return Promise.all([ return Promise.all([

View File

@ -7,13 +7,9 @@ const dirtyChai = require('dirty-chai')
const expect = chai.expect const expect = chai.expect
chai.use(dirtyChai) chai.use(dirtyChai)
chai.use(require('chai-string')) chai.use(require('chai-string'))
const uint8ArrayFromString = require('uint8arrays/from-string')
const os = require('os') const uint8ArrayToString = require('uint8arrays/to-string')
const path = require('path') const { MemoryDatastore } = require('interface-datastore')
const { isNode } = require('ipfs-utils/src/env')
const FsStore = require('datastore-fs')
const LevelStore = require('datastore-level')
const Keychain = require('../../src/keychain') const Keychain = require('../../src/keychain')
describe('cms interop', () => { describe('cms interop', () => {
@ -22,13 +18,11 @@ describe('cms interop', () => {
let ks let ks
before(() => { before(() => {
const datastore = isNode const datastore = new MemoryDatastore()
? new FsStore(path.join(os.tmpdir(), 'test-keystore-1-' + Date.now()))
: new LevelStore('test-keystore-1', { db: require('level') })
ks = new Keychain(datastore, { passPhrase: passPhrase }) ks = new Keychain(datastore, { passPhrase: passPhrase })
}) })
const plainData = Buffer.from('This is a message from Alice to Bob') const plainData = uint8ArrayFromString('This is a message from Alice to Bob')
it('imports openssl key', async function () { it('imports openssl key', async function () {
this.timeout(10 * 1000) this.timeout(10 * 1000)
@ -67,8 +61,8 @@ knU1yykWGkdlbclCuu0NaAfmb8o0OX50CbEKZB7xmsv8tnqn0H0jMF4GCSqGSIb3
DQEHATAdBglghkgBZQMEASoEEP/PW1JWehQx6/dsLkp/Mf+gMgQwFM9liLTqC56B DQEHATAdBglghkgBZQMEASoEEP/PW1JWehQx6/dsLkp/Mf+gMgQwFM9liLTqC56B
nHILFmhac/+a/StQOKuf9dx5qXeGvt9LnwKuGGSfNX4g+dTkoa6N nHILFmhac/+a/StQOKuf9dx5qXeGvt9LnwKuGGSfNX4g+dTkoa6N
` `
const plain = await ks.cms.decrypt(Buffer.from(example, 'base64')) const plain = await ks.cms.decrypt(uint8ArrayFromString(example.replace(/\s/g, ''), 'base64'))
expect(plain).to.exist() expect(plain).to.exist()
expect(plain.toString()).to.equal(plainData.toString()) expect(uint8ArrayToString(plain)).to.equal(uint8ArrayToString(plainData))
}) })
}) })

View File

@ -5,15 +5,12 @@
const { chai, expect } = require('aegir/utils/chai') const { chai, expect } = require('aegir/utils/chai')
const fail = expect.fail const fail = expect.fail
chai.use(require('chai-string')) chai.use(require('chai-string'))
const uint8ArrayFromString = require('uint8arrays/from-string')
const uint8ArrayToString = require('uint8arrays/to-string')
const peerUtils = require('../utils/creators/peer') const peerUtils = require('../utils/creators/peer')
const os = require('os')
const path = require('path')
const { isNode } = require('ipfs-utils/src/env')
const { MemoryDatastore } = require('interface-datastore') const { MemoryDatastore } = require('interface-datastore')
const FsStore = require('datastore-fs')
const LevelStore = require('datastore-level')
const Keychain = require('../../src/keychain') const Keychain = require('../../src/keychain')
const PeerId = require('peer-id') const PeerId = require('peer-id')
@ -26,16 +23,20 @@ describe('keychain', () => {
let ks let ks
let datastore1, datastore2 let datastore1, datastore2
before(() => { before(async () => {
datastore1 = isNode datastore1 = new MemoryDatastore()
? new FsStore(path.join(os.tmpdir(), 'test-keystore-1-' + Date.now())) datastore2 = new MemoryDatastore()
: new LevelStore('test-keystore-1', { db: require('level') })
datastore2 = isNode
? new FsStore(path.join(os.tmpdir(), 'test-keystore-2-' + Date.now()))
: new LevelStore('test-keystore-2', { db: require('level') })
ks = new Keychain(datastore2, { passPhrase: passPhrase }) ks = new Keychain(datastore2, { passPhrase: passPhrase })
emptyKeystore = new Keychain(datastore1, { passPhrase: passPhrase }) emptyKeystore = new Keychain(datastore1, { passPhrase: passPhrase })
await datastore1.open()
await datastore2.open()
})
after(async () => {
await datastore2.close()
await datastore2.close()
}) })
it('can start without a password', () => { it('can start without a password', () => {
@ -74,7 +75,7 @@ describe('keychain', () => {
const keychainWithPassword = new Keychain(datastore2, { passPhrase: `hello-${Date.now()}-${Date.now()}` }) const keychainWithPassword = new Keychain(datastore2, { passPhrase: `hello-${Date.now()}-${Date.now()}` })
const id = `key-${Math.random()}` const id = `key-${Math.random()}`
await keychainWithPassword.createKey(id, 'rsa', 2048) await keychainWithPassword.createKey(id, 'ed25519')
await expect(keychain.findKeyById(id)).to.eventually.be.ok() await expect(keychain.findKeyById(id)).to.eventually.be.ok()
}) })
@ -84,7 +85,7 @@ describe('keychain', () => {
const keychainWithPassword = new Keychain(datastore2, { passPhrase: `hello-${Date.now()}-${Date.now()}` }) const keychainWithPassword = new Keychain(datastore2, { passPhrase: `hello-${Date.now()}-${Date.now()}` })
const name = `key-${Math.random()}` const name = `key-${Math.random()}`
expect(await keychainWithPassword.createKey(name, 'rsa', 2048)).to.have.property('name', name) expect(await keychainWithPassword.createKey(name, 'ed25519')).to.have.property('name', name)
expect(await keychainWithoutPassword.findKeyByName(name)).to.have.property('name', name) expect(await keychainWithoutPassword.findKeyByName(name)).to.have.property('name', name)
await keychainWithoutPassword.removeKey(name) await keychainWithoutPassword.removeKey(name)
await expect(keychainWithoutPassword.findKeyByName(name)).to.be.rejectedWith(/does not exist/) await expect(keychainWithoutPassword.findKeyByName(name)).to.be.rejectedWith(/does not exist/)
@ -278,7 +279,7 @@ describe('keychain', () => {
}) })
describe('CMS protected data', () => { describe('CMS protected data', () => {
const plainData = Buffer.from('This is a message from Alice to Bob') const plainData = uint8ArrayFromString('This is a message from Alice to Bob')
let cms let cms
it('service is available', () => { it('service is available', () => {
@ -291,7 +292,7 @@ describe('keychain', () => {
expect(err).to.have.property('code', 'ERR_KEY_NOT_FOUND') expect(err).to.have.property('code', 'ERR_KEY_NOT_FOUND')
}) })
it('requires plain data as a Buffer', async () => { it('requires plain data as a Uint8Array', async () => {
const err = await ks.cms.encrypt(rsaKeyName, 'plain data').then(fail, err => err) const err = await ks.cms.encrypt(rsaKeyName, 'plain data').then(fail, err => err)
expect(err).to.exist() expect(err).to.exist()
expect(err).to.have.property('code', 'ERR_INVALID_PARAMS') expect(err).to.have.property('code', 'ERR_INVALID_PARAMS')
@ -300,7 +301,7 @@ describe('keychain', () => {
it('encrypts', async () => { it('encrypts', async () => {
cms = await ks.cms.encrypt(rsaKeyName, plainData) cms = await ks.cms.encrypt(rsaKeyName, plainData)
expect(cms).to.exist() expect(cms).to.exist()
expect(cms).to.be.instanceOf(Buffer) expect(cms).to.be.instanceOf(Uint8Array)
}) })
it('is a PKCS #7 message', async () => { it('is a PKCS #7 message', async () => {
@ -326,7 +327,7 @@ describe('keychain', () => {
it('can be read with the key', async () => { it('can be read with the key', async () => {
const plain = await ks.cms.decrypt(cms) const plain = await ks.cms.decrypt(cms)
expect(plain).to.exist() expect(plain).to.exist()
expect(plain.toString()).to.equal(plainData.toString()) expect(uint8ArrayToString(plain)).to.equal(uint8ArrayToString(plainData))
}) })
}) })
@ -380,7 +381,7 @@ describe('keychain', () => {
let alice let alice
before(async function () { before(async function () {
const encoded = Buffer.from(alicePrivKey, 'base64') const encoded = uint8ArrayFromString(alicePrivKey, 'base64pad')
alice = await PeerId.createFromPrivKey(encoded) alice = await PeerId.createFromPrivKey(encoded)
}) })
@ -522,7 +523,7 @@ describe('libp2p.keychain', () => {
await libp2p.loadKeychain() await libp2p.loadKeychain()
const kInfo = await libp2p.keychain.createKey('keyName', 'rsa', 2048) const kInfo = await libp2p.keychain.createKey('keyName', 'ed25519')
expect(kInfo).to.exist() expect(kInfo).to.exist()
}) })
@ -555,7 +556,7 @@ describe('libp2p.keychain', () => {
}) })
await libp2p.loadKeychain() await libp2p.loadKeychain()
const kInfo = await libp2p.keychain.createKey('keyName', 'rsa', 2048) const kInfo = await libp2p.keychain.createKey('keyName', 'ed25519')
expect(kInfo).to.exist() expect(kInfo).to.exist()
const [libp2p2] = await peerUtils.createPeer({ const [libp2p2] = await peerUtils.createPeer({

View File

@ -10,6 +10,7 @@ const multihash = require('multihashes')
const crypto = require('libp2p-crypto') const crypto = require('libp2p-crypto')
const rsaUtils = require('libp2p-crypto/src/keys/rsa-utils') const rsaUtils = require('libp2p-crypto/src/keys/rsa-utils')
const rsaClass = require('libp2p-crypto/src/keys/rsa-class') const rsaClass = require('libp2p-crypto/src/keys/rsa-class')
const uint8ArrayFromString = require('uint8arrays/from-string')
const sample = { const sample = {
id: '122019318b6e5e0cf93a2314bf01269a2cc23cd3dcd452d742cdb9379d8646f6e4a9', id: '122019318b6e5e0cf93a2314bf01269a2cc23cd3dcd452d742cdb9379d8646f6e4a9',
@ -22,7 +23,7 @@ describe('peer ID', () => {
let publicKeyDer // a buffer let publicKeyDer // a buffer
before(async () => { before(async () => {
const encoded = Buffer.from(sample.privKey, 'base64') const encoded = uint8ArrayFromString(sample.privKey, 'base64pad')
peer = await PeerId.createFromPrivKey(encoded) peer = await PeerId.createFromPrivKey(encoded)
}) })

View File

@ -13,6 +13,7 @@ const crypto = require('libp2p-crypto')
const KadDht = require('libp2p-kad-dht') const KadDht = require('libp2p-kad-dht')
const MulticastDNS = require('libp2p-mdns') const MulticastDNS = require('libp2p-mdns')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
const uint8ArrayToString = require('uint8arrays/to-string')
const Libp2p = require('../../src') const Libp2p = require('../../src')
const baseOptions = require('../utils/base-options') const baseOptions = require('../utils/base-options')
@ -110,7 +111,7 @@ describe('peer discovery scenarios', () => {
enabled: true, enabled: true,
interval: 200, // discover quickly interval: 200, // discover quickly
// use a random tag to prevent CI collision // use a random tag to prevent CI collision
serviceTag: crypto.randomBytes(10).toString('hex') serviceTag: uint8ArrayToString(crypto.randomBytes(10), 'base16')
} }
} }
} }

View File

@ -5,6 +5,7 @@ const chai = require('chai')
chai.use(require('dirty-chai')) chai.use(require('dirty-chai'))
chai.use(require('chai-bytes')) chai.use(require('chai-bytes'))
const { expect } = chai const { expect } = chai
const uint8ArrayFromString = require('uint8arrays/from-string')
const pDefer = require('p-defer') const pDefer = require('p-defer')
const PeerStore = require('../../src/peer-store') const PeerStore = require('../../src/peer-store')
@ -76,7 +77,7 @@ describe('metadataBook', () => {
it('stores the content and emit change event', () => { it('stores the content and emit change event', () => {
const defer = pDefer() const defer = pDefer()
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
peerStore.once('change:metadata', ({ peerId, metadata }) => { peerStore.once('change:metadata', ({ peerId, metadata }) => {
expect(peerId).to.exist() expect(peerId).to.exist()
@ -99,8 +100,8 @@ describe('metadataBook', () => {
it('emits on set if not storing the exact same content', () => { it('emits on set if not storing the exact same content', () => {
const defer = pDefer() const defer = pDefer()
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue1 = Buffer.from('mars') const metadataValue1 = uint8ArrayFromString('mars')
const metadataValue2 = Buffer.from('saturn') const metadataValue2 = uint8ArrayFromString('saturn')
let changeCounter = 0 let changeCounter = 0
peerStore.on('change:metadata', () => { peerStore.on('change:metadata', () => {
@ -129,7 +130,7 @@ describe('metadataBook', () => {
it('does not emit on set if it is storing the exact same content', () => { it('does not emit on set if it is storing the exact same content', () => {
const defer = pDefer() const defer = pDefer()
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
let changeCounter = 0 let changeCounter = 0
peerStore.on('change:metadata', () => { peerStore.on('change:metadata', () => {
@ -180,7 +181,7 @@ describe('metadataBook', () => {
it('returns the metadata stored', () => { it('returns the metadata stored', () => {
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
mb.set(peerId, metadataKey, metadataValue) mb.set(peerId, metadataKey, metadataValue)
@ -217,7 +218,7 @@ describe('metadataBook', () => {
it('returns the metadata value stored for the given key', () => { it('returns the metadata value stored for the given key', () => {
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
mb.set(peerId, metadataKey, metadataValue) mb.set(peerId, metadataKey, metadataValue)
@ -229,7 +230,7 @@ describe('metadataBook', () => {
it('returns undefined if no metadata is known for the provided peer and key', () => { it('returns undefined if no metadata is known for the provided peer and key', () => {
const metadataKey = 'location' const metadataKey = 'location'
const metadataBadKey = 'nickname' const metadataBadKey = 'nickname'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
mb.set(peerId, metadataKey, metadataValue) mb.set(peerId, metadataKey, metadataValue)
@ -279,7 +280,7 @@ describe('metadataBook', () => {
it('returns true if the record exists and an event is emitted', () => { it('returns true if the record exists and an event is emitted', () => {
const defer = pDefer() const defer = pDefer()
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
mb.set(peerId, metadataKey, metadataValue) mb.set(peerId, metadataKey, metadataValue)
@ -337,7 +338,7 @@ describe('metadataBook', () => {
it('returns true if the record exists and an event is emitted', () => { it('returns true if the record exists and an event is emitted', () => {
const defer = pDefer() const defer = pDefer()
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
mb.set(peerId, metadataKey, metadataValue) mb.set(peerId, metadataKey, metadataValue)
@ -357,7 +358,7 @@ describe('metadataBook', () => {
const defer = pDefer() const defer = pDefer()
const metadataKey = 'location' const metadataKey = 'location'
const metadataBadKey = 'nickname' const metadataBadKey = 'nickname'
const metadataValue = Buffer.from('mars') const metadataValue = uint8ArrayFromString('mars')
mb.set(peerId, metadataKey, metadataValue) mb.set(peerId, metadataKey, metadataValue)

View File

@ -7,6 +7,7 @@ const { expect } = chai
const PeerStore = require('../../src/peer-store') const PeerStore = require('../../src/peer-store')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
const uint8ArrayFromString = require('uint8arrays/from-string')
const peerUtils = require('../utils/creators/peer') const peerUtils = require('../utils/creators/peer')
@ -196,7 +197,7 @@ describe('peer-store', () => {
it('returns peers if only metadata is known', () => { it('returns peers if only metadata is known', () => {
const metadataKey = 'location' const metadataKey = 'location'
const metadataValue = Buffer.from('earth') const metadataValue = uint8ArrayFromString('earth')
peerStore.metadataBook.set(peerIds[0], metadataKey, metadataValue) peerStore.metadataBook.set(peerIds[0], metadataKey, metadataValue)
const peers = peerStore.peers const peers = peerStore.peers

View File

@ -12,6 +12,7 @@ const PeerStore = require('../../src/peer-store/persistent')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
const { MemoryDatastore } = require('interface-datastore') const { MemoryDatastore } = require('interface-datastore')
const uint8ArrayFromString = require('uint8arrays/from-string')
const peerUtils = require('../utils/creators/peer') const peerUtils = require('../utils/creators/peer')
@ -145,7 +146,7 @@ describe('Persisted PeerStore', () => {
await Promise.all(commitSpy.returnValues) await Promise.all(commitSpy.returnValues)
// MetadataBook // MetadataBook
peerStore.metadataBook.set(peers[0], 'location', Buffer.from('earth')) peerStore.metadataBook.set(peers[0], 'location', uint8ArrayFromString('earth'))
// let batch commit complete // let batch commit complete
await Promise.all(commitSpy.returnValues) await Promise.all(commitSpy.returnValues)
@ -186,7 +187,7 @@ describe('Persisted PeerStore', () => {
// ProtoBook // ProtoBook
peerStore.protoBook.set(peer, protocols) peerStore.protoBook.set(peer, protocols)
// MetadataBook // MetadataBook
peerStore.metadataBook.set(peer, 'location', Buffer.from('earth')) peerStore.metadataBook.set(peer, 'location', uint8ArrayFromString('earth'))
// let batch commit complete // let batch commit complete
await Promise.all(commitSpy.returnValues) await Promise.all(commitSpy.returnValues)
@ -408,7 +409,7 @@ describe('Persisted PeerStore', () => {
// Add Peer0 data in multiple books // Add Peer0 data in multiple books
peerStore.addressBook.set(peers[0], multiaddrs) peerStore.addressBook.set(peers[0], multiaddrs)
peerStore.protoBook.set(peers[0], protocols) peerStore.protoBook.set(peers[0], protocols)
peerStore.metadataBook.set(peers[0], 'location', Buffer.from('earth')) peerStore.metadataBook.set(peers[0], 'location', uint8ArrayFromString('earth'))
// let batch commit complete // let batch commit complete
await Promise.all(commitSpy.returnValues) await Promise.all(commitSpy.returnValues)

View File

@ -1,7 +1,6 @@
/* eslint-env mocha */ /* eslint-env mocha */
'use strict' 'use strict'
const { Buffer } = require('buffer')
const chai = require('chai') const chai = require('chai')
const dirtyChai = require('dirty-chai') const dirtyChai = require('dirty-chai')
chai.use(dirtyChai) chai.use(dirtyChai)
@ -9,13 +8,14 @@ const expect = chai.expect
const duplexPair = require('it-pair/duplex') const duplexPair = require('it-pair/duplex')
const pipe = require('it-pipe') const pipe = require('it-pipe')
const { collect } = require('streaming-iterables') const { collect } = require('streaming-iterables')
const uint8ArrayFromString = require('uint8arrays/from-string')
const Protector = require('../../src/pnet') const Protector = require('../../src/pnet')
const Errors = Protector.errors const Errors = Protector.errors
const generate = Protector.generate const generate = Protector.generate
const swarmKeyBuffer = Buffer.alloc(95) const swarmKeyBuffer = new Uint8Array(95)
const wrongSwarmKeyBuffer = Buffer.alloc(95) const wrongSwarmKeyBuffer = new Uint8Array(95)
// Write new psk files to the buffers // Write new psk files to the buffers
generate(swarmKeyBuffer) generate(swarmKeyBuffer)
@ -39,7 +39,7 @@ describe('private network', () => {
]) ])
pipe( pipe(
[Buffer.from('hello world'), Buffer.from('doo dah')], [uint8ArrayFromString('hello world'), uint8ArrayFromString('doo dah')],
aToB aToB
) )
@ -53,7 +53,7 @@ describe('private network', () => {
collect collect
) )
expect(output).to.eql([Buffer.from('hello world'), Buffer.from('doo dah')]) expect(output).to.eql([uint8ArrayFromString('hello world'), uint8ArrayFromString('doo dah')])
}) })
it('should not be able to share correct data with different keys', async () => { it('should not be able to share correct data with different keys', async () => {
@ -67,7 +67,7 @@ describe('private network', () => {
]) ])
pipe( pipe(
[Buffer.from('hello world'), Buffer.from('doo dah')], [uint8ArrayFromString('hello world'), uint8ArrayFromString('doo dah')],
aToB aToB
) )
@ -76,19 +76,19 @@ describe('private network', () => {
collect collect
) )
expect(output).to.not.eql([Buffer.from('hello world'), Buffer.from('doo dah')]) expect(output).to.not.eql([uint8ArrayFromString('hello world'), uint8ArrayFromString('doo dah')])
}) })
describe('invalid psks', () => { describe('invalid psks', () => {
it('should not accept a bad psk', () => { it('should not accept a bad psk', () => {
expect(() => { expect(() => {
return new Protector(Buffer.from('not-a-key')) return new Protector(uint8ArrayFromString('not-a-key'))
}).to.throw(Errors.INVALID_PSK) }).to.throw(Errors.INVALID_PSK)
}) })
it('should not accept a psk of incorrect length', () => { it('should not accept a psk of incorrect length', () => {
expect(() => { expect(() => {
return new Protector(Buffer.from('/key/swarm/psk/1.0.0/\n/base16/\ndffb7e')) return new Protector(uint8ArrayFromString('/key/swarm/psk/1.0.0/\n/base16/\ndffb7e'))
}).to.throw(Errors.INVALID_PSK) }).to.throw(Errors.INVALID_PSK)
}) })
}) })

View File

@ -13,6 +13,7 @@ const Floodsub = require('libp2p-floodsub')
const Gossipsub = require('libp2p-gossipsub') const Gossipsub = require('libp2p-gossipsub')
const { multicodec: floodsubMulticodec } = require('libp2p-floodsub') const { multicodec: floodsubMulticodec } = require('libp2p-floodsub')
const { multicodec: gossipsubMulticodec } = require('libp2p-gossipsub') const { multicodec: gossipsubMulticodec } = require('libp2p-gossipsub')
const uint8ArrayToString = require('uint8arrays/to-string')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
@ -81,7 +82,7 @@ describe('Pubsub subsystem is able to use different implementations', () => {
expect(connection).to.exist() expect(connection).to.exist()
libp2p.pubsub.subscribe(topic, (msg) => { libp2p.pubsub.subscribe(topic, (msg) => {
expect(msg.data.toString()).to.equal(data) expect(uint8ArrayToString(msg.data)).to.equal(data)
defer.resolve() defer.resolve()
}) })

View File

@ -10,6 +10,7 @@ const pWaitFor = require('p-wait-for')
const pDefer = require('p-defer') const pDefer = require('p-defer')
const mergeOptions = require('merge-options') const mergeOptions = require('merge-options')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
const uint8ArrayToString = require('uint8arrays/to-string')
const { create } = require('../../src') const { create } = require('../../src')
const { subsystemOptions, subsystemMulticodecs } = require('./utils') const { subsystemOptions, subsystemMulticodecs } = require('./utils')
@ -82,7 +83,7 @@ describe('Pubsub subsystem operates correctly', () => {
expect(subscribedTopics).to.not.include(topic) expect(subscribedTopics).to.not.include(topic)
libp2p.pubsub.subscribe(topic, (msg) => { libp2p.pubsub.subscribe(topic, (msg) => {
expect(msg.data.toString()).to.equal(data) expect(uint8ArrayToString(msg.data)).to.equal(data)
defer.resolve() defer.resolve()
}) })
@ -171,7 +172,7 @@ describe('Pubsub subsystem operates correctly', () => {
expect(subscribedTopics).to.not.include(topic) expect(subscribedTopics).to.not.include(topic)
libp2p.pubsub.subscribe(topic, (msg) => { libp2p.pubsub.subscribe(topic, (msg) => {
expect(msg.data.toString()).to.equal(data) expect(uint8ArrayToString(msg.data)).to.equal(data)
defer.resolve() defer.resolve()
}) })
@ -242,7 +243,7 @@ describe('Pubsub subsystem operates correctly', () => {
const defer1 = pDefer() const defer1 = pDefer()
const defer2 = pDefer() const defer2 = pDefer()
const handler = (msg) => { const handler = (msg) => {
expect(msg.data.toString()).to.equal(data) expect(uint8ArrayToString(msg.data)).to.equal(data)
counter++ counter++
counter === 1 ? defer1.resolve() : defer2.resolve() counter === 1 ? defer1.resolve() : defer2.resolve()
} }
@ -307,7 +308,7 @@ describe('Pubsub subsystem operates correctly', () => {
libp2p.pubsub.publish(topic, 'message1') libp2p.pubsub.publish(topic, 'message1')
remoteLibp2p.pubsub.publish(topic, 'message2') remoteLibp2p.pubsub.publish(topic, 'message2')
await pWaitFor(() => handlerSpy.callCount === 2) await pWaitFor(() => handlerSpy.callCount === 2)
expect(handlerSpy.args.map(([message]) => message.data.toString())).to.include.members(['message1', 'message2']) expect(handlerSpy.args.map(([message]) => uint8ArrayToString(message.data))).to.include.members(['message1', 'message2'])
// Disconnect the first connection (this acts as a delayed reconnect) // Disconnect the first connection (this acts as a delayed reconnect)
await originalConnection.close() await originalConnection.close()
@ -317,7 +318,7 @@ describe('Pubsub subsystem operates correctly', () => {
libp2p.pubsub.publish(topic, 'message3') libp2p.pubsub.publish(topic, 'message3')
remoteLibp2p.pubsub.publish(topic, 'message4') remoteLibp2p.pubsub.publish(topic, 'message4')
await pWaitFor(() => handlerSpy.callCount === 2) await pWaitFor(() => handlerSpy.callCount === 2)
expect(handlerSpy.args.map(([message]) => message.data.toString())).to.include.members(['message3', 'message4']) expect(handlerSpy.args.map(([message]) => uint8ArrayToString(message.data))).to.include.members(['message3', 'message4'])
}) })
}) })
}) })

View File

@ -4,6 +4,7 @@
const chai = require('chai') const chai = require('chai')
chai.use(require('dirty-chai')) chai.use(require('dirty-chai'))
chai.use(require('chai-bytes')) chai.use(require('chai-bytes'))
chai.use(require('chai-as-promised'))
const { expect } = chai const { expect } = chai
const Envelope = require('../../src/record/envelope') const Envelope = require('../../src/record/envelope')

View File

@ -1,11 +1,7 @@
'use strict' 'use strict'
/* eslint-env mocha */ /* eslint-env mocha */
const { Buffer } = require('buffer') const { expect } = require('aegir/utils/chai')
const chai = require('chai')
chai.use(require('dirty-chai'))
chai.use(require('chai-as-promised'))
const { expect } = chai
const sinon = require('sinon') const sinon = require('sinon')
const Muxer = require('libp2p-mplex') const Muxer = require('libp2p-mplex')
const multiaddr = require('multiaddr') const multiaddr = require('multiaddr')
@ -16,7 +12,8 @@ const pSettle = require('p-settle')
const Transport = require('libp2p-websockets') const Transport = require('libp2p-websockets')
const { NOISE: Crypto } = require('libp2p-noise') const { NOISE: Crypto } = require('libp2p-noise')
const Protector = require('../../src/pnet') const Protector = require('../../src/pnet')
const swarmKeyBuffer = Buffer.from(require('../fixtures/swarm.key')) const uint8ArrayFromString = require('uint8arrays/from-string')
const swarmKeyBuffer = uint8ArrayFromString(require('../fixtures/swarm.key'))
const Libp2p = require('../../src') const Libp2p = require('../../src')
const Upgrader = require('../../src/upgrader') const Upgrader = require('../../src/upgrader')
@ -102,7 +99,7 @@ describe('Upgrader', () => {
const { stream, protocol } = await connections[0].newStream('/echo/1.0.0') const { stream, protocol } = await connections[0].newStream('/echo/1.0.0')
expect(protocol).to.equal('/echo/1.0.0') expect(protocol).to.equal('/echo/1.0.0')
const hello = Buffer.from('hello there!') const hello = uint8ArrayFromString('hello there!')
const result = await pipe( const result = await pipe(
[hello], [hello],
stream, stream,
@ -172,7 +169,7 @@ describe('Upgrader', () => {
const { stream, protocol } = await connections[0].newStream('/echo/1.0.0') const { stream, protocol } = await connections[0].newStream('/echo/1.0.0')
expect(protocol).to.equal('/echo/1.0.0') expect(protocol).to.equal('/echo/1.0.0')
const hello = Buffer.from('hello there!') const hello = uint8ArrayFromString('hello there!')
const result = await pipe( const result = await pipe(
[hello], [hello],
stream, stream,