5.0.5 • Published 6 months ago

@begin/data v5.0.5

Weekly downloads
732
License
Apache-2.0
Repository
github
Last release
6 months ago

Begin Data

@begin/data

GitHub CI status

Begin Data is an easy to use, fast, and durable key/value and document store built on top of DynamoDB. Originally built for Begin serverless apps, Begin Data’s core API has three simple methods: get, set, and destroy.

Concepts

Begin Data organizes itself into tables. A table contain documents which are just collections of plain Objects. Documents stored in Begin Data always have the properties table and key.

Optionally a document can also have a ttl property with a UNIX epoch value representing the expiry time for the document.

Usage

Begin Data operates on one DynamoDB table named data with a partition key scopeID and a sort key of dataID (and, optionally, a ttl for expiring documents).

Example app.arc:

@app
myapp

@tables
data
  scopeID *String
  dataID **String
  ttl TTL

Or equivalent CloudFormation YAML:

AWSTemplateFormatVersion: "2010-09-09"
Resources:
    BeginData:
        Type: "AWS::DynamoDB::Table"
        Properties:
            TableName: "data"
            BillingMode: "PAY_PER_REQUEST"
            KeySchema:
              -
                AttributeName: "scopeID"
                KeyType: "HASH"
              -
                AttributeName: "dataID"
                KeyType: "RANGE"
            SSESpecification:
                Enabled: "false"
            TimeToLiveSpecification:
                AttributeName: "ttl"
                Enabled: "TRUE"

Note: projects not based on Architect will need a BEGIN_DATA_TABLE_NAME environment variable. You can also use this env var to override and name the table anything you want. This also allows for multiple apps to share a single table.

API

let data = require('@begin/data')

The core API is three methods:

  • data.get(params[, callback])[Promise] for retreiving data
  • data.set(params[, callback])[Promise] for writing data
  • data.destroy(params[, callback])[Promise] for removing data

Additional helper methods are also made available:

  • data.incr(params[, callback])[Promise] increment an attribute on a document
  • data.decr(params[, callback])[Promise] decrement an attribute on a document
  • data.count(params[, callback])[Promise] get the number of documents for a given table

All methods accept a params object and, optionally, a Node-style errback. If no errback is supplied, a Promise is returned. All methods support async/await.

Writes

Save a document in a table by key. Remember: table is required; key is optional.

let taco = await data.set({
  table: 'tacos',
  key: 'al-pastor'
})

All documents have a key. If no key is given, set will generate a unique key.

let token = await data.set({
  table: 'tokens',
})
// {table:'tokens', key:'LCJkYX9jYWwidW50RhSU'}

Batch save multiple documents at once by passing an Array of Objects.

let collection = await data.set([
  {table: 'ppl', name:'brian', email:'b@brian.io'},
  {table: 'ppl', name:'sutr0', email:'sutr0@brian.io'},
  {table: 'tacos', key:'pollo'},
  {table: 'tacos', key:'carnitas'},
])

Reads

Read a document by key:

let yum = await data.get({
  table: 'tacos',
  key: 'baja'
})

Batch read by passing an Array of Objects. With these building blocks you can construct secondary indexes and joins, like one-to-many and many-to-many.

await data.get([
  {table:'tacos', key:'carnitas'},
  {table:'tacos', key:'al-pastor'},
])

Destroy

Delete a document by key.

await data.destroy({
  table: 'tacos',
  key: 'pollo'
})

Batch delete documents by passing an Array of Objects.

await data.destroy([
  {table:'tacos', key:'carnitas'},
  {table:'tacos', key:'al-pastor'},
])

Pagination

Large sets of data can not be retrieved in one call because the underlying get api paginates results. In this case use the for await syntax with a limit set to get paginated data.

let pages = data.page({ table:'ppl', limit:25 })
let count = 0  
for await (let page of pages) {
  console.log(page)
  count++
}

Additional Superpowers

  • Documents can be expired by setting ttl to an UNIX epoch in the future.
  • Atomic counters: data.incr and data.decr

See the tests for more examples!

Patterns

Coming soon! Detailed guides for various data persistence tasks:

  • Denormalizing
  • Pagination
  • Counters
  • Secondary indexes
  • One to many
  • Many to many

More

5.0.5

6 months ago

5.0.4

7 months ago

5.0.3

10 months ago

5.0.2

10 months ago

5.0.1

10 months ago

5.0.0

10 months ago

5.0.0-RC.2

10 months ago

5.0.0-RC.1

10 months ago

5.0.0-RC.0

10 months ago

4.0.2-RC.1

2 years ago

4.0.2-RC.0

2 years ago

4.0.2

2 years ago

4.0.1-RC.0

2 years ago

4.0.1

2 years ago

4.0.0

3 years ago

4.0.0-RC.2

3 years ago

4.0.0-RC.0

3 years ago

4.0.0-RC.1

3 years ago

3.0.4

3 years ago

3.0.3

3 years ago

3.0.0

3 years ago

2.0.0-RC.2

4 years ago

2.0.1

4 years ago

2.0.0

4 years ago

2.0.0-RC.0

4 years ago

1.2.4-RC.0

4 years ago

1.2.3-RC.0

4 years ago

1.2.3

4 years ago

1.2.2

5 years ago

1.2.1

5 years ago

1.2.0

5 years ago

1.1.8-RC.3

5 years ago

1.1.8-RC.2

5 years ago

1.1.8-RC.1

5 years ago

1.1.7

5 years ago

1.1.7-RC.0

5 years ago

1.1.6

5 years ago

1.1.5

5 years ago

1.1.5-RC.0

5 years ago

1.1.4

5 years ago

1.1.4-RC.0

5 years ago

1.1.2

5 years ago

1.1.1

6 years ago

1.1.0

6 years ago

1.0.3

6 years ago

1.0.2

6 years ago

1.0.1

6 years ago

1.0.0

6 years ago

0.0.1

6 years ago