ironsmith/datastore/ds.go
2016-04-18 20:31:22 +00:00

102 lines
2.2 KiB
Go

// Copyright 2016 Tim Shannon. All rights reserved.
// Use of this source code is governed by the MIT license
// that can be found in the LICENSE file.
// Package datastore manages the bolt data files and the reading and writing data to them
package datastore
import (
"encoding/json"
"errors"
"time"
"github.com/boltdb/bolt"
)
//TODO: Move this all over to GobStore if I ever get around to finishing it
// ErrNotFound is the error returned when a value cannot be found in the store for the given key
var ErrNotFound = errors.New("Value not found in datastore")
// Store is a datastore for getting and setting data for a given ironsmith project
// run on top of a Bolt DB file
type Store struct {
bolt *bolt.DB
}
// Open opens an existing datastore file, or creates a new one
// caller is responsible for closing the datastore
func Open(filename string) (*Store, error) {
db, err := bolt.Open(filename, 0666, &bolt.Options{Timeout: 1 * time.Minute})
if err != nil {
return nil, err
}
store := &Store{
bolt: db,
}
err = store.bolt.Update(func(tx *bolt.Tx) error {
_, err := tx.CreateBucketIfNotExists([]byte(bucketLog))
if err != nil {
return err
}
_, err = tx.CreateBucketIfNotExists([]byte(bucketReleases))
if err != nil {
return err
}
_, err = tx.CreateBucketIfNotExists([]byte(bucketFiles))
if err != nil {
return err
}
return nil
})
if err != nil {
return nil, err
}
return store, nil
}
// Close closes the bolt datastore
func (ds *Store) Close() error {
return ds.bolt.Close()
}
func (ds *Store) get(bucket string, key []byte, result interface{}) error {
return ds.bolt.View(func(tx *bolt.Tx) error {
dsValue := tx.Bucket([]byte(bucket)).Get(key)
if dsValue == nil {
return ErrNotFound
}
return json.Unmarshal(dsValue, result)
})
}
func (ds *Store) put(bucket string, key []byte, value interface{}) error {
var err error
dsValue, ok := value.([]byte)
if !ok {
dsValue, err = json.Marshal(value)
if err != nil {
return err
}
}
return ds.bolt.Update(func(tx *bolt.Tx) error {
return tx.Bucket([]byte(bucket)).Put(key, dsValue)
})
}
func (ds *Store) delete(bucket string, key []byte) error {
return ds.bolt.Update(func(tx *bolt.Tx) error {
return tx.Bucket([]byte(bucket)).Delete(key)
})
}