func GetMap(tx *bolt.Tx, bucket string, key []byte) (map[string]struct{}, error) {
	var rs map[string]struct{}
	_, err := Get(tx, bucket, key, &rs)
	return rs, err
}
GetMap gets map[string]struct{} value.
package db
import (
	"bytes"
	"encoding/binary"
	"errors"
	"fmt"
	"log"
	"path"
	"encoding/json"
	"github.com/boltdb/bolt"
	"github.com/shingetsu-gou/shingetsu-gou/cfg"
)
var DB *bolt.DB
func Setup() {
	dbpath := path.Join(cfg.RunDir, "gou_bolt.db")
	var err error
	DB, err = bolt.Open(dbpath, 0644, nil)
	if err != nil {
		log.Fatal(err)
	}
}
func Tob(v interface{}) ([]byte, error) {
	switch t := v.(type) {
	case []byte:
		return t, nil
	case string:
		return []byte(t), nil
	case int:
		b := make([]byte, 8)
		binary.BigEndian.PutUint64(b, uint64(t))
		return b, nil
	case int64:
		b := make([]byte, 8)
		binary.BigEndian.PutUint64(b, uint64(t))
		return b, nil
	case uint64:
		b := make([]byte, 8)
		binary.BigEndian.PutUint64(b, t)
		return b, nil
	default:
		return json.Marshal(v)
	}
}
func MustTob(v interface{}) []byte {
	b, err := Tob(v)
	if err != nil {
		log.Fatal(err)
	}
	return b
}
func ToKey(v ...interface{}) []byte {
	var r []byte
	for _, vv := range v {
		b := MustTob(vv)
		r = append(r, b...)
		if _, ok := vv.(string); ok {
			r = append(r, '\x00')
		}
	}
	return r
}
func b2v(from []byte, to interface{}) error {
	var err error
	switch t := to.(type) {
	case *string:
		(*t) = string(from)
	case *int64:
		(*t) = int64(binary.BigEndian.Uint64(from))
	case *int:
		(*t) = int(binary.BigEndian.Uint64(from))
	case *uint64:
		(*t) = binary.BigEndian.Uint64(from)
	case nil:
	default:
		err = json.Unmarshal(from, to)
	}
	return err
}
func Get(tx *bolt.Tx, bucket string, key []byte, value interface{}) ([]byte, error) {
	b := tx.Bucket([]byte(bucket))
	if b == nil {
		return nil, errors.New("bucket not found " + bucket)
	}
	v := b.Get(key)
	if v == nil {
		return nil, errors.New("key not found")
	}
	return v, b2v(v, value)
}
func Put(tx *bolt.Tx, bucket string, key []byte, value interface{}) error {
	val, err := Tob(value)
	if err != nil {
		return err
	}
	b, errr := tx.CreateBucketIfNotExists([]byte(bucket))
	if errr != nil {
		return fmt.Errorf("create bucket: %s", err)
	}
	return b.Put(key, val)
}
func HasKey(tx *bolt.Tx, bucket string, key []byte) (bool, error) {
	var v []byte
	b := tx.Bucket([]byte(bucket))
	if b == nil {
		return false, errors.New("bucket not found " + bucket)
	}
	v = b.Get(key)
	return v != nil, nil
}
func Count(tx *bolt.Tx, bucket string, prefix []byte) (int, error) {
	var cnt int
	b := tx.Bucket([]byte(bucket))
	if b == nil {
		return 0, errors.New("bucket not found " + bucket)
	}
	c := b.Cursor()
	for k, _ := c.Seek(prefix); bytes.HasPrefix(k, prefix); k, _ = c.Next() {
		cnt++
	}
	return cnt, nil
}
func GetStrings(tx *bolt.Tx, bucket string, prefix []byte) ([]string, error) {
	var cnt []string
	b := tx.Bucket([]byte(bucket))
	if b == nil {
		return nil, errors.New("bucket not found " + bucket)
	}
	c := b.Cursor()
	for k, v := c.Seek(prefix); bytes.HasPrefix(k, prefix); k, v = c.Next() {
		var str string
		if err := b2v(v, &str); err != nil {
			return nil, err
		}
		cnt = append(cnt, str)
	}
	return cnt, nil
}
func KeyStrings(tx *bolt.Tx, bucket string) ([]string, error) {
	var cnt []string
	b := tx.Bucket([]byte(bucket))
	if b == nil {
		return nil, errors.New("bucket not found " + bucket)
	}
	err := b.ForEach(func(k, v []byte) error {
		var str string
		if err := b2v(k, &str); err != nil {
			return err
		}
		cnt = append(cnt, str)
		return nil
	})
	return cnt, err
}
func Del(tx *bolt.Tx, bucket string, key []byte) error {
	b := tx.Bucket([]byte(bucket))
	if b == nil {
		return errors.New("bucket not found " + bucket)
	}
	return b.Delete(key)
}