func ParseId(s string) (Id, error) {
	b, err := base64.RawURLEncoding.DecodeString(s)
	if err != nil {
		return "", err
	}
	if len(b) != 8 {
		return "", fmt.Errorf("bow.ParseId: input must be exactly 8 bytes long")
	}
	return Id(b), nil
}
ParseId parses the user-friendly output of String to an Id.
package bow
import (
	"encoding/base64"
	"encoding/binary"
	"encoding/json"
	"errors"
	"fmt"
	"math"
	"math/rand"
	"sync"
	"github.com/dgraph-io/badger/v2"
	"github.com/zippoxer/bow/codec"
	jsoncodec "github.com/zippoxer/bow/codec/json"
	keycodec "github.com/zippoxer/bow/codec/key"
	"github.com/sony/sonyflake"
)
var (
	ErrNotFound = errors.New("Record doesn't exist")
	ErrReadOnly = errors.New("Put and Delete aren't allowed in read-only mode")
)
const version = 1
const bucketIdSize = 2
const MaxBuckets = math.MaxUint16 - (8 * 256)
const reserved byte = 0x00
var (
	bucketIdSequence = []byte{reserved, 0x00}
	metaKey = []byte{reserved, 0x01}
)
var (
	keyCodec = keycodec.Codec{}
	sonyflakeKeygen = sonyflake.NewSonyflake(sonyflake.Settings{
		MachineID: func() (uint16, error) {
			return uint16(rand.Uint32() & (1<<16 - 1)), nil
		},
	})
)
type Id string
func NewId() Id {
	id, err := sonyflakeKeygen.NextID()
	if err != nil {
		panic(fmt.Sprintf("bow.NewId: %v", err))
	}
	b := make([]byte, 8)
	binary.BigEndian.PutUint64(b, id)
	return Id(b)
}