diff --git a/examples/browser-browserify/src/index.js b/examples/browser-browserify/src/index.js
index 7397c159c3..96836f860c 100644
--- a/examples/browser-browserify/src/index.js
+++ b/examples/browser-browserify/src/index.js
@@ -3,7 +3,12 @@
const IPFS = require('ipfs')
document.addEventListener('DOMContentLoaded', async () => {
- const node = await IPFS.create({ repo: String(Math.random() + Date.now()) })
+ const node = await IPFS.create({
+ repo: String(Math.random() + Date.now()),
+ init: { alogorithm: 'ed25519' }
+
+ })
+ const button = document.getElementById('store')
console.log('IPFS node is ready')
@@ -25,5 +30,6 @@ document.addEventListener('DOMContentLoaded', async () => {
}
}
- document.getElementById('store').onclick = store
+ button.onclick = store
+ button.setAttribute('style', 'display: inline')
})
diff --git a/examples/browser-browserify/test.js b/examples/browser-browserify/test.js
index f3e8df812c..516c302a87 100644
--- a/examples/browser-browserify/test.js
+++ b/examples/browser-browserify/test.js
@@ -9,9 +9,8 @@ module.exports = {
.waitForElementVisible('#source')
.setValue('#source', 'hello')
.waitForElementVisible('#store')
- .pause(1000)
.click('#store')
- .waitForElementVisible('#output')
+ .waitForElementVisible('#output', 5e3, 100)
browser.expect.element('#cid').text.to.contain('QmWfVY9y3xjsixTgbd9AorQxH7VtMpzfx2HaWtsoUYecaX')
browser.expect.element('#content').text.to.contain('hello')
diff --git a/examples/circuit-relaying/index.html b/examples/circuit-relaying/index.html
index e5ad98cb03..aecb20e112 100644
--- a/examples/circuit-relaying/index.html
+++ b/examples/circuit-relaying/index.html
@@ -46,7 +46,7 @@
diff --git a/examples/circuit-relaying/src/app.js b/examples/circuit-relaying/src/app.js
index 15619cc898..ffc97f877c 100644
--- a/examples/circuit-relaying/src/app.js
+++ b/examples/circuit-relaying/src/app.js
@@ -54,6 +54,7 @@ document.addEventListener('DOMContentLoaded', async () => {
let room = createRoom(roomName)
+ $peerId.setAttribute('style', '')
$peerId.innerHTML = `
${info.id}`
$send.addEventListener('click', () => {
diff --git a/examples/circuit-relaying/src/helpers.js b/examples/circuit-relaying/src/helpers.js
index 6b84940600..255b9be2c0 100644
--- a/examples/circuit-relaying/src/helpers.js
+++ b/examples/circuit-relaying/src/helpers.js
@@ -7,7 +7,6 @@ const $msgs = document.querySelector('#msgs')
const $addrs = document.querySelector('#addrs')
const $peers = document.querySelector('#peers')
const $pAddrs = document.querySelector('#peers-addrs')
-const delay = require('delay')
const NAMESPACE = 'ipfs-quick-msg'
diff --git a/examples/circuit-relaying/test.js b/examples/circuit-relaying/test.js
index 2b1c4e404f..274e695e6b 100644
--- a/examples/circuit-relaying/test.js
+++ b/examples/circuit-relaying/test.js
@@ -91,10 +91,10 @@ module.exports[pkg.name] = function (browser) {
browser
.url(process.env.IPFS_EXAMPLE_TEST_URL)
- .waitForElementVisible('#peer')
+ .waitForElementVisible('#peer-id') // Wait for ipfs to start
.clearValue('#peer')
.setValue('#peer', process.env.IPFS_RELAY_ADDRESS)
- .pause(1000)
+ .pause(100)
.click('#connect')
browser.expect.element('#peers-addrs').text.to.contain(process.env.IPFS_RELAY_ID)
diff --git a/packages/interface-ipfs-core/package.json b/packages/interface-ipfs-core/package.json
index cff0f8dfdb..d9b83216d9 100644
--- a/packages/interface-ipfs-core/package.json
+++ b/packages/interface-ipfs-core/package.json
@@ -52,6 +52,7 @@
"it-drain": "^1.0.1",
"it-last": "^1.0.1",
"it-pushable": "^1.3.1",
+ "libp2p-crypto": "^0.17.9",
"multiaddr": "^7.4.3",
"multibase": "^1.0.1",
"multihashing-async": "^1.0.0",
diff --git a/packages/interface-ipfs-core/src/key/export.js b/packages/interface-ipfs-core/src/key/export.js
deleted file mode 100644
index 160af76ce4..0000000000
--- a/packages/interface-ipfs-core/src/key/export.js
+++ /dev/null
@@ -1,37 +0,0 @@
-/* eslint-env mocha */
-'use strict'
-
-const { nanoid } = require('nanoid')
-const { getDescribe, getIt, expect } = require('../utils/mocha')
-const testTimeout = require('../utils/test-timeout')
-
-/** @typedef { import("ipfsd-ctl/src/factory") } Factory */
-/**
- * @param {Factory} common
- * @param {Object} options
- */
-module.exports = (common, options) => {
- const describe = getDescribe(options)
- const it = getIt(options)
-
- describe('.key.export', () => {
- let ipfs
-
- before(async () => {
- ipfs = (await common.spawn()).api
- })
-
- after(() => common.clean())
-
- it('should respect timeout option when exporting a key', () => {
- return testTimeout(() => ipfs.key.export('self', nanoid(), {
- timeout: 1
- }))
- })
-
- it('should export "self" key', async function () {
- const pem = await ipfs.key.export('self', nanoid())
- expect(pem).to.exist()
- })
- })
-}
diff --git a/packages/interface-ipfs-core/src/key/import.js b/packages/interface-ipfs-core/src/key/import.js
index 6bc116e6c6..9c7721ad65 100644
--- a/packages/interface-ipfs-core/src/key/import.js
+++ b/packages/interface-ipfs-core/src/key/import.js
@@ -2,6 +2,7 @@
'use strict'
const { nanoid } = require('nanoid')
+const keys = require('libp2p-crypto/src/keys')
const { getDescribe, getIt, expect } = require('../utils/mocha')
const testTimeout = require('../utils/test-timeout')
@@ -26,10 +27,10 @@ module.exports = (common, options) => {
it('should respect timeout option when importing a key', async () => {
const password = nanoid()
- const pem = await ipfs.key.export('self', password)
- expect(pem).to.exist()
+ const key = await keys.generateKeyPair('ed25519')
+ const exported = key.export(password)
- await testTimeout(() => ipfs.key.import('derp', pem, password, {
+ await testTimeout(() => ipfs.key.import('derp', exported, password, {
timeout: 1
}))
})
@@ -37,13 +38,13 @@ module.exports = (common, options) => {
it('should import an exported key', async () => {
const password = nanoid()
- const pem = await ipfs.key.export('self', password)
- expect(pem).to.exist()
+ const key = await keys.generateKeyPair('ed25519')
+ const exported = await key.export(password)
- const key = await ipfs.key.import('clone', pem, password)
- expect(key).to.exist()
- expect(key).to.have.property('name', 'clone')
- expect(key).to.have.property('id')
+ const importedKey = await ipfs.key.import('clone', exported, password)
+ expect(importedKey).to.exist()
+ expect(importedKey).to.have.property('name', 'clone')
+ expect(importedKey).to.have.property('id')
})
})
}
diff --git a/packages/interface-ipfs-core/src/key/index.js b/packages/interface-ipfs-core/src/key/index.js
index cbe2aaa358..a96414e4a0 100644
--- a/packages/interface-ipfs-core/src/key/index.js
+++ b/packages/interface-ipfs-core/src/key/index.js
@@ -6,7 +6,6 @@ const tests = {
list: require('./list'),
rename: require('./rename'),
rm: require('./rm'),
- export: require('./export'),
import: require('./import')
}
diff --git a/packages/ipfs-http-client/src/key/export.js b/packages/ipfs-http-client/src/key/export.js
deleted file mode 100644
index 1692fef16f..0000000000
--- a/packages/ipfs-http-client/src/key/export.js
+++ /dev/null
@@ -1,26 +0,0 @@
-'use strict'
-
-const configure = require('../lib/configure')
-const toUrlSearchParams = require('../lib/to-url-search-params')
-
-module.exports = configure(api => {
- return async (name, password, options = {}) => {
- if (typeof password !== 'string') {
- options = password || {}
- password = null
- }
-
- const res = await api.post('key/export', {
- timeout: options.timeout,
- signal: options.signal,
- searchParams: toUrlSearchParams({
- arg: name,
- password: password,
- ...options
- }),
- headers: options.headers
- })
-
- return res.text()
- }
-})
diff --git a/packages/ipfs-http-client/src/key/index.js b/packages/ipfs-http-client/src/key/index.js
index de12c732c8..c9d9c59f08 100644
--- a/packages/ipfs-http-client/src/key/index.js
+++ b/packages/ipfs-http-client/src/key/index.js
@@ -5,6 +5,5 @@ module.exports = config => ({
list: require('./list')(config),
rename: require('./rename')(config),
rm: require('./rm')(config),
- export: require('./export')(config),
import: require('./import')(config)
})
diff --git a/packages/ipfs/docs/MODULE.md b/packages/ipfs/docs/MODULE.md
index 9e05865ba9..9aa2012d6b 100644
--- a/packages/ipfs/docs/MODULE.md
+++ b/packages/ipfs/docs/MODULE.md
@@ -94,7 +94,8 @@ Note that *initializing* a repo is different from creating an instance of [`ipfs
Instead of a boolean, you may provide an object with custom initialization options. All properties are optional:
- `emptyRepo` (boolean) Whether to remove built-in assets, like the instructional tour and empty mutable file system, from the repo. (Default: `false`)
-- `bits` (number) Number of bits to use in the generated key pair. (Default: `2048`)
+- `algorithm` (string) The type of key to use. Supports `rsa`, `ed25519`, `secp256k1`. (Default: `rsa`)
+- `bits` (number) Number of bits to use in the generated key pair (rsa only). (Default: `2048`)
- `privateKey` (string/PeerId) A pre-generated private key to use. Can be either a base64 string or a [PeerId](https://github.com/libp2p/js-peer-id) instance. **NOTE: This overrides `bits`.**
```js
// Generating a Peer ID:
diff --git a/packages/ipfs/package.json b/packages/ipfs/package.json
index c1af7a5f4a..4a7cdddb45 100644
--- a/packages/ipfs/package.json
+++ b/packages/ipfs/package.json
@@ -129,9 +129,9 @@
"iterable-ndjson": "^1.1.0",
"jsondiffpatch": "^0.4.1",
"just-safe-set": "^2.1.0",
- "libp2p": "^0.28.5",
+ "libp2p": "^0.28.10",
"libp2p-bootstrap": "^0.11.0",
- "libp2p-crypto": "^0.17.8",
+ "libp2p-crypto": "^0.17.9",
"libp2p-delegated-content-routing": "^0.5.0",
"libp2p-delegated-peer-routing": "^0.5.0",
"libp2p-floodsub": "^0.21.0",
diff --git a/packages/ipfs/src/cli/commands/init.js b/packages/ipfs/src/cli/commands/init.js
index 76fa703d71..9b13636e51 100644
--- a/packages/ipfs/src/cli/commands/init.js
+++ b/packages/ipfs/src/cli/commands/init.js
@@ -17,6 +17,12 @@ module.exports = {
describe: 'Node config, this should be a path to a file or JSON and will be merged with the default config. See https://github.com/ipfs/js-ipfs#optionsconfig',
type: 'string'
})
+ .option('algorithm', {
+ type: 'string',
+ alias: 'a',
+ default: 'rsa',
+ describe: 'Cryptographic algorithm to use for key generation. Supports [rsa, ed25519, secp256k1]'
+ })
.option('bits', {
type: 'number',
alias: 'b',
@@ -72,6 +78,7 @@ module.exports = {
try {
await node.init({
+ algorithm: argv.algorithm,
bits: argv.bits,
privateKey: argv.privateKey,
emptyRepo: argv.emptyRepo,
diff --git a/packages/ipfs/src/core/components/init.js b/packages/ipfs/src/core/components/init.js
index 3474d14bd4..b751462c05 100644
--- a/packages/ipfs/src/core/components/init.js
+++ b/packages/ipfs/src/core/components/init.js
@@ -174,7 +174,7 @@ module.exports = ({
return apiManager.api
}
-async function initNewRepo (repo, { privateKey, emptyRepo, bits, profiles, config, pass, print }) {
+async function initNewRepo (repo, { privateKey, emptyRepo, algorithm, bits, profiles, config, pass, print }) {
emptyRepo = emptyRepo || false
bits = bits == null ? 2048 : Number(bits)
@@ -188,7 +188,7 @@ async function initNewRepo (repo, { privateKey, emptyRepo, bits, profiles, confi
throw new Error('repo already exists')
}
- const peerId = await createPeerId({ privateKey, bits, print })
+ const peerId = await createPeerId({ privateKey, algorithm, bits, print })
log('identity generated')
@@ -257,7 +257,7 @@ async function initExistingRepo (repo, { config: newConfig, profiles, pass }) {
return { peerId, keychain: libp2p.keychain }
}
-function createPeerId ({ privateKey, bits, print }) {
+function createPeerId ({ privateKey, algorithm = 'rsa', bits, print }) {
if (privateKey) {
log('using user-supplied private-key')
return typeof privateKey === 'object'
@@ -265,8 +265,8 @@ function createPeerId ({ privateKey, bits, print }) {
: PeerId.createFromPrivKey(Buffer.from(privateKey, 'base64'))
} else {
// Generate peer identity keypair + transform to desired format + add to config.
- print('generating %s-bit RSA keypair...', bits)
- return PeerId.create({ bits })
+ print('generating %s-bit (rsa only) %s keypair...', bits, algorithm)
+ return PeerId.create({ keyType: algorithm, bits })
}
}
diff --git a/packages/ipfs/src/core/components/name/publish.js b/packages/ipfs/src/core/components/name/publish.js
index 0908d9df9c..753def749b 100644
--- a/packages/ipfs/src/core/components/name/publish.js
+++ b/packages/ipfs/src/core/components/name/publish.js
@@ -21,16 +21,16 @@ const { resolvePath } = require('./utils')
* @param {IPFS} self
* @returns {Object}
*/
-module.exports = ({ ipns, dag, peerId, isOnline, keychain, options: constructorOptions }) => {
+module.exports = ({ ipns, dag, peerId, isOnline, keychain }) => {
const lookupKey = async keyName => {
if (keyName === 'self') {
return peerId.privKey
}
try {
- const pass = constructorOptions.pass
- const pem = await keychain.exportKey(keyName, pass)
- const privateKey = await crypto.keys.import(pem, pass)
+ // We're exporting and immediately importing the key, so we can just use a throw away password
+ const pem = await keychain.exportKey(keyName, 'temp')
+ const privateKey = await crypto.keys.import(pem, 'temp')
return privateKey
} catch (err) {
log.error(err)
diff --git a/packages/ipfs/src/http/api/resources/key.js b/packages/ipfs/src/http/api/resources/key.js
index b9d2a5b44d..c935f9a6a0 100644
--- a/packages/ipfs/src/http/api/resources/key.js
+++ b/packages/ipfs/src/http/api/resources/key.js
@@ -181,50 +181,6 @@ exports.gen = {
}
}
-exports.export = {
- options: {
- validate: {
- options: {
- allowUnknown: true,
- stripUnknown: true
- },
- query: Joi.object().keys({
- name: Joi.string().required(),
- password: Joi.string().required(),
- timeout: Joi.timeout()
- })
- .rename('arg', 'name', {
- override: true,
- ignoreUndefined: true
- })
- }
- },
- handler: async (request, h) => {
- const {
- app: {
- signal
- },
- server: {
- app: {
- ipfs
- }
- },
- query: {
- name,
- password,
- timeout
- }
- } = request
-
- const pem = await ipfs.key.export(name, password, {
- signal,
- timeout
- })
-
- return h.response(pem).type('application/x-pem-file')
- }
-}
-
exports.import = {
options: {
validate: {
diff --git a/packages/ipfs/src/http/api/resources/name.js b/packages/ipfs/src/http/api/resources/name.js
index 4bb39d2671..a7663728af 100644
--- a/packages/ipfs/src/http/api/resources/name.js
+++ b/packages/ipfs/src/http/api/resources/name.js
@@ -80,7 +80,7 @@ exports.publish = {
name: Joi.string().required(),
resolve: Joi.boolean().default(true),
lifetime: Joi.string().default('24h'),
- ttl: Joi.string(),
+ ttl: Joi.string().allow(''),
key: Joi.string().default('self'),
allowOffline: Joi.boolean(),
timeout: Joi.timeout()
diff --git a/packages/ipfs/src/http/api/routes/key.js b/packages/ipfs/src/http/api/routes/key.js
index 8290f617e5..c4bdb42bb3 100644
--- a/packages/ipfs/src/http/api/routes/key.js
+++ b/packages/ipfs/src/http/api/routes/key.js
@@ -23,11 +23,6 @@ module.exports = [
path: '/api/v0/key/rename',
...resources.key.rename
},
- {
- method: 'POST',
- path: '/api/v0/key/export',
- ...resources.key.export
- },
{
method: 'POST',
path: '/api/v0/key/import',
diff --git a/packages/ipfs/test/cli/init.js b/packages/ipfs/test/cli/init.js
index f7bf81f826..601733332c 100644
--- a/packages/ipfs/test/cli/init.js
+++ b/packages/ipfs/test/cli/init.js
@@ -4,6 +4,8 @@
const { expect } = require('interface-ipfs-core/src/utils/mocha')
const path = require('path')
const fs = require('fs')
+const PeerId = require('peer-id')
+const { supportedKeys } = require('libp2p-crypto/src/keys')
const clean = require('../utils/clean')
const { nanoid } = require('nanoid')
const ipfsExec = require('../utils/ipfs-exec')
@@ -49,6 +51,12 @@ describe('init', function () {
expect(out2).to.equal(readme)
})
+ it('algorithm', async function () {
+ await ipfs('init --algorithm ed25519')
+ const peerId = await PeerId.createFromPrivKey(repoConfSync().Identity.PrivKey)
+ expect(peerId.privKey).is.instanceOf(supportedKeys.ed25519.Ed25519PrivateKey)
+ })
+
it('bits', async function () {
await ipfs('init --bits 1024')
expect(repoDirSync('blocks')).to.have.length.above(2)
diff --git a/packages/ipfs/test/core/create-node.spec.js b/packages/ipfs/test/core/create-node.spec.js
index e9db246332..4e66babfd4 100644
--- a/packages/ipfs/test/core/create-node.spec.js
+++ b/packages/ipfs/test/core/create-node.spec.js
@@ -6,10 +6,13 @@ const { expect } = require('interface-ipfs-core/src/utils/mocha')
const sinon = require('sinon')
const { isNode } = require('ipfs-utils/src/env')
const tmpDir = require('ipfs-utils/src/temp-dir')
+const PeerId = require('peer-id')
+const { supportedKeys } = require('libp2p-crypto/src/keys')
const IPFS = require('../../src/core')
// This gets replaced by `create-repo-browser.js` in the browser
const createTempRepo = require('../utils/create-repo-nodejs.js')
+const { console } = require('ipfs-utils/src/globalthis')
describe('create node', function () {
let tempRepo
@@ -58,6 +61,21 @@ describe('create node', function () {
await node.stop()
})
+ it('should create and initialize with algorithm', async () => {
+ const ipfs = await IPFS.create({
+ init: { algorithm: 'ed25519' },
+ start: false,
+ repo: tempRepo,
+ config: { Addresses: { Swarm: [] } }
+ })
+
+ const id = await ipfs.id()
+ const config = await ipfs.config.getAll()
+ const peerId = await PeerId.createFromPrivKey(config.Identity.PrivKey)
+ expect(peerId.privKey).is.instanceOf(supportedKeys.ed25519.Ed25519PrivateKey)
+ expect(id.id).to.equal(peerId.toB58String())
+ })
+
it('should create and initialize but not start', async () => {
const ipfs = await IPFS.create({
init: { bits: 512 },
diff --git a/packages/ipfs/test/core/init.spec.js b/packages/ipfs/test/core/init.spec.js
index 222e4f0067..782b7dd977 100644
--- a/packages/ipfs/test/core/init.spec.js
+++ b/packages/ipfs/test/core/init.spec.js
@@ -6,9 +6,13 @@ const { expect } = require('interface-ipfs-core/src/utils/mocha')
const { isNode } = require('ipfs-utils/src/env')
const { Buffer } = require('buffer')
const { nanoid } = require('nanoid')
+const PeerId = require('peer-id')
+const { supportedKeys } = require('libp2p-crypto/src/keys')
const IPFS = require('../../src/core')
const privateKey = 'CAASqAkwggSkAgEAAoIBAQChVmiObYo6pkKrMSd3OzW1cTL+RDmX1rkETYGKWV9TPXMNgElFTYoYHqT9QZomj5RI8iUmHccjzqr4J0mV+E0NpvHHOLlmDZ82lAw2Zx7saUkeQWvC0S9Z0o3aTx2sSubZV53rSomkZgQH4fYTs4RERejV4ltzLFdzQQBwWrBvlagpPHUCxKDUCnE5oIzdbD26ltWViPBWr7TfotzC8Lyi/tceqCpHMUJGMbsVgypnlgpey07MBvs71dVh5LcRen/ztsQO6Yju4D3QgWoyD0SIUdJFvBzEwL9bSiA3QjUc/fkGd7EcdN5bebYOqAi4ZIiAMLp3i4+B8Tzq/acull43AgMBAAECggEBAIDgZE75o4SsEO9tKWht7L5OeXxxBUyMImkUfJkGQUZd/MzZIC5y/Q+9UvBW+gs5gCsw+onTGaM50Iq/32Ej4nE4XURVxIuH8BmJ86N1hlc010qK2cjajqeCsPulXT+m6XbOLYCpnv+q2idt0cL1EH/1FEPeOEztK8ION4qIdw36SoykfTx/RqtkKHtS01AwN82EOPbWk7huyQT5R5MsCZmRJXBFkpNtiL+8619BH2aVlghHO4NouF9wQjdz/ysVuyYg+3rX2cpGjuHDTZ6hVQiJD1lF6D+dua7UPyHYAG2iRQiKZmCjitt9ywzPxiRaYF/aZ02FEMWckZulR09axskCgYEAzjl6ER8WwxYHn4tHse+CrIIF2z5cscdrh7KSwd3Rse9hIIBDJ/0KkvoYd1IcWrS8ywLrRfSLIjEU9u7IN1m+IRVWJ61fXNqOHm9clAu6qNhCN6W2+JfxDkUygTwmsq0v3huO+qkiMQz+a4nAXJe8Utd36ywgPhVGxFa/7x1v1N0CgYEAyEdiYRFf1aQZcO7+B2FH+tkGJsB30VIBhcpG9EukuQUUulLHhScc/KRj+EFAACLdkTqlVI0xVYIWaaCXwoQCWKixjZ5mYPC+bBLgn4IoDS6XTdHtR7Vn3UUvGTKsM0/z4e8/0eSzGNCHoYez9IoBlPNic0sQuST4jzgS2RYnFCMCgYASWSzSLyjwTJp7CIJlg4Dl5l+tBRxsOOkJVssV8q2AnmLO6HqRKUNylkvs+eJJ88DEc0sJm1txvFo4KkCoJBT1jpduyk8szMlOTew3w99kvHEP0G+6KJKrCV8X/okW5q/WnC8ZgEjpglV0rfnugxWfbUpfIzrvKydzuqAzHzRfBQKBgQDANtKSeoxRjEbmfljLWHAure8bbgkQmfXgI7xpZdfXwqqcECpw/pLxXgycDHOSLeQcJ/7Y4RGCEXHVOk2sX+mokW6mjmmPjD4VlyCBtfcef6KzC1EBS3c9g9KqCln+fTOBmY7UsPu6SxiAzK7HeVP/Un8gS+Dm8DalrZlZQ8uJpQKBgF6mL/Xo/XUOiz2jAD18l8Y6s49bA9H2CoLpBGTV1LfY5yTFxRy4R3qnX/IzsKy567sbtkEFKJxplc/RzCQfrgbdj7k26SbKtHR3yERaFGRYq8UeAHeYC1/N19LF5BMQL4y5R4PJ1SFPeJCL/wXiMqs1maTqvKqtc4bbegNdwlxn'
+const edPrivateKey = 'CAESYFeZamw+9QdwHgSmcvPmfLUpmWTtYpUeycbXcfnkTnDI7OaPmE6V8i+Lw7FNB5CtYuDFKUsOS5h+AogyF/Dft4Ds5o+YTpXyL4vDsU0HkK1i4MUpSw5LmH4CiDIX8N+3gA=='
+const secpPrivateKey = 'CAISIKCfwZsMEwmzLxGv9duM6j6YQzMx2V46+Yl3laV24Qus'
// This gets replaced by `create-repo-browser.js` in the browser
const createTempRepo = require('../utils/create-repo-nodejs.js')
@@ -33,7 +37,7 @@ describe('init', function () {
afterEach(() => repo.teardown())
it('should init successfully', async () => {
- await ipfs.init({ bits: 512, pass: nanoid() })
+ await ipfs.init({ bits: 512 })
const res = await repo.exists()
expect(res).to.equal(true)
@@ -44,10 +48,40 @@ describe('init', function () {
expect(config.Keychain).to.exist()
})
+ it('should init successfully with a keychain pass', async () => {
+ await ipfs.init({ bits: 512, pass: nanoid() })
+
+ const res = await repo.exists()
+ expect(res).to.equal(true)
+
+ const config = await repo.config.getAll()
+
+ expect(config.Keychain).to.exist()
+
+ const peerId = await PeerId.createFromPrivKey(config.Identity.PrivKey)
+ expect(peerId.privKey).is.instanceOf(supportedKeys.rsa.RsaPrivateKey)
+ })
+
+ it('should init with a key algorithm (ed25519)', async () => {
+ await ipfs.init({ algorithm: 'ed25519' })
+
+ const config = await repo.config.getAll()
+ const peerId = await PeerId.createFromPrivKey(config.Identity.PrivKey)
+ expect(peerId.privKey).is.instanceOf(supportedKeys.ed25519.Ed25519PrivateKey)
+ })
+
+ it('should init with a key algorithm (secp256k1)', async () => {
+ await ipfs.init({ algorithm: 'secp256k1' })
+
+ const config = await repo.config.getAll()
+ const peerId = await PeerId.createFromPrivKey(config.Identity.PrivKey)
+ expect(peerId.privKey).is.instanceOf(supportedKeys.secp256k1.Secp256k1PrivateKey)
+ })
+
it('should set # of bits in key', async function () {
this.timeout(40 * 1000)
- await ipfs.init({ bits: 1024, pass: nanoid() })
+ await ipfs.init({ bits: 1024 })
const config = await repo.config.getAll()
expect(config.Identity.PrivKey.length).is.above(256)
@@ -60,8 +94,22 @@ describe('init', function () {
expect(config.Identity.PeerID).is.equal('QmRsooYQasV5f5r834NSpdUtmejdQcpxXkK6qsozZWEihC')
})
+ it('should allow a pregenerated ed25519 key to be used', async () => {
+ await ipfs.init({ privateKey: edPrivateKey })
+
+ const config = await repo.config.getAll()
+ expect(config.Identity.PeerID).is.equal('12D3KooWRm8J3iL796zPFi2EtGGtUJn58AG67gcqzMFHZnnsTzqD')
+ })
+
+ it('should allow a pregenerated secp256k1 key to be used', async () => {
+ await ipfs.init({ privateKey: secpPrivateKey })
+
+ const config = await repo.config.getAll()
+ expect(config.Identity.PeerID).is.equal('16Uiu2HAm5qw8UyXP2RLxQUx5KvtSN8DsTKz8quRGqGNC3SYiaB8E')
+ })
+
it('should write init docs', async () => {
- await ipfs.init({ bits: 512, pass: nanoid() })
+ await ipfs.init({ bits: 512 })
const multihash = 'QmPZ9gcCEpqKTo6aq61g2nXGUhM4iCL3ewB6LDXZCtioEB'
const node = await ipfs.object.get(multihash, { enc: 'base58' })
diff --git a/packages/ipfs/test/core/key-exchange.spec.js b/packages/ipfs/test/core/key-exchange.spec.js
index 16a54704cb..b8d7642b63 100644
--- a/packages/ipfs/test/core/key-exchange.spec.js
+++ b/packages/ipfs/test/core/key-exchange.spec.js
@@ -14,11 +14,7 @@ describe('key exchange', function () {
const passwordPem = nanoid()
before(async () => {
- ipfs = (await df.spawn({
- ipfsOptions: {
- pass: nanoid()
- }
- })).api
+ ipfs = (await df.spawn()).api
})
after(() => df.clean())
@@ -35,4 +31,30 @@ describe('key exchange', function () {
expect(key).to.have.property('name', 'clone')
expect(key).to.have.property('id')
})
+
+ it('should create ed25519 keys', async () => {
+ const name = 'my-ed-key'
+ const pass = 'password for my ed key'
+ const key = await ipfs.key.gen(name, { type: 'ed25519' })
+ // export it
+ const exportedKey = await ipfs.key.export(name, pass)
+ // delete it
+ await ipfs.key.rm(name)
+ // import it back to the same name
+ const imported = await ipfs.key.import(name, exportedKey, pass)
+ expect(imported.id).to.equal(key.id)
+ })
+
+ it('should create secp256k1 keys', async () => {
+ const name = 'my-secp-key'
+ const pass = 'password for my secp key'
+ const key = await ipfs.key.gen(name, { type: 'secp256k1' })
+ // export it
+ const exportedKey = await ipfs.key.export(name, pass)
+ // delete it
+ await ipfs.key.rm(name)
+ // import it back to the same name
+ const imported = await ipfs.key.import(name, exportedKey, pass)
+ expect(imported.id).to.equal(key.id)
+ })
})
diff --git a/packages/ipfs/test/http-api/inject/key.js b/packages/ipfs/test/http-api/inject/key.js
index 96cc59cd2b..7ae199b2e4 100644
--- a/packages/ipfs/test/http-api/inject/key.js
+++ b/packages/ipfs/test/http-api/inject/key.js
@@ -18,7 +18,6 @@ describe('/key', function () {
rm: sinon.stub(),
rename: sinon.stub(),
gen: sinon.stub(),
- export: sinon.stub(),
import: sinon.stub()
}
}
@@ -228,50 +227,6 @@ describe('/key', function () {
})
})
- describe('/export', () => {
- const defaultOptions = {
- signal: sinon.match.instanceOf(AbortSignal),
- timeout: undefined
- }
-
- it('only accepts POST', () => {
- return testHttpMethod('/api/v0/key/export')
- })
-
- it('should export a key', async () => {
- const name = 'name'
- const password = 'password'
-
- ipfs.key.export.withArgs(name, password, defaultOptions).returns('pem')
-
- const res = await http({
- method: 'POST',
- url: `/api/v0/key/export?arg=${name}&password=${password}`
- }, { ipfs })
-
- expect(res).to.have.property('statusCode', 200)
- expect(res).to.have.property('result', 'pem')
- })
-
- it('accepts a timeout', async () => {
- const name = 'name'
- const password = 'password'
-
- ipfs.key.export.withArgs(name, password, {
- ...defaultOptions,
- timeout: 1000
- }).returns('pem')
-
- const res = await http({
- method: 'POST',
- url: `/api/v0/key/export?arg=${name}&password=${password}&timeout=1s`
- }, { ipfs })
-
- expect(res).to.have.property('statusCode', 200)
- expect(res).to.have.property('result', 'pem')
- })
- })
-
describe('/import', () => {
const defaultOptions = {
signal: sinon.match.instanceOf(AbortSignal),