Comparing version 0.10.3 to 0.11.0
{ | ||
"name": "lowdb", | ||
"version": "0.10.3", | ||
"description": "Flat JSON file database", | ||
"version": "0.11.0", | ||
"description": "JSON database for Node and the browser powered by lodash", | ||
"keywords": [ | ||
@@ -14,10 +14,13 @@ "flat", | ||
"underscore", | ||
"underscore-db", | ||
"localStorage", | ||
"embed", | ||
"embeddable" | ||
"embeddable", | ||
"extendable" | ||
], | ||
"main": "src/index.js", | ||
"main": "lib", | ||
"scripts": { | ||
"test": "standard && mocha", | ||
"precommit": "npm test" | ||
"test": "babel-node test/all && standard", | ||
"prepublish": "npm run build", | ||
"precommit": "npm test", | ||
"build": "babel src --out-dir lib" | ||
}, | ||
@@ -38,13 +41,22 @@ "repository": { | ||
"lodash": "^3.1.0", | ||
"steno": "^0.4.1", | ||
"q": "^1.4.1" | ||
"steno": "^0.4.1" | ||
}, | ||
"devDependencies": { | ||
"babel-cli": "^6.2.0", | ||
"babel-eslint": "^4.1.6", | ||
"babel-preset-es2015": "^6.1.18", | ||
"babel-preset-stage-3": "^6.3.13", | ||
"husky": "^0.9.0", | ||
"mocha": "^2.2.5", | ||
"rimraf": "^2.2.8", | ||
"sinon": "^1.12.2", | ||
"sinon": "^1.17.2", | ||
"standard": "^4.0.1", | ||
"tape": "^4.2.2", | ||
"tempfile": "^1.1.1", | ||
"underscore-db": "^0.9.0" | ||
}, | ||
"engines": { | ||
"node": ">= 0.12" | ||
}, | ||
"standard": { | ||
"parser": "babel-eslint" | ||
} | ||
} |
283
README.md
# lowdb [![NPM version](https://badge.fury.io/js/lowdb.svg)](http://badge.fury.io/js/lowdb) [![Build Status](https://travis-ci.org/typicode/lowdb.svg?branch=master)](https://travis-ci.org/typicode/lowdb) | ||
> Need a quick way to get a local database? | ||
> Need a quick way to get a local database for a CLI, a small server or the browser? | ||
## Example | ||
```javascript | ||
var low = require('lowdb') | ||
var db = low('db.json') | ||
```js | ||
const low = require('lowdb') | ||
const storage = require('lowdb/file-sync') | ||
const db = low('db.json', { storage }) | ||
db('posts').push({ title: 'lowdb is awesome'}) | ||
@@ -16,3 +18,3 @@ ``` | ||
```javascript | ||
```js | ||
{ | ||
@@ -25,8 +27,10 @@ "posts": [ | ||
You can query and manipulate it using __any__ [lodash](https://lodash.com/docs) __method__ | ||
You can query and manipulate it using __any__ [lodash](https://lodash.com/docs) __method__. | ||
```javascript | ||
```js | ||
db('posts').find({ title: 'lowdb is awesome' }) | ||
``` | ||
Please note that lowdb can only be run in one instance of Node, it doesn't support Cluster. | ||
## Install | ||
@@ -40,42 +44,138 @@ | ||
* Small | ||
* Serverless | ||
* lodash rich API | ||
* In-memory or disk-based | ||
* __Hackable__ (mixins, id, encryption, ...) | ||
* Very small (~100 lines for core) | ||
* lodash API | ||
* Extendable: | ||
* __Custom storage__ (file, browser, in-memory, ...) | ||
* __Custom format__ (JSON, BSON, YAML, ...) | ||
* __Mixins__ (id support, ...) | ||
* __Encryption__ | ||
It's also __very easy to learn and use__ since it has __only 8 methods and properties__. | ||
Lowdb is also very easy to learn since it has __only 4 methods and properties__. | ||
_lowdb powers [json-server](https://github.com/typicode/json-server) package, [jsonplaceholder](http://jsonplaceholder.typicode.com/) website and [other projects](https://www.npmjs.com/browse/depended/lowdb)._ | ||
_lowdb powers [json-server](https://github.com/typicode/json-server) package, [jsonplaceholder](http://jsonplaceholder.typicode.com/) website and [many other great projects](https://www.npmjs.com/browse/depended/lowdb)._ | ||
## API | ||
## Usage examples | ||
__low([filename, options])__ | ||
Depending on the context, you can use different storages and formats. | ||
Creates a disk-based or in-memory database instance. If a filename is provided, it loads or creates it. | ||
Lowdb comes bundled with `file-sync`, `file-async` and `browser` storages, but you can also write your own if needed. | ||
```javascript | ||
var db = low() // in-memory | ||
var db = low('db.json') // disk-based | ||
### CLI | ||
For CLIs, it's easier to use `lowdb/file-sync` synchronous file storage . | ||
```js | ||
const low = require('lowdb') | ||
const fileSync = require('lowdb/file-sync') | ||
const db = low('db.json', fileSync) | ||
db('users').push({ name: 'typicode' }) | ||
const user = db('users').find({ name: 'typicode' }) | ||
``` | ||
When a filename is provided you can set options. | ||
### Server | ||
```javascript | ||
var db = low('db.json', { | ||
autosave: true, // automatically save database on change (default: true) | ||
async: true // asynchronous write (default: true) | ||
promise: false // .save() and .value() return a promise (default: false) | ||
For servers, it's better to avoid blocking requests. Use `lowdb/file-async` asynchronous file storage. | ||
__Important__ | ||
* When you modify the database, a Promise is returned. | ||
* When you read from the database, the result is immediately returned. | ||
```js | ||
const low = require('lowdb'). | ||
const storage = require('lowdb/file-async') | ||
const db = low('db.json', { storage }) | ||
app.get('/posts/:id', (req, res) => { | ||
// Returns a post | ||
const post = db('posts').find({ id: req.params.id }) | ||
res.send(post) | ||
}) | ||
app.post('/posts', (req, res) => { | ||
// Returns a Promise that resolves to a post | ||
db('posts') | ||
.push(req.body) | ||
.then(post => res.send(post)) | ||
}) | ||
``` | ||
__low.stringify(obj)__ and __low.parse(str)__ | ||
### Browser | ||
Overwrite these methods to customize JSON stringifying and parsing. | ||
In the browser, `lowdb/browser` will add `localStorage` support. | ||
```js | ||
const low = require('lowdb') | ||
const storage = require('lowdb/browser') | ||
const db = low('db.json', { storage }) | ||
db('users').push({ name: 'typicode' }) | ||
const user = db('users').find({ name: 'typicode' }) | ||
``` | ||
### In-memory | ||
For the best performance, use lowdb in-memory storage. | ||
```js | ||
const low = require('lowdb') | ||
const db = low() | ||
db('users').push({ name: 'typicode' }) | ||
const user = db('users').find({ name: 'typicode' }) | ||
``` | ||
Please note that, as an alternative, you can also disable `writeOnChange` if you want to control when data is written. | ||
## API | ||
__low([filename, [storage, [writeOnChange = true]]])__ | ||
Creates a new database instance. Here are some examples: | ||
```js | ||
low() // in-memory | ||
low('db.json', { storage: /* */ }) // persisted | ||
low('db.json', { storage: /* */ }, false) // auto write disabled | ||
// To create read-only or write-only database | ||
// pass only the read or write function. | ||
// For example: | ||
const fileSync = require('lowdb/fileSync') | ||
// write-only | ||
low('db.json', { | ||
storage: { write: fileSync.write } | ||
}) | ||
// read-only | ||
low('db.json', { | ||
storage: { read: fileSync.read } | ||
}) | ||
``` | ||
Full method signature: | ||
```js | ||
low(source, { | ||
storage: { | ||
read: (source, deserialize) => // obj | ||
write: (dest, obj, serialize) => // undefined or a Promise | ||
}, | ||
format: { | ||
deserialize: (data) => // obj | ||
serialize: (obj) => // data | ||
} | ||
}, writeOnChange) | ||
``` | ||
__db.___ | ||
Database lodash instance. Use it for example to add your own utility functions or third-party libraries. | ||
Database lodash instance. Use it to add your own utility functions or third-party mixins like [underscore-contrib](https://github.com/documentcloud/underscore-contrib) or [underscore-db](https://github.com/typicode/underscore-db). | ||
```javascript | ||
```js | ||
db._.mixin({ | ||
@@ -95,32 +195,33 @@ second: function(array) { | ||
```javascript | ||
if (db.object.songs) console.log('songs array exists') | ||
```js | ||
db.object // { songs: [ ... ] } | ||
``` | ||
__db.save([filename])__ | ||
If you directly modify the content of the database object, you will need to manually call `write` to persist changes. | ||
Saves database to file. | ||
```js | ||
// Delete an array | ||
delete db.object.songs | ||
db.write() | ||
```javascript | ||
var db = low('db.json') | ||
db.save() // saves to db.json | ||
db.save('copy.json') | ||
// Drop database | ||
db.object = {} | ||
db.write() | ||
``` | ||
Note: In case you directly modify the content of the database object, you'll need to manually call `save` | ||
__db.write([source])__ | ||
```javascript | ||
delete db.object.songs | ||
db.save() | ||
Persists database using `storage.write` method. | ||
```js | ||
const db = low('db.json') | ||
db.write() // writes to db.json | ||
db.write('copy.json') // writes to copy.json | ||
``` | ||
__db.saveSync([filename])__ | ||
Synchronous version of `db.save()` | ||
## Guide | ||
### Operations | ||
### How to query | ||
With LowDB you get access to the entire [lodash API](http://lodash.com/), so there's many ways to query and manipulate data. Here are a few examples to get you started. | ||
With lowdb, you get access to the entire [lodash API](http://lodash.com/), so there is many ways to query and manipulate data. Here are a few examples to get you started. | ||
@@ -131,5 +232,7 @@ Please note that data is returned by reference, this means that modifications to returned objects may change the database. To avoid such behaviour, you need to use `.cloneDeep()`. | ||
#### Examples | ||
Sort the top five songs. | ||
```javascript | ||
```js | ||
db('songs') | ||
@@ -145,3 +248,3 @@ .chain() | ||
```javascript | ||
```js | ||
db('songs').pluck('title') | ||
@@ -152,3 +255,3 @@ ``` | ||
```javascript | ||
```js | ||
db('songs').size() | ||
@@ -159,3 +262,3 @@ ``` | ||
```javascript | ||
```js | ||
db('songs').cloneDeep() | ||
@@ -166,3 +269,3 @@ ``` | ||
```javascript | ||
```js | ||
db('songs') | ||
@@ -177,7 +280,7 @@ .chain() | ||
```javascript | ||
```js | ||
db('songs').remove({ title: 'low!' }) | ||
``` | ||
### Id support | ||
### How to use id based resources | ||
@@ -188,3 +291,3 @@ Being able to retrieve data using an id can be quite useful, particularly in servers. To add id-based resources support to lowdb, you have 2 options. | ||
```javascript | ||
```js | ||
var db = low('db.json') | ||
@@ -198,5 +301,5 @@ | ||
[uuid](https://github.com/broofa/node-uuid) returns a unique id. | ||
[uuid](https://github.com/broofa/node-uuid) is more minimalist and returns a unique id that you can use when creating resources. | ||
```javascript | ||
```js | ||
var uuid = require('uuid') | ||
@@ -208,32 +311,62 @@ | ||
### Encryption support | ||
### How to use custom format | ||
In some cases, you may want to make it harder to read database content. By overwriting, `low.stringify` and `low.parse`, you can add custom encryption. | ||
By default, lowdb storages will use `JSON` to `parse` and `stringify` database object. | ||
```javascript | ||
var crypto = require('crypto') | ||
But it's also possible to specify custom `format.serializer` and `format.deserializer` methods that will be passed by lowdb to `storage.read` and `storage.write` methods. | ||
var cipher = crypto.createCipher('aes256', secretKey) | ||
var decipher = crypto.createDecipher('aes256', secretKey) | ||
For example, if you want to store database in `.bson` files ([MongoDB file format](https://github.com/mongodb/js-bson)): | ||
low.stringify = function(obj) { | ||
var str = JSON.stringify(obj) | ||
return cipher.update(str, 'utf8', 'hex') + cipher.final('hex') | ||
} | ||
```js | ||
const low = require('lowdb') | ||
const storage = require('lowdb/file-sync') | ||
const bson = require('bson') | ||
const BSON = new bson.BSONPure.BSON() | ||
low.parse = function(encrypted) { | ||
var str = decipher.update(encrypted, 'hex', 'utf8') + decipher.final('utf8') | ||
return JSON.parse(str) | ||
} | ||
low('db.bson', { storage, format: { | ||
serialize: BSON.serialize | ||
deserialize: BSON.deserialize | ||
}) | ||
// Alternative ES2015 short syntax | ||
const bson = require('bson') | ||
const format = new bson.BSONPure.BSON() | ||
low('db.bson', { storage, format }) | ||
``` | ||
### How to encrypt data | ||
Simply `encrypt` and `decrypt` data in `format.serialize` and `format.deserialize` methods. | ||
For example, using [cryptr](https://github.com/MauriceButler/cryptr): | ||
```js | ||
const Cryptr = require("./cryptr"), | ||
const cryptr = new Cryptr('my secret key') | ||
const db = low('db.json', { | ||
format: { | ||
deserialize: (str) => { | ||
const decrypted = cryptr.decrypt(str) | ||
const obj = JSON.parse(decrypted) | ||
return obj | ||
}, | ||
serialize: (obj) => { | ||
const str = JSON.stringify(obj) | ||
const encrypted = cryptr.encrypt(str) | ||
return encrypted | ||
} | ||
} | ||
}) | ||
``` | ||
## Changelog | ||
See details changes for each version in the [release notes](https://github.com/typicode/lowdb/releases). | ||
See changes for each version in the [release notes](https://github.com/typicode/lowdb/releases). | ||
## Limits | ||
lowdb is a convenient method for storing data without setting up a database server. It's fast enough and safe to be used as an embedded database. | ||
lowdb is a convenient method for storing data without setting up a database server. It is fast enough and safe to be used as an embedded database. | ||
However, if you need high performance and scalability more than simplicity, you should stick to databases like MongoDB. | ||
However, if you seek high performance and scalability more than simplicity, you should probably stick to traditional databases like MongoDB. | ||
@@ -240,0 +373,0 @@ ## License |
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
15754
4
10
363
10
145
1