Merge pull request #29 from orbitdb/test/various

Test/various
This commit is contained in:
Haad 2023-03-07 15:53:46 +02:00 committed by GitHub
commit 4f640641e3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 343 additions and 273 deletions

View File

@ -74,8 +74,17 @@ const verifyMessage = async (signature, publicKey, data) => {
return res
}
const defaultPath = './keystore'
/**
* Creates an instance of KeyStore.
* @param {Object} options Various options to use when instantiating KeyStore.
* @param {Object} options.storage An instance of a storage class. Can be one of ComposedStorage, IPFSBlockStorage, LevelStorage, etc. Defaults to ComposedStorage.
* @param {string} options.path The path to a valid storage. Defaults to ./keystore.
* @return {KeyStore} An instance of KeyStore.
*/
const KeyStore = async ({ storage, path } = {}) => {
storage = storage || await ComposedStorage(await LevelStorage({ path: path || './keystore' }), await LRUStorage({ size: 1000 }))
storage = storage || await ComposedStorage(await LRUStorage({ size: 1000 }), await LevelStorage({ path: path || defaultPath }))
const close = async () => {
await storage.close()
@ -103,12 +112,8 @@ const KeyStore = async ({ storage, path } = {}) => {
}
const addKey = async (id, key) => {
try {
await storage.put('public_' + id, key.publicKey)
await storage.put('private_' + id, key.privateKey)
} catch (e) {
console.log(e)
}
await storage.put('public_' + id, key.publicKey)
await storage.put('private_' + id, key.privateKey)
}
const createKey = async (id, { entropy } = {}) => {

View File

@ -1,176 +0,0 @@
// import assert from 'assert'
// import mapSeries from 'p-each-series'
// import rmrf from 'rimraf'
// import OrbitDB from '../src/OrbitDB.js'
// // Include test utilities
// import {
// config,
// startIpfs,
// stopIpfs,
// testAPIs,
// connectPeers,
// waitForPeers
// } from 'orbit-db-test-utils'
// const orbitdbPath1 = './orbitdb/tests/counters/1'
// const orbitdbPath2 = './orbitdb/tests/counters/2'
// const dbPath1 = './orbitdb/tests/counters/db1'
// const dbPath2 = './orbitdb/tests/counters/db2'
// Object.keys(testAPIs).forEach(API => {
// describe(`orbit-db - Counters (${API})`, function () {
// this.timeout(config.timeout)
// let orbitdb1, orbitdb2
// let ipfsd1, ipfsd2, ipfs1, ipfs2
// before(async () => {
// rmrf.sync(dbPath1)
// rmrf.sync(dbPath2)
// rmrf.sync(orbitdbPath1)
// rmrf.sync(orbitdbPath2)
// ipfsd1 = await startIpfs(API, config.daemon1)
// ipfsd2 = await startIpfs(API, config.daemon2)
// ipfs1 = ipfsd1.api
// ipfs2 = ipfsd2.api
// // Connect the peers manually to speed up test times
// const isLocalhostAddress = (addr) => addr.toString().includes('127.0.0.1')
// await connectPeers(ipfs1, ipfs2, { filter: isLocalhostAddress })
// })
// after(async () => {
// if (orbitdb1)
// await orbitdb1.stop()
// if (orbitdb2)
// await orbitdb2.stop()
// if (ipfsd1)
// await stopIpfs(ipfsd1)
// if (ipfsd2)
// await stopIpfs(ipfsd2)
// })
// beforeEach(async () => {
// orbitdb1 = await OrbitDB.createInstance(ipfs1, { directory: './orbitdb/1' })
// orbitdb2 = await OrbitDB.createInstance(ipfs2, { directory: './orbitdb/2' })
// })
// afterEach(async () => {
// if (orbitdb1)
// await orbitdb1.stop()
// if (orbitdb2)
// await orbitdb2.stop()
// })
// describe('counters', function() {
// let address
// it('creates and opens a database', async () => {
// const db = await orbitdb1.counter('counter database')
// assert.notEqual(db, null)
// assert.equal(db.type, 'counter')
// assert.equal(db.dbname, 'counter database')
// })
// it('value is zero when it\'s a fresh database', async () => {
// const db = await orbitdb1.counter('counter database')
// assert.equal(db.value, 0)
// await db.close()
// })
// it('increases a counter value', async () => {
// const counter = await orbitdb1.counter('counter test', { path: dbPath1 })
// address = counter.address.toString()
// await mapSeries([13, 1], (f) => counter.inc(f))
// assert.equal(counter.value, 14)
// await counter.close()
// })
// it('opens a saved counter', async () => {
// const counter = await orbitdb1.counter(address, { path: dbPath1 })
// await counter.load()
// assert.equal(counter.value, 14)
// await counter.drop()
// })
// it('syncs counters', async () => {
// console.log("Sync counters")
// let options = {
// accessController: {
// // Set write access for both clients
// write: [
// orbitdb1.identity.id,
// orbitdb2.identity.id
// ]
// }
// }
// const dbName = new Date().getTime().toString()
// const numbers = [[13, 10], [2, 5]]
// const increaseCounter = (counterDB, i) => mapSeries(numbers[i], n => counterDB.inc(n))
// // Create a new counter database in the first client
// options = Object.assign({}, options, { path: dbPath1 })
// const counter1 = await orbitdb1.counter(dbName, options)
// // Open the database in the second client
// options = Object.assign({}, options, { path: dbPath2 })
// const counter2 = await orbitdb2.counter(dbName, options)
// // Make sure database addresses match since they're built deterministically
// assert.equal(counter1.address.toString(), counter2.address.toString())
// // Wait for peers to connect
// console.log("Waiting for peers to connect")
// await waitForPeers(ipfs1, [orbitdb2.id], counter1.address.toString())
// await waitForPeers(ipfs2, [orbitdb1.id], counter1.address.toString())
// let finished1 = counter1.value === 30
// let finished2 = counter2.value === 30
// counter1.events.on('replicated', () => {
// finished1 = (counter1.value === 30)
// finished2 = (counter2.value === 30)
// })
// counter2.events.on('replicated', () => {
// finished1 = (counter1.value === 30)
// finished2 = (counter2.value === 30)
// })
// counter1.events.on('write', () => {
// finished1 = (counter1.value === 30)
// finished2 = (counter2.value === 30)
// })
// counter2.events.on('write', () => {
// finished1 = (counter1.value === 30)
// finished2 = (counter2.value === 30)
// })
// // Increase the counters sequentially
// await mapSeries([counter1, counter2], increaseCounter)
// console.log("Waiting for replication to finish")
// return new Promise((resolve, reject) => {
// let timer = setInterval(async () => {
// if (finished1 && finished2) {
// try {
// clearInterval(timer)
// assert.equal(counter1.value, 30)
// assert.equal(counter2.value, 30)
// await counter1.close()
// await counter2.close()
// resolve()
// } catch (e) {
// reject(e)
// }
// }
// }, 100)
// })
// })
// })
// })
// })

View File

@ -1,78 +0,0 @@
// import assert from 'assert'
// import rmrf from 'rimraf'
// import path from 'path'
// import OrbitDB from '../src/OrbitDB.js'
// import Identities from 'orbit-db-identity-provider'
// // Include test utilities
// import {
// config,
// startIpfs,
// stopIpfs,
// testAPIs,
// } from 'orbit-db-test-utils'
// import {
// CustomTestKeystore,
// databases,
// } from './utils/index.js'
// Identities.addIdentityProvider(CustomTestKeystore().identityProvider)
// const dbPath = './orbitdb/tests/customKeystore'
// Object.keys(testAPIs).forEach(API => {
// describe(`orbit-db - Use a Custom Keystore (${API})`, function() {
// this.timeout(20000)
// let ipfsd, ipfs, orbitdb1
// before(async () => {
// rmrf.sync(dbPath)
// ipfsd = await startIpfs(API, config.daemon1)
// ipfs = ipfsd.api
// const identity = await Identities.createIdentity({ type: 'custom', keystore: CustomTestKeystore().create() })
// orbitdb1 = await OrbitDB.createInstance(ipfs, {
// directory: path.join(dbPath, '1'),
// identity
// })
// })
// after(async () => {
// await orbitdb1.stop()
// await stopIpfs(ipfsd)
// })
// describe('allows orbit to use a custom keystore with different store types', function() {
// databases.forEach(async (database) => {
// it(database.type + ' allows custom keystore', async () => {
// const db1 = await database.create(orbitdb1, 'custom-keystore')
// await database.tryInsert(db1)
// assert.deepEqual(database.getTestValue(db1), database.expectedValue)
// await db1.close()
// })
// })
// })
// describe('allows a custom keystore to be used with different store and write permissions', function() {
// databases.forEach(async (database) => {
// it(database.type + ' allows custom keystore', async () => {
// const options = {
// accessController: {
// // Set write access for both clients
// write: [orbitdb1.identity.id]
// }
// }
// const db1 = await database.create(orbitdb1, 'custom-keystore', options)
// await database.tryInsert(db1)
// assert.deepEqual(database.getTestValue(db1), database.expectedValue)
// await db1.close()
// })
// })
// })
// })
// })

View File

@ -0,0 +1,217 @@
import { deepStrictEqual } from 'assert'
import rmrf from 'rimraf'
import { copy } from 'fs-extra'
import * as IPFS from 'ipfs'
import { Log, Entry, Database, KeyStore, Identities } from '../../../src/index.js'
import { KeyValue, KeyValuePersisted } from '../../../src/db/index.js'
import config from '../../config.js'
import testKeysPath from '../../fixtures/test-keys-path.js '
import connectPeers from '../../utils/connect-nodes.js'
import waitFor from '../../utils/wait-for.js'
const OpLog = { Log, Entry }
const keysPath = './testkeys'
describe('KeyValue Database Replication', function () {
this.timeout(30000)
let ipfs1, ipfs2
let keystore
let identities
let testIdentity1, testIdentity2
let kv1, kv2
const databaseId = 'kv-AAA'
const accessController = {
canAppend: async (entry) => {
const identity = await identities.getIdentity(entry.identity)
return identity.id === testIdentity1.id
}
}
before(async () => {
ipfs1 = await IPFS.create({ ...config.daemon1, repo: './ipfs1' })
ipfs2 = await IPFS.create({ ...config.daemon2, repo: './ipfs2' })
await connectPeers(ipfs1, ipfs2)
await copy(testKeysPath, keysPath)
keystore = await KeyStore({ path: keysPath })
identities = await Identities({ keystore })
testIdentity1 = await identities.createIdentity({ id: 'userA' })
testIdentity2 = await identities.createIdentity({ id: 'userB' })
})
after(async () => {
if (ipfs1) {
await ipfs1.stop()
}
if (ipfs2) {
await ipfs2.stop()
}
if (keystore) {
await keystore.close()
}
await rmrf(keysPath)
await rmrf('./orbitdb1')
await rmrf('./orbitdb2')
await rmrf('./ipfs1')
await rmrf('./ipfs2')
})
afterEach(async () => {
if (kv1) {
await kv1.drop()
await kv1.close()
}
if (kv2) {
await kv2.drop()
await kv2.close()
}
})
it('replicates a database', async () => {
let connected = false
let updateCount = 0
const onConnected = async (peerId) => {
connected = true
}
const onUpdate = (entry) => {
++updateCount
}
const onError = (err) => {
console.error(err)
}
kv1 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
kv2.events.on('join', onConnected)
kv1.events.on('join', onConnected)
kv2.events.on('update', onUpdate)
kv2.events.on('error', onError)
kv1.events.on('error', onError)
await kv1.set('init', true)
await kv1.set('hello', 'friend')
await kv1.del('hello')
await kv1.set('hello', 'friend2')
await kv1.del('hello')
await kv1.set('empty', '')
await kv1.del('empty')
await kv1.set('hello', 'friend3')
await waitFor(() => connected, () => true)
await waitFor(() => updateCount > 0, () => true)
const value0 = await kv2.get('init')
deepStrictEqual(value0, true)
const value2 = await kv2.get('hello')
deepStrictEqual(value2, 'friend3')
const value1 = await kv1.get('hello')
deepStrictEqual(value1, 'friend3')
const value9 = await kv1.get('empty')
deepStrictEqual(value9, undefined)
const all2 = []
for await (const keyValue of kv2.iterator()) {
all2.push(keyValue)
}
deepStrictEqual(all2, [
{ key: 'hello', value: 'friend3' },
{ key: 'init', value: true }
])
const all1 = []
for await (const keyValue of kv1.iterator()) {
all1.push(keyValue)
}
deepStrictEqual(all1, [
{ key: 'hello', value: 'friend3' },
{ key: 'init', value: true }
])
})
it('loads the database after replication', async () => {
let updateCount = 0
let connected = false
const onConnected = async (peerId) => {
connected = true
}
const onUpdate = (entry) => {
++updateCount
}
const onError = (err) => {
console.error(err)
}
kv1 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
kv2.events.on('join', onConnected)
kv1.events.on('join', onConnected)
kv2.events.on('update', onUpdate)
kv2.events.on('error', onError)
kv1.events.on('error', onError)
await kv1.set('init', true)
await kv1.set('hello', 'friend')
await kv1.del('hello')
await kv1.set('hello', 'friend2')
await kv1.del('hello')
await kv1.set('empty', '')
await kv1.del('empty')
await kv1.set('hello', 'friend3')
await waitFor(() => connected, () => true)
await waitFor(() => updateCount > 0, () => true)
await kv1.close()
await kv2.close()
kv1 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
const value0 = await kv2.get('init')
deepStrictEqual(value0, true)
const value2 = await kv2.get('hello')
deepStrictEqual(value2, 'friend3')
const value1 = await kv1.get('hello')
deepStrictEqual(value1, 'friend3')
const value9 = await kv1.get('empty')
deepStrictEqual(value9, undefined)
const all2 = []
for await (const keyValue of kv2.iterator()) {
all2.push(keyValue)
}
deepStrictEqual(all2, [
{ key: 'hello', value: 'friend3' },
{ key: 'init', value: true }
])
const all1 = []
for await (const keyValue of kv1.iterator()) {
all1.push(keyValue)
}
deepStrictEqual(all1, [
{ key: 'hello', value: 'friend3' },
{ key: 'init', value: true }
])
})
})

View File

@ -3,7 +3,7 @@ import rmrf from 'rimraf'
import { copy } from 'fs-extra'
import * as IPFS from 'ipfs'
import { Log, Entry, Database, KeyStore, Identities } from '../../../src/index.js'
import { KeyValue, KeyValuePersisted } from '../../../src/db/index.js'
import { KeyValue } from '../../../src/db/index.js'
import config from '../../config.js'
import testKeysPath from '../../fixtures/test-keys-path.js '
import connectPeers from '../../utils/connect-nodes.js'
@ -89,8 +89,8 @@ describe('KeyValue Database Replication', function () {
console.error(err)
}
kv1 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
kv1 = await KeyValue({ OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValue({ OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
kv2.events.on('join', onConnected)
kv1.events.on('join', onConnected)
@ -157,8 +157,8 @@ describe('KeyValue Database Replication', function () {
console.error(err)
}
kv1 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
kv1 = await KeyValue({ OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValue({ OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
kv2.events.on('join', onConnected)
kv1.events.on('join', onConnected)
@ -181,8 +181,8 @@ describe('KeyValue Database Replication', function () {
await kv1.close()
await kv2.close()
kv1 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValuePersisted({ KeyValue, OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
kv1 = await KeyValue({ OpLog, Database, ipfs: ipfs1, identity: testIdentity1, address: databaseId, accessController, directory: './orbitdb1' })
kv2 = await KeyValue({ OpLog, Database, ipfs: ipfs2, identity: testIdentity2, address: databaseId, accessController, directory: './orbitdb2' })
const value0 = await kv2.get('init')
deepStrictEqual(value0, true)

View File

@ -1,30 +1,36 @@
import { strictEqual, deepStrictEqual } from 'assert'
import * as crypto from '@libp2p/crypto'
import { Buffer } from 'safe-buffer'
import rmrf from 'rimraf'
import { copy } from 'fs-extra'
import KeyStore, { signMessage, verifyMessage } from '../src/key-store.js'
import LevelStorage from '../src/storage/level.js'
import testKeysPath from './fixtures/test-keys-path.js '
const defaultPath = './keystore'
const keysPath = './testkeys'
describe('KeyStore', () => {
let keystore
describe('Creating and retrieving keys', () => {
let id
beforeEach(async () => {
await copy(testKeysPath, keysPath)
keystore = await KeyStore({ path: keysPath })
keystore = await KeyStore()
id = 'key1'
await keystore.createKey(id)
})
afterEach(async () => {
if (keystore) {
await keystore.close()
await rmrf(defaultPath)
}
await rmrf(keysPath)
})
it('creates a key', async () => {
const id = 'key1'
await keystore.createKey(id)
const hasKey = await keystore.hasKey(id)
strictEqual(hasKey, true)
})
@ -80,6 +86,7 @@ describe('KeyStore', () => {
it('gets a key', async () => {
const id = 'key1'
const keys = await keystore.createKey(id)
deepStrictEqual(await keystore.getKey(id), keys)
})
@ -121,6 +128,101 @@ describe('KeyStore', () => {
strictEqual(actual, expected)
})
it('doesn\'t create a key when keystore is closed', async () => {
let err
await keystore.close()
try {
await keystore.createKey(id)
} catch (e) {
err = e.toString()
}
strictEqual(err, 'Error: Database is not open')
})
})
describe('Options', () => {
const unmarshal = crypto.keys.supportedKeys.secp256k1.unmarshalSecp256k1PrivateKey
const privateKey = '198594a8de39fd97017d11996d619b3746211605a9d290964badf58bc79bdb33'
const publicKey = '0260baeaffa1de1e4135e5b395e0380563a622b9599d1b8e012a0f7603f516bdaa'
let privateKeyBuffer, publicKeyBuffer, unmarshalledPrivateKey
before(async () => {
privateKeyBuffer = Buffer.from(privateKey, 'hex')
publicKeyBuffer = Buffer.from(publicKey, 'hex')
unmarshalledPrivateKey = await unmarshal(privateKeyBuffer)
})
describe('Using default options', () => {
beforeEach(async () => {
const storage = await LevelStorage({ path: defaultPath })
await storage.put('private_key1', privateKeyBuffer)
await storage.put('public_key1', publicKeyBuffer)
await storage.close()
keystore = await KeyStore()
})
afterEach(async () => {
if (keystore) {
await keystore.close()
await rmrf(defaultPath)
}
})
it('uses default storage and default path to retrieve a key', async () => {
deepStrictEqual(await keystore.getKey('key1'), unmarshalledPrivateKey)
})
})
describe('Setting options.storage', () => {
const path = './custom-level-key-store'
beforeEach(async () => {
const storage = await LevelStorage({ path })
await storage.put('private_key2', privateKeyBuffer)
await storage.put('public_key2', publicKeyBuffer)
keystore = await KeyStore({ storage })
})
afterEach(async () => {
if (keystore) {
await keystore.close()
await rmrf(path)
}
})
it('uses the given storage to retrieve a key', async () => {
deepStrictEqual(await keystore.getKey('key2'), unmarshalledPrivateKey)
})
})
describe('Setting options.path', () => {
beforeEach(async () => {
await copy(testKeysPath, keysPath)
const storage = await LevelStorage({ path: keysPath })
await storage.put('private_key3', privateKeyBuffer)
await storage.put('public_key3', publicKeyBuffer)
await storage.close()
keystore = await KeyStore({ path: keysPath })
})
afterEach(async () => {
if (keystore) {
await keystore.close()
}
await rmrf(keysPath)
})
it('uses default storage using given path to retrieve a key', async () => {
deepStrictEqual(await keystore.getKey('key3'), unmarshalledPrivateKey)
})
})
})
describe('Using keys for signing and verifying', () => {