2015-04-07 08:20:55 +00:00
|
|
|
package bolt
|
|
|
|
|
2015-04-10 19:52:33 +00:00
|
|
|
import (
|
2015-04-13 22:51:15 +00:00
|
|
|
"bytes"
|
|
|
|
|
2015-04-10 19:52:33 +00:00
|
|
|
"github.com/boltdb/bolt"
|
2015-04-11 05:22:55 +00:00
|
|
|
"github.com/youtube/vitess/go/bson"
|
2015-04-10 19:52:33 +00:00
|
|
|
)
|
2015-04-07 08:20:55 +00:00
|
|
|
|
|
|
|
func encode(v interface{}) ([]byte, error) {
|
|
|
|
return bson.Marshal(v)
|
|
|
|
}
|
|
|
|
|
|
|
|
func decode(raw []byte, v interface{}) error {
|
|
|
|
return bson.Unmarshal(raw, v)
|
|
|
|
}
|
|
|
|
|
2015-04-10 19:52:33 +00:00
|
|
|
func get(t *bolt.Tx, bucket, key []byte, v interface{}) error {
|
2015-04-07 08:20:55 +00:00
|
|
|
raw := t.Bucket(bucket).Get(key)
|
|
|
|
if raw == nil {
|
|
|
|
return ErrKeyNotFound
|
|
|
|
}
|
|
|
|
return bson.Unmarshal(raw, v)
|
|
|
|
}
|
|
|
|
|
2015-04-10 19:52:33 +00:00
|
|
|
func raw(t *bolt.Tx, bucket, key []byte) ([]byte, error) {
|
2015-04-07 08:20:55 +00:00
|
|
|
raw := t.Bucket(bucket).Get(key)
|
|
|
|
if raw == nil {
|
|
|
|
return nil, ErrKeyNotFound
|
|
|
|
}
|
|
|
|
return raw, nil
|
|
|
|
}
|
|
|
|
|
2015-04-10 19:52:33 +00:00
|
|
|
func update(t *bolt.Tx, bucket, key []byte, v interface{}) error {
|
2015-04-07 08:20:55 +00:00
|
|
|
raw, err := encode(v)
|
|
|
|
if err != nil {
|
|
|
|
t.Rollback()
|
|
|
|
return err
|
|
|
|
}
|
2015-04-11 05:22:55 +00:00
|
|
|
return t.Bucket(bucket).Put(key, raw)
|
2015-04-07 08:20:55 +00:00
|
|
|
}
|
|
|
|
|
2015-04-10 19:52:33 +00:00
|
|
|
func insert(t *bolt.Tx, bucket, key []byte, v interface{}) error {
|
2015-04-07 08:20:55 +00:00
|
|
|
raw, err := encode(v)
|
|
|
|
if err != nil {
|
|
|
|
t.Rollback()
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
// verify the key does not already exists
|
|
|
|
// in the bucket. If exists, fail
|
|
|
|
if t.Bucket(bucket).Get(key) != nil {
|
|
|
|
return ErrKeyExists
|
|
|
|
}
|
2015-04-11 05:22:55 +00:00
|
|
|
return t.Bucket(bucket).Put(key, raw)
|
2015-04-07 08:20:55 +00:00
|
|
|
}
|
|
|
|
|
2015-04-10 19:52:33 +00:00
|
|
|
func delete(t *bolt.Tx, bucket, key []byte) error {
|
2015-04-11 05:22:55 +00:00
|
|
|
return t.Bucket(bucket).Delete(key)
|
2015-04-07 08:20:55 +00:00
|
|
|
}
|
2015-04-13 22:51:15 +00:00
|
|
|
|
|
|
|
func push(t *bolt.Tx, bucket, index, value []byte) error {
|
|
|
|
var keys [][]byte
|
|
|
|
err := get(t, bucket, index, &keys)
|
|
|
|
if err != nil && err != ErrKeyNotFound {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
keys = append(keys, value)
|
|
|
|
return update(t, bucket, index, &keys)
|
|
|
|
}
|
|
|
|
|
|
|
|
func splice(t *bolt.Tx, bucket, index, value []byte) error {
|
|
|
|
var keys [][]byte
|
|
|
|
err := get(t, bucket, index, &keys)
|
|
|
|
if err != nil && err != ErrKeyNotFound {
|
|
|
|
return err
|
|
|
|
}
|
2015-04-14 04:39:05 +00:00
|
|
|
|
2015-04-13 22:51:15 +00:00
|
|
|
for i, key := range keys {
|
|
|
|
if bytes.Equal(key, value) {
|
|
|
|
keys = keys[:i+copy(keys[i:], keys[i+1:])]
|
|
|
|
break
|
|
|
|
}
|
|
|
|
}
|
2015-04-14 04:39:05 +00:00
|
|
|
|
2015-04-13 22:51:15 +00:00
|
|
|
return update(t, bucket, index, &keys)
|
|
|
|
}
|