Merge branch 'master' into determine-address
This commit is contained in:
commit
15aae2959b
2
API.md
2
API.md
@ -76,6 +76,8 @@ Creates and returns an instance of OrbitDB. Use the optional `directory` argumen
|
||||
|
||||
- `keystore` (Keystore Instance) : By default creates an instance of [Keystore](https://github.com/orbitdb/orbit-db-keystore). A custom keystore instance can be used, see [this](https://github.com/orbitdb/orbit-db/blob/master/test/utils/custom-test-keystore.js) for an example.
|
||||
|
||||
- 'cache' (Cache Instance) : By default creates an instance of [Cache](https://github.com/orbitdb/orbit-db-cache). A custom cache instance can also be used.
|
||||
|
||||
After creating an `OrbitDB` instance , you can access the different data stores. Creating a database instance, eg. with `orbitdb.keyvalue(...)`, returns a *Promise* that resolves to a [database instance](#store-api). See the [Store](#store-api) section for details of common methods and properties.
|
||||
|
||||
*For further details, see usage for [kvstore](https://github.com/orbitdb/orbit-db-kvstore#usage), [eventlog](https://github.com/orbitdb/orbit-db-eventstore#usage), [feed](https://github.com/orbitdb/orbit-db-feedstore#usage), [docstore](https://github.com/orbitdb/orbit-db-docstore#usage) and [counter](https://github.com/orbitdb/orbit-db-counterstore#usage).*
|
||||
|
71
CODE_OF_CONDUCT.md
Normal file
71
CODE_OF_CONDUCT.md
Normal file
@ -0,0 +1,71 @@
|
||||
# Contributor Covenant Code of Conduct
|
||||
|
||||
## Our Pledge
|
||||
|
||||
In the interest of fostering an open and welcoming environment, we as
|
||||
contributors and maintainers pledge to making participation in our project and
|
||||
our community a harassment-free experience for everyone, regardless of age, body
|
||||
size, disability, ethnicity, sex characteristics, gender identity and expression,
|
||||
level of experience, education, socio-economic status, nationality, personal
|
||||
appearance, race, religion, or sexual identity and orientation.
|
||||
|
||||
## Our Standards
|
||||
|
||||
Examples of behavior that contributes to creating a positive environment
|
||||
include:
|
||||
|
||||
* Using welcoming and inclusive language
|
||||
* Being respectful of differing viewpoints and experiences
|
||||
* Gracefully accepting constructive criticism
|
||||
* Focusing on what is best for the community
|
||||
* Showing empathy towards other community members
|
||||
|
||||
Examples of unacceptable behavior by participants include:
|
||||
|
||||
* The use of sexualized language or imagery and unwelcome sexual attention or
|
||||
advances
|
||||
* Trolling, insulting/derogatory comments, and personal or political attacks
|
||||
* Public or private harassment
|
||||
* Publishing others' private information, such as a physical or electronic
|
||||
address, without explicit permission
|
||||
* Other conduct which could reasonably be considered inappropriate in a
|
||||
professional setting
|
||||
|
||||
## Our Responsibilities
|
||||
|
||||
Project maintainers are responsible for clarifying the standards of acceptable
|
||||
behavior and are expected to take appropriate and fair corrective action in
|
||||
response to any instances of unacceptable behavior.
|
||||
|
||||
Project maintainers have the right and responsibility to remove, edit, or
|
||||
reject comments, commits, code, wiki edits, issues, and other contributions
|
||||
that are not aligned to this Code of Conduct, or to ban temporarily or
|
||||
permanently any contributor for other behaviors that they deem inappropriate,
|
||||
threatening, offensive, or harmful.
|
||||
|
||||
## Scope
|
||||
|
||||
This Code of Conduct applies both within project spaces and in public spaces
|
||||
when an individual is representing the project or its community. Examples of
|
||||
representing a project or community include using an official project e-mail
|
||||
address, posting via an official social media account, or acting as an appointed
|
||||
representative at an online or offline event. Representation of a project may be
|
||||
further defined and clarified by project maintainers.
|
||||
|
||||
## Enforcement
|
||||
|
||||
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
||||
reported by contacting the project team at [community@orbitdb.org](mailto:community@orbitdb.org), which goes to all members of the @OrbitDB community team, or to [richardlitt@orbitdb.org](mailto:richardlitt@orbitdb.org), which goes only to [@RichardLitt](https://github.com/RichardLitt) or to [haadcode@orbitdb.org](mailto:haadcode@orbitdb.org), which goes only to [@haadcode](https://github.com/haadcode).
|
||||
|
||||
All complaints will be reviewed and investigated and will result in a response that is deemed necessary and appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately.
|
||||
|
||||
Project maintainers who do not follow or enforce the Code of Conduct in good
|
||||
faith may face temporary or permanent repercussions as determined by other
|
||||
members of the project's leadership.
|
||||
|
||||
## Attribution
|
||||
|
||||
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
|
||||
available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html
|
||||
|
||||
[homepage]: https://www.contributor-covenant.org
|
6
Makefile
6
Makefile
@ -20,6 +20,10 @@ build: test
|
||||
clean:
|
||||
rm -rf orbitdb/
|
||||
rm -rf node_modules/
|
||||
rm package-lock.json
|
||||
|
||||
clean-dependencies: clean
|
||||
if [ -a package-lock.json ]; then rm package-lock.json; fi;
|
||||
|
||||
rebuild: | clean-dependencies build
|
||||
|
||||
.PHONY: test build
|
||||
|
@ -27,6 +27,9 @@ All databases are [implemented](https://github.com/orbitdb/orbit-db-store) on to
|
||||
#### Project status & support
|
||||
This is the Javascript implementation and it works both in **Browsers** and **Node.js** with support for Linux and OS X (Windows is not supported yet). The minimum required version of Node.js is now 8.0.0. To use with older versions of Node.js, we provide an ES5-compatible build through the npm package, located in `dist/es5/` when installed through npm.
|
||||
|
||||
#### Community Calls
|
||||
We also have **regular community calls**, which we announce in the issues in [the @orbitdb welcome repository](https://github.com/orbitdb/welcome/issues). Join us!
|
||||
|
||||
## Table of Contents
|
||||
|
||||
<!-- toc -->
|
||||
@ -257,6 +260,8 @@ We also have **regular community calls**, which we announce in the issues in [th
|
||||
|
||||
If you want to code but don't know where to start, check out the issues labelled ["help wanted"](https://github.com/orbitdb/orbit-db/issues?q=is%3Aopen+is%3Aissue+label%3A%22help+wanted%22+sort%3Areactions-%2B1-desc) or the project's [status board](https://waffle.io/orbitdb/orbit-db).
|
||||
|
||||
Please note that we have a [Code of Conduct](CODE_OF_CONDUCT.md), and that all activity in the [@orbitdb](https://github.com/orbitdb) organization falls under it. Read it when you get the chance, as being part of this community means that you agree to abide by it. Thanks.
|
||||
|
||||
## Sponsors
|
||||
|
||||
The development of OrbitDB has been sponsored by:
|
||||
|
68
package-lock.json
generated
68
package-lock.json
generated
@ -272,6 +272,11 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"argsarray": {
|
||||
"version": "0.0.1",
|
||||
"resolved": "https://registry.npmjs.org/argsarray/-/argsarray-0.0.1.tgz",
|
||||
"integrity": "sha1-bnIHtOzbObCviDA/pa4ivajfYcs="
|
||||
},
|
||||
"arr-diff": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz",
|
||||
@ -2270,6 +2275,11 @@
|
||||
"es5-ext": "0.10.45"
|
||||
}
|
||||
},
|
||||
"d64": {
|
||||
"version": "1.0.0",
|
||||
"resolved": "http://registry.npmjs.org/d64/-/d64-1.0.0.tgz",
|
||||
"integrity": "sha1-QAKofoUMv8n52XBrYPymE6MzbpA="
|
||||
},
|
||||
"dashdash": {
|
||||
"version": "1.14.1",
|
||||
"resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz",
|
||||
@ -5236,6 +5246,11 @@
|
||||
"integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
|
||||
"dev": true
|
||||
},
|
||||
"has-localstorage": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/has-localstorage/-/has-localstorage-1.0.1.tgz",
|
||||
"integrity": "sha1-/mJAbEdn+9bXhNrGkFkoEIuClxs="
|
||||
},
|
||||
"has-unicode": {
|
||||
"version": "2.0.1",
|
||||
"resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz",
|
||||
@ -5414,6 +5429,15 @@
|
||||
"promisify-es6": "1.0.3"
|
||||
}
|
||||
},
|
||||
"humble-localstorage": {
|
||||
"version": "1.4.2",
|
||||
"resolved": "http://registry.npmjs.org/humble-localstorage/-/humble-localstorage-1.4.2.tgz",
|
||||
"integrity": "sha1-0Fqw1SbE7b3b98amDfb/WAUoNGk=",
|
||||
"requires": {
|
||||
"has-localstorage": "1.0.1",
|
||||
"localstorage-memory": "1.0.3"
|
||||
}
|
||||
},
|
||||
"idb-readable-stream": {
|
||||
"version": "0.0.4",
|
||||
"resolved": "https://registry.npmjs.org/idb-readable-stream/-/idb-readable-stream-0.0.4.tgz",
|
||||
@ -8809,6 +8833,45 @@
|
||||
"json5": "0.5.1"
|
||||
}
|
||||
},
|
||||
"localstorage-down": {
|
||||
"version": "0.6.7",
|
||||
"resolved": "https://registry.npmjs.org/localstorage-down/-/localstorage-down-0.6.7.tgz",
|
||||
"integrity": "sha1-0Hmak7MebF+lGI7AYkLrHM6dbRU=",
|
||||
"requires": {
|
||||
"abstract-leveldown": "0.12.3",
|
||||
"argsarray": "0.0.1",
|
||||
"buffer-from": "0.1.2",
|
||||
"d64": "1.0.0",
|
||||
"humble-localstorage": "1.4.2",
|
||||
"inherits": "2.0.3",
|
||||
"tiny-queue": "0.2.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"abstract-leveldown": {
|
||||
"version": "0.12.3",
|
||||
"resolved": "http://registry.npmjs.org/abstract-leveldown/-/abstract-leveldown-0.12.3.tgz",
|
||||
"integrity": "sha1-EWsexcdxDvei1XBnaLvbREC+EHA=",
|
||||
"requires": {
|
||||
"xtend": "3.0.0"
|
||||
}
|
||||
},
|
||||
"buffer-from": {
|
||||
"version": "0.1.2",
|
||||
"resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-0.1.2.tgz",
|
||||
"integrity": "sha512-RiWIenusJsmI2KcvqQABB83tLxCByE3upSP8QU3rJDMVFGPWLvPQJt/O1Su9moRWeH7d+Q2HYb68f6+v+tw2vg=="
|
||||
},
|
||||
"xtend": {
|
||||
"version": "3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/xtend/-/xtend-3.0.0.tgz",
|
||||
"integrity": "sha1-XM50B7r2Qsunvs2laBEcST9ZZlo="
|
||||
}
|
||||
}
|
||||
},
|
||||
"localstorage-memory": {
|
||||
"version": "1.0.3",
|
||||
"resolved": "https://registry.npmjs.org/localstorage-memory/-/localstorage-memory-1.0.3.tgz",
|
||||
"integrity": "sha512-t9P8WB6DcVttbw/W4PIE8HOqum8Qlvx5SjR6oInwR9Uia0EEmyUeBh7S+weKByW+l/f45Bj4L/dgZikGFDM6ng=="
|
||||
},
|
||||
"locate-path": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz",
|
||||
@ -12996,6 +13059,11 @@
|
||||
"integrity": "sha1-jru/1tYpXxNwAD+7NxYq/loKUdE=",
|
||||
"dev": true
|
||||
},
|
||||
"tiny-queue": {
|
||||
"version": "0.2.0",
|
||||
"resolved": "https://registry.npmjs.org/tiny-queue/-/tiny-queue-0.2.0.tgz",
|
||||
"integrity": "sha1-xJ/LXIdVW+G0pd9+uHEB1beLydw="
|
||||
},
|
||||
"to-array": {
|
||||
"version": "0.1.4",
|
||||
"resolved": "https://registry.npmjs.org/to-array/-/to-array-0.1.4.tgz",
|
||||
|
@ -15,6 +15,7 @@
|
||||
"dependencies": {
|
||||
"ipfs-pubsub-1on1": "~0.0.4",
|
||||
"ipld-dag-pb": "0.14.11",
|
||||
"localstorage-down": "^0.6.7",
|
||||
"logplease": "^1.2.14",
|
||||
"multihashes": "^0.4.12",
|
||||
"orbit-db-cache": "~0.2.4",
|
||||
|
@ -37,6 +37,7 @@ class OrbitDB {
|
||||
this.stores = {}
|
||||
this.directory = directory || './orbitdb'
|
||||
this.keystore = options.keystore || Keystore.create(path.join(this.directory, this.id, '/keystore'))
|
||||
this.cache = options.cache || Cache
|
||||
this.key = this.keystore.getKey(this.id) || this.keystore.createKey(this.id)
|
||||
this._directConnections = {}
|
||||
}
|
||||
@ -357,7 +358,7 @@ class OrbitDB {
|
||||
async _loadCache (directory, dbAddress) {
|
||||
let cache
|
||||
try {
|
||||
cache = await Cache.load(directory, dbAddress)
|
||||
cache = await this.cache.load(directory, dbAddress)
|
||||
} catch (e) {
|
||||
console.log(e)
|
||||
logger.error("Couldn't load Cache:", e)
|
||||
|
58
test/custom-cache.test.js
Normal file
58
test/custom-cache.test.js
Normal file
@ -0,0 +1,58 @@
|
||||
'use strict'
|
||||
|
||||
const assert = require('assert')
|
||||
const rmrf = require('rimraf')
|
||||
const OrbitDB = require('../src/OrbitDB')
|
||||
const CustomCache = require('orbit-db-cache')
|
||||
// Include test utilities
|
||||
const {
|
||||
config,
|
||||
startIpfs,
|
||||
stopIpfs,
|
||||
testAPIs,
|
||||
CustomTestCache,
|
||||
databases,
|
||||
} = require('./utils')
|
||||
|
||||
const dbPath = './orbitdb/tests/customKeystore'
|
||||
const ipfsPath = './orbitdb/tests/customKeystore/ipfs'
|
||||
|
||||
Object.keys(testAPIs).forEach(API => {
|
||||
describe(`orbit-db - Use a Custom Cache (${API})`, function() {
|
||||
this.timeout(20000)
|
||||
|
||||
let ipfsd, ipfs, orbitdb1
|
||||
|
||||
before(async () => {
|
||||
config.daemon1.repo = ipfsPath
|
||||
rmrf.sync(config.daemon1.repo)
|
||||
rmrf.sync(dbPath)
|
||||
ipfsd = await startIpfs(API, config.daemon1)
|
||||
ipfs = ipfsd.api
|
||||
orbitdb1 = new OrbitDB(ipfs, dbPath + '/1', {
|
||||
cache: CustomTestCache
|
||||
})
|
||||
})
|
||||
|
||||
after(async () => {
|
||||
if(orbitdb1)
|
||||
await orbitdb1.stop()
|
||||
|
||||
if (ipfsd)
|
||||
await stopIpfs(ipfsd)
|
||||
})
|
||||
|
||||
describe('allows orbit to use a custom cache 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()
|
||||
})
|
||||
})
|
||||
})
|
||||
})
|
||||
})
|
@ -10,54 +10,12 @@ const {
|
||||
stopIpfs,
|
||||
testAPIs,
|
||||
CustomTestKeystore,
|
||||
databases,
|
||||
} = require('./utils')
|
||||
|
||||
const dbPath = './orbitdb/tests/customKeystore'
|
||||
const ipfsPath = './orbitdb/tests/customKeystore/ipfs'
|
||||
|
||||
const databases = [
|
||||
{
|
||||
type: 'eventlog',
|
||||
create: (orbitdb, name, options) => orbitdb.eventlog(name, options),
|
||||
tryInsert: (db) => db.add('hello'),
|
||||
query: (db) => db.iterator({ limit: -1 }).collect(),
|
||||
getTestValue: (db) => db.iterator({ limit: -1 }).collect()[0].payload.value,
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'feed',
|
||||
create: (orbitdb, name, options) => orbitdb.feed(name, options),
|
||||
tryInsert: (db) => db.add('hello'),
|
||||
query: (db) => db.iterator({ limit: -1 }).collect(),
|
||||
getTestValue: (db) => db.iterator({ limit: -1 }).collect()[0].payload.value,
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'key-value',
|
||||
create: (orbitdb, name, options) => orbitdb.kvstore(name, options),
|
||||
tryInsert: (db) => db.set('one', 'hello'),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.get('one'),
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'documents',
|
||||
create: (orbitdb, name, options) => orbitdb.docstore(name, options),
|
||||
tryInsert: (db) => db.put({ _id: 'hello world', doc: 'all the things'}),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.get('hello world'),
|
||||
expectedValue: [{ _id: 'hello world', doc: 'all the things'}],
|
||||
},
|
||||
{
|
||||
type: 'counter',
|
||||
create: (orbitdb, name, options) => orbitdb.counter(name, options),
|
||||
tryInsert: (db) => db.inc(8),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.value,
|
||||
expectedValue: 8,
|
||||
},
|
||||
]
|
||||
|
||||
Object.keys(testAPIs).forEach(API => {
|
||||
describe(`orbit-db - Use a Custom Keystore (${API})`, function() {
|
||||
this.timeout(20000)
|
||||
|
@ -11,265 +11,279 @@ const {
|
||||
startIpfs,
|
||||
stopIpfs,
|
||||
testAPIs,
|
||||
CustomTestCache
|
||||
} = require('./utils')
|
||||
|
||||
const dbPath = './orbitdb/tests/persistency'
|
||||
const ipfsPath = './orbitdb/tests/persistency/ipfs'
|
||||
|
||||
const tests = [
|
||||
{
|
||||
title: 'Persistency',
|
||||
orbitDBConfig: {}
|
||||
},
|
||||
{
|
||||
title: 'Persistency with custom cache',
|
||||
orbitDBConfig: { cache: CustomTestCache }
|
||||
}
|
||||
]
|
||||
|
||||
Object.keys(testAPIs).forEach(API => {
|
||||
describe(`orbit-db - Persistency (${API})`, function() {
|
||||
this.timeout(config.timeout)
|
||||
tests.forEach(test => {
|
||||
describe(`orbit-db - ${test.title} (${API})`, function() {
|
||||
this.timeout(config.timeout)
|
||||
|
||||
const entryCount = 65
|
||||
const entryCount = 65
|
||||
|
||||
let ipfsd, ipfs, orbitdb1, db, address
|
||||
let ipfsd, ipfs, orbitdb1, db, address
|
||||
|
||||
before(async () => {
|
||||
config.daemon1.repo = ipfsPath
|
||||
rmrf.sync(config.daemon1.repo)
|
||||
rmrf.sync(dbPath)
|
||||
ipfsd = await startIpfs(API, config.daemon1)
|
||||
ipfs = ipfsd.api
|
||||
orbitdb1 = new OrbitDB(ipfs, dbPath + '/1')
|
||||
})
|
||||
|
||||
after(async () => {
|
||||
if(orbitdb1)
|
||||
await orbitdb1.stop()
|
||||
|
||||
if (ipfsd)
|
||||
await stopIpfs(ipfsd)
|
||||
})
|
||||
|
||||
describe('load', function() {
|
||||
beforeEach(async () => {
|
||||
const dbName = new Date().getTime().toString()
|
||||
const entryArr = []
|
||||
|
||||
for (let i = 0; i < entryCount; i ++)
|
||||
entryArr.push(i)
|
||||
|
||||
db = await orbitdb1.eventlog(dbName)
|
||||
address = db.address.toString()
|
||||
await mapSeries(entryArr, (i) => db.add('hello' + i))
|
||||
await db.close()
|
||||
db = null
|
||||
before(async () => {
|
||||
config.daemon1.repo = ipfsPath
|
||||
rmrf.sync(config.daemon1.repo)
|
||||
rmrf.sync(dbPath)
|
||||
ipfsd = await startIpfs(API, config.daemon1)
|
||||
ipfs = ipfsd.api
|
||||
orbitdb1 = new OrbitDB(ipfs, dbPath + '/1', test.orbitDBConfig)
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
await db.drop()
|
||||
after(async () => {
|
||||
if(orbitdb1)
|
||||
await orbitdb1.stop()
|
||||
|
||||
if (ipfsd)
|
||||
await stopIpfs(ipfsd)
|
||||
})
|
||||
|
||||
it('loads database from local cache', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.load()
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
})
|
||||
describe('load', function() {
|
||||
beforeEach(async () => {
|
||||
const dbName = new Date().getTime().toString()
|
||||
const entryArr = []
|
||||
|
||||
it('loads database partially', async () => {
|
||||
const amount = 33
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.load(amount)
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, amount)
|
||||
assert.equal(items[0].payload.value, 'hello' + (entryCount - amount))
|
||||
assert.equal(items[1].payload.value, 'hello' + (entryCount - amount + 1))
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
})
|
||||
for (let i = 0; i < entryCount; i ++)
|
||||
entryArr.push(i)
|
||||
|
||||
it('load and close several times', async () => {
|
||||
const amount = 8
|
||||
for (let i = 0; i < amount; i ++) {
|
||||
db = await orbitdb1.eventlog(dbName)
|
||||
address = db.address.toString()
|
||||
await mapSeries(entryArr, (i) => db.add('hello' + i))
|
||||
await db.close()
|
||||
db = null
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
await db.drop()
|
||||
})
|
||||
|
||||
it('loads database from local cache', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.load()
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[1].payload.value, 'hello1')
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
await db.close()
|
||||
}
|
||||
})
|
||||
})
|
||||
|
||||
it('closes database while loading', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
db.load() // don't wait for load to finish
|
||||
await db.close()
|
||||
assert.equal(db._cache.store, null)
|
||||
})
|
||||
|
||||
it('load, add one, close - several times', async () => {
|
||||
const amount = 8
|
||||
for (let i = 0; i < amount; i ++) {
|
||||
it('loads database partially', async () => {
|
||||
const amount = 33
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.load()
|
||||
await db.add('hello' + (entryCount + i))
|
||||
await db.load(amount)
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount + i + 1)
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount + i))
|
||||
await db.close()
|
||||
}
|
||||
})
|
||||
assert.equal(items.length, amount)
|
||||
assert.equal(items[0].payload.value, 'hello' + (entryCount - amount))
|
||||
assert.equal(items[1].payload.value, 'hello' + (entryCount - amount + 1))
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
})
|
||||
|
||||
it('loading a database emits \'ready\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve) => {
|
||||
db.events.on('ready', () => {
|
||||
it('load and close several times', async () => {
|
||||
const amount = 8
|
||||
for (let i = 0; i < amount; i ++) {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.load()
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[1].payload.value, 'hello1')
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
resolve()
|
||||
})
|
||||
await db.load()
|
||||
await db.close()
|
||||
}
|
||||
})
|
||||
})
|
||||
|
||||
it('loading a database emits \'load.progress\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve, reject) => {
|
||||
let count = 0
|
||||
db.events.on('load.progress', (address, hash, entry) => {
|
||||
count ++
|
||||
try {
|
||||
assert.equal(address, db.address.toString())
|
||||
|
||||
const { progress, max } = db.replicationStatus
|
||||
assert.equal(max, entryCount)
|
||||
assert.equal(progress, count)
|
||||
|
||||
assert.notEqual(hash, null)
|
||||
assert.notEqual(entry, null)
|
||||
|
||||
if (progress === entryCount && count === entryCount) {
|
||||
setTimeout(() => {
|
||||
resolve()
|
||||
}, 200)
|
||||
}
|
||||
} catch (e) {
|
||||
reject(e)
|
||||
}
|
||||
})
|
||||
// Start loading the database
|
||||
await db.load()
|
||||
})
|
||||
})
|
||||
})
|
||||
|
||||
describe('load from empty snapshot', function() {
|
||||
it('loads database from an empty snapshot', async () => {
|
||||
db = await orbitdb1.eventlog('empty-snapshot')
|
||||
address = db.address.toString()
|
||||
await db.saveSnapshot()
|
||||
await db.close()
|
||||
|
||||
db = await orbitdb1.open(address)
|
||||
await db.loadFromSnapshot()
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, 0)
|
||||
})
|
||||
})
|
||||
|
||||
describe('load from snapshot', function() {
|
||||
beforeEach(async () => {
|
||||
const dbName = new Date().getTime().toString()
|
||||
const entryArr = []
|
||||
|
||||
for (let i = 0; i < entryCount; i ++)
|
||||
entryArr.push(i)
|
||||
|
||||
db = await orbitdb1.eventlog(dbName)
|
||||
address = db.address.toString()
|
||||
await mapSeries(entryArr, (i) => db.add('hello' + i))
|
||||
await db.saveSnapshot()
|
||||
await db.close()
|
||||
db = null
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
await db.drop()
|
||||
})
|
||||
|
||||
it('loads database from snapshot', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.loadFromSnapshot()
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[entryCount - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
})
|
||||
|
||||
it('load, add one and save snapshot several times', async () => {
|
||||
const amount = 4
|
||||
for (let i = 0; i < amount; i ++) {
|
||||
it('closes database while loading', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.loadFromSnapshot()
|
||||
await db.add('hello' + (entryCount + i))
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount + i + 1)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount + i))
|
||||
db.load() // don't wait for load to finish
|
||||
await db.close()
|
||||
assert.equal(db._cache.store, null)
|
||||
})
|
||||
|
||||
it('load, add one, close - several times', async () => {
|
||||
const amount = 8
|
||||
for (let i = 0; i < amount; i ++) {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.load()
|
||||
await db.add('hello' + (entryCount + i))
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount + i + 1)
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount + i))
|
||||
await db.close()
|
||||
}
|
||||
})
|
||||
|
||||
it('loading a database emits \'ready\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve) => {
|
||||
db.events.on('ready', () => {
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
resolve()
|
||||
})
|
||||
await db.load()
|
||||
})
|
||||
})
|
||||
|
||||
it('loading a database emits \'load.progress\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve, reject) => {
|
||||
let count = 0
|
||||
db.events.on('load.progress', (address, hash, entry) => {
|
||||
count ++
|
||||
try {
|
||||
assert.equal(address, db.address.toString())
|
||||
|
||||
const { progress, max } = db.replicationStatus
|
||||
assert.equal(max, entryCount)
|
||||
assert.equal(progress, count)
|
||||
|
||||
assert.notEqual(hash, null)
|
||||
assert.notEqual(entry, null)
|
||||
|
||||
if (progress === entryCount && count === entryCount) {
|
||||
setTimeout(() => {
|
||||
resolve()
|
||||
}, 200)
|
||||
}
|
||||
} catch (e) {
|
||||
reject(e)
|
||||
}
|
||||
})
|
||||
// Start loading the database
|
||||
await db.load()
|
||||
})
|
||||
})
|
||||
})
|
||||
|
||||
describe('load from empty snapshot', function() {
|
||||
it('loads database from an empty snapshot', async () => {
|
||||
db = await orbitdb1.eventlog('empty-snapshot')
|
||||
address = db.address.toString()
|
||||
await db.saveSnapshot()
|
||||
await db.close()
|
||||
}
|
||||
})
|
||||
|
||||
it('throws an error when trying to load a missing snapshot', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.drop()
|
||||
db = null
|
||||
db = await orbitdb1.eventlog(address)
|
||||
|
||||
let err
|
||||
try {
|
||||
await db.loadFromSnapshot()
|
||||
} catch (e) {
|
||||
err = e.toString()
|
||||
}
|
||||
assert.equal(err, `Error: Snapshot for ${address} not found!`)
|
||||
})
|
||||
|
||||
it('loading a database emits \'ready\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve) => {
|
||||
db.events.on('ready', () => {
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[entryCount - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
resolve()
|
||||
})
|
||||
db = await orbitdb1.open(address)
|
||||
await db.loadFromSnapshot()
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, 0)
|
||||
})
|
||||
})
|
||||
|
||||
it('loading a database emits \'load.progress\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve, reject) => {
|
||||
let count = 0
|
||||
db.events.on('load.progress', (address, hash, entry) => {
|
||||
count ++
|
||||
try {
|
||||
assert.equal(address, db.address.toString())
|
||||
describe('load from snapshot', function() {
|
||||
beforeEach(async () => {
|
||||
const dbName = new Date().getTime().toString()
|
||||
const entryArr = []
|
||||
|
||||
const { progress, max } = db.replicationStatus
|
||||
assert.equal(max, entryCount)
|
||||
assert.equal(progress, count)
|
||||
for (let i = 0; i < entryCount; i ++)
|
||||
entryArr.push(i)
|
||||
|
||||
assert.notEqual(hash, null)
|
||||
assert.notEqual(entry, null)
|
||||
if (progress === entryCount && count === entryCount) {
|
||||
resolve()
|
||||
}
|
||||
} catch (e) {
|
||||
reject(e)
|
||||
}
|
||||
})
|
||||
// Start loading the database
|
||||
db = await orbitdb1.eventlog(dbName)
|
||||
address = db.address.toString()
|
||||
await mapSeries(entryArr, (i) => db.add('hello' + i))
|
||||
await db.saveSnapshot()
|
||||
await db.close()
|
||||
db = null
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
await db.drop()
|
||||
})
|
||||
|
||||
it('loads database from snapshot', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.loadFromSnapshot()
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[entryCount - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
})
|
||||
|
||||
it('load, add one and save snapshot several times', async () => {
|
||||
const amount = 4
|
||||
for (let i = 0; i < amount; i ++) {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.loadFromSnapshot()
|
||||
await db.add('hello' + (entryCount + i))
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount + i + 1)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[items.length - 1].payload.value, 'hello' + (entryCount + i))
|
||||
await db.saveSnapshot()
|
||||
await db.close()
|
||||
}
|
||||
})
|
||||
|
||||
it('throws an error when trying to load a missing snapshot', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
await db.drop()
|
||||
db = null
|
||||
db = await orbitdb1.eventlog(address)
|
||||
|
||||
let err
|
||||
try {
|
||||
await db.loadFromSnapshot()
|
||||
} catch (e) {
|
||||
err = e.toString()
|
||||
}
|
||||
assert.equal(err, `Error: Snapshot for ${address} not found!`)
|
||||
})
|
||||
|
||||
it('loading a database emits \'ready\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve) => {
|
||||
db.events.on('ready', () => {
|
||||
const items = db.iterator({ limit: -1 }).collect()
|
||||
assert.equal(items.length, entryCount)
|
||||
assert.equal(items[0].payload.value, 'hello0')
|
||||
assert.equal(items[entryCount - 1].payload.value, 'hello' + (entryCount - 1))
|
||||
resolve()
|
||||
})
|
||||
await db.loadFromSnapshot()
|
||||
})
|
||||
})
|
||||
|
||||
it('loading a database emits \'load.progress\' event', async () => {
|
||||
db = await orbitdb1.eventlog(address)
|
||||
return new Promise(async (resolve, reject) => {
|
||||
let count = 0
|
||||
db.events.on('load.progress', (address, hash, entry) => {
|
||||
count ++
|
||||
try {
|
||||
assert.equal(address, db.address.toString())
|
||||
|
||||
const { progress, max } = db.replicationStatus
|
||||
assert.equal(max, entryCount)
|
||||
assert.equal(progress, count)
|
||||
|
||||
assert.notEqual(hash, null)
|
||||
assert.notEqual(entry, null)
|
||||
if (progress === entryCount && count === entryCount) {
|
||||
resolve()
|
||||
}
|
||||
} catch (e) {
|
||||
reject(e)
|
||||
}
|
||||
})
|
||||
// Start loading the database
|
||||
await db.loadFromSnapshot()
|
||||
})
|
||||
})
|
||||
})
|
||||
})
|
||||
|
9
test/utils/custom-test-cache.js
Normal file
9
test/utils/custom-test-cache.js
Normal file
@ -0,0 +1,9 @@
|
||||
const OrbitDbCache = require('orbit-db-cache/Cache.js')
|
||||
const localdown = require('localstorage-down')
|
||||
|
||||
/**
|
||||
* A custom cache example. To create a differing custom example, orbitdb cache was
|
||||
* used with another abstract-leveldown compliant storage, localdown as an example
|
||||
*/
|
||||
|
||||
module.exports = OrbitDbCache(localdown)
|
44
test/utils/databases.js
Normal file
44
test/utils/databases.js
Normal file
@ -0,0 +1,44 @@
|
||||
const databases = [
|
||||
{
|
||||
type: 'eventlog',
|
||||
create: (orbitdb, name, options) => orbitdb.eventlog(name, options),
|
||||
tryInsert: (db) => db.add('hello'),
|
||||
query: (db) => db.iterator({ limit: -1 }).collect(),
|
||||
getTestValue: (db) => db.iterator({ limit: -1 }).collect()[0].payload.value,
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'feed',
|
||||
create: (orbitdb, name, options) => orbitdb.feed(name, options),
|
||||
tryInsert: (db) => db.add('hello'),
|
||||
query: (db) => db.iterator({ limit: -1 }).collect(),
|
||||
getTestValue: (db) => db.iterator({ limit: -1 }).collect()[0].payload.value,
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'key-value',
|
||||
create: (orbitdb, name, options) => orbitdb.kvstore(name, options),
|
||||
tryInsert: (db) => db.set('one', 'hello'),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.get('one'),
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'documents',
|
||||
create: (orbitdb, name, options) => orbitdb.docstore(name, options),
|
||||
tryInsert: (db) => db.put({ _id: 'hello world', doc: 'all the things'}),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.get('hello world'),
|
||||
expectedValue: [{ _id: 'hello world', doc: 'all the things'}],
|
||||
},
|
||||
{
|
||||
type: 'counter',
|
||||
create: (orbitdb, name, options) => orbitdb.counter(name, options),
|
||||
tryInsert: (db) => db.inc(8),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.value,
|
||||
expectedValue: 8,
|
||||
},
|
||||
]
|
||||
|
||||
module.exports = databases
|
@ -6,3 +6,5 @@ exports.waitForPeers = require('./wait-for-peers')
|
||||
exports.connectPeers = require('./connect-peers')
|
||||
exports.MemStore = require('./mem-store')
|
||||
exports.CustomTestKeystore = require('./custom-test-keystore')
|
||||
exports.CustomTestCache = require('./custom-test-cache')
|
||||
exports.databases = require('./databases')
|
||||
|
@ -5,59 +5,17 @@ const rmrf = require('rimraf')
|
||||
const OrbitDB = require('../src/OrbitDB')
|
||||
|
||||
// Include test utilities
|
||||
const {
|
||||
config,
|
||||
startIpfs,
|
||||
stopIpfs,
|
||||
testAPIs,
|
||||
const {
|
||||
config,
|
||||
startIpfs,
|
||||
stopIpfs,
|
||||
testAPIs,
|
||||
databases,
|
||||
} = require('./utils')
|
||||
|
||||
const dbPath = './orbitdb/tests/write-permissions'
|
||||
const ipfsPath = './orbitdb/tests/write-permissions/ipfs'
|
||||
|
||||
const databases = [
|
||||
{
|
||||
type: 'eventlog',
|
||||
create: (orbitdb, name, options) => orbitdb.eventlog(name, options),
|
||||
tryInsert: (db) => db.add('hello'),
|
||||
query: (db) => db.iterator({ limit: -1 }).collect(),
|
||||
getTestValue: (db) => db.iterator({ limit: -1 }).collect()[0].payload.value,
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'feed',
|
||||
create: (orbitdb, name, options) => orbitdb.feed(name, options),
|
||||
tryInsert: (db) => db.add('hello'),
|
||||
query: (db) => db.iterator({ limit: -1 }).collect(),
|
||||
getTestValue: (db) => db.iterator({ limit: -1 }).collect()[0].payload.value,
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'key-value',
|
||||
create: (orbitdb, name, options) => orbitdb.kvstore(name, options),
|
||||
tryInsert: (db) => db.set('one', 'hello'),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.get('one'),
|
||||
expectedValue: 'hello',
|
||||
},
|
||||
{
|
||||
type: 'documents',
|
||||
create: (orbitdb, name, options) => orbitdb.docstore(name, options),
|
||||
tryInsert: (db) => db.put({ _id: 'hello world', doc: 'all the things'}),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.get('hello world'),
|
||||
expectedValue: [{ _id: 'hello world', doc: 'all the things'}],
|
||||
},
|
||||
{
|
||||
type: 'counter',
|
||||
create: (orbitdb, name, options) => orbitdb.counter(name, options),
|
||||
tryInsert: (db) => db.inc(8),
|
||||
query: (db) => [],
|
||||
getTestValue: (db) => db.value,
|
||||
expectedValue: 8,
|
||||
},
|
||||
]
|
||||
|
||||
Object.keys(testAPIs).forEach(API => {
|
||||
describe(`orbit-db - Write Permissions (${API})`, function() {
|
||||
this.timeout(20000)
|
||||
@ -75,10 +33,10 @@ Object.keys(testAPIs).forEach(API => {
|
||||
})
|
||||
|
||||
after(async () => {
|
||||
if(orbitdb1)
|
||||
if(orbitdb1)
|
||||
await orbitdb1.stop()
|
||||
|
||||
if(orbitdb2)
|
||||
if(orbitdb2)
|
||||
await orbitdb2.stop()
|
||||
|
||||
if (ipfsd)
|
||||
@ -88,10 +46,10 @@ Object.keys(testAPIs).forEach(API => {
|
||||
describe('allows multiple peers to write to the databases', function() {
|
||||
databases.forEach(async (database) => {
|
||||
it(database.type + ' allows multiple writers', async () => {
|
||||
let options = {
|
||||
let options = {
|
||||
// Set write access for both clients
|
||||
write: [
|
||||
orbitdb1.key.getPublic('hex'),
|
||||
orbitdb1.key.getPublic('hex'),
|
||||
orbitdb2.key.getPublic('hex')
|
||||
],
|
||||
}
|
||||
@ -115,10 +73,10 @@ Object.keys(testAPIs).forEach(API => {
|
||||
describe('syncs databases', function() {
|
||||
databases.forEach(async (database) => {
|
||||
it(database.type + ' syncs', async () => {
|
||||
let options = {
|
||||
let options = {
|
||||
// Set write access for both clients
|
||||
write: [
|
||||
orbitdb1.key.getPublic('hex'),
|
||||
orbitdb1.key.getPublic('hex'),
|
||||
orbitdb2.key.getPublic('hex')
|
||||
],
|
||||
}
|
||||
@ -148,7 +106,7 @@ Object.keys(testAPIs).forEach(API => {
|
||||
describe('syncs databases that anyone can write to', function() {
|
||||
databases.forEach(async (database) => {
|
||||
it(database.type + ' syncs', async () => {
|
||||
let options = {
|
||||
let options = {
|
||||
// Set write permission for everyone
|
||||
write: ['*'],
|
||||
}
|
||||
@ -179,7 +137,7 @@ Object.keys(testAPIs).forEach(API => {
|
||||
databases.forEach(async (database) => {
|
||||
it(database.type + ' doesn\'t sync', async () => {
|
||||
|
||||
let options = {
|
||||
let options = {
|
||||
// Only peer 1 can write
|
||||
write: [orbitdb1.key.getPublic('hex')],
|
||||
}
|
||||
@ -228,7 +186,7 @@ Object.keys(testAPIs).forEach(API => {
|
||||
describe('throws an error if peer is not allowed to write to the database', function() {
|
||||
databases.forEach(async (database) => {
|
||||
it(database.type + ' throws an error', async () => {
|
||||
let options = {
|
||||
let options = {
|
||||
// No write access (only creator of the database can write)
|
||||
write: [],
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user