mirror of
https://github.com/gogrlx/bitcask.git
synced 2026-04-16 18:14:57 -07:00
Compare commits
5 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
f88919ecd0 | ||
|
|
108cb54cb2 | ||
|
|
904f6b19a0 | ||
|
|
4b52dea172 | ||
|
|
e9997642fe |
76
CODE_OF_CONDUCT.md
Normal file
76
CODE_OF_CONDUCT.md
Normal file
@@ -0,0 +1,76 @@
|
|||||||
|
# Contributor Covenant Code of Conduct
|
||||||
|
|
||||||
|
## Our Pledge
|
||||||
|
|
||||||
|
In the interest of fostering an open and welcoming environment, we as
|
||||||
|
contributors and maintainers pledge to making participation in our project and
|
||||||
|
our community a harassment-free experience for everyone, regardless of age, body
|
||||||
|
size, disability, ethnicity, sex characteristics, gender identity and expression,
|
||||||
|
level of experience, education, socio-economic status, nationality, personal
|
||||||
|
appearance, race, religion, or sexual identity and orientation.
|
||||||
|
|
||||||
|
## Our Standards
|
||||||
|
|
||||||
|
Examples of behavior that contributes to creating a positive environment
|
||||||
|
include:
|
||||||
|
|
||||||
|
* Using welcoming and inclusive language
|
||||||
|
* Being respectful of differing viewpoints and experiences
|
||||||
|
* Gracefully accepting constructive criticism
|
||||||
|
* Focusing on what is best for the community
|
||||||
|
* Showing empathy towards other community members
|
||||||
|
|
||||||
|
Examples of unacceptable behavior by participants include:
|
||||||
|
|
||||||
|
* The use of sexualized language or imagery and unwelcome sexual attention or
|
||||||
|
advances
|
||||||
|
* Trolling, insulting/derogatory comments, and personal or political attacks
|
||||||
|
* Public or private harassment
|
||||||
|
* Publishing others' private information, such as a physical or electronic
|
||||||
|
address, without explicit permission
|
||||||
|
* Other conduct which could reasonably be considered inappropriate in a
|
||||||
|
professional setting
|
||||||
|
|
||||||
|
## Our Responsibilities
|
||||||
|
|
||||||
|
Project maintainers are responsible for clarifying the standards of acceptable
|
||||||
|
behavior and are expected to take appropriate and fair corrective action in
|
||||||
|
response to any instances of unacceptable behavior.
|
||||||
|
|
||||||
|
Project maintainers have the right and responsibility to remove, edit, or
|
||||||
|
reject comments, commits, code, wiki edits, issues, and other contributions
|
||||||
|
that are not aligned to this Code of Conduct, or to ban temporarily or
|
||||||
|
permanently any contributor for other behaviors that they deem inappropriate,
|
||||||
|
threatening, offensive, or harmful.
|
||||||
|
|
||||||
|
## Scope
|
||||||
|
|
||||||
|
This Code of Conduct applies both within project spaces and in public spaces
|
||||||
|
when an individual is representing the project or its community. Examples of
|
||||||
|
representing a project or community include using an official project e-mail
|
||||||
|
address, posting via an official social media account, or acting as an appointed
|
||||||
|
representative at an online or offline event. Representation of a project may be
|
||||||
|
further defined and clarified by project maintainers.
|
||||||
|
|
||||||
|
## Enforcement
|
||||||
|
|
||||||
|
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
||||||
|
reported by contacting the project team at . All
|
||||||
|
complaints will be reviewed and investigated and will result in a response that
|
||||||
|
is deemed necessary and appropriate to the circumstances. The project team is
|
||||||
|
obligated to maintain confidentiality with regard to the reporter of an incident.
|
||||||
|
Further details of specific enforcement policies may be posted separately.
|
||||||
|
|
||||||
|
Project maintainers who do not follow or enforce the Code of Conduct in good
|
||||||
|
faith may face temporary or permanent repercussions as determined by other
|
||||||
|
members of the project's leadership.
|
||||||
|
|
||||||
|
## Attribution
|
||||||
|
|
||||||
|
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
|
||||||
|
available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html
|
||||||
|
|
||||||
|
[homepage]: https://www.contributor-covenant.org
|
||||||
|
|
||||||
|
For answers to common questions about this code of conduct, see
|
||||||
|
https://www.contributor-covenant.org/faq
|
||||||
21
LICENSE
Normal file
21
LICENSE
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2019 James Mills
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
||||||
@@ -61,11 +61,12 @@ Benchmarks run on a 11" Macbook with a 1.4Ghz Intel Core i7:
|
|||||||
```
|
```
|
||||||
$ make bench
|
$ make bench
|
||||||
...
|
...
|
||||||
BenchmarkGet-4 50000 33185 ns/op 600 B/op 14 allocs/op
|
BenchmarkGet-4 300000 5065 ns/op 144 B/op 4 allocs/op
|
||||||
BenchmarkPut-4 100000 16757 ns/op 699 B/op 7 allocs/op
|
BenchmarkPut-4 100000 14640 ns/op 699 B/op 7 allocs/op
|
||||||
```
|
```
|
||||||
|
|
||||||
* ~30,000 reads/sec
|
* ~30,000 reads/sec for non-active data
|
||||||
|
* ~180,000 reads/sec for active data
|
||||||
* ~60,000 writes/sec
|
* ~60,000 writes/sec
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|||||||
47
bitcask.go
47
bitcask.go
@@ -22,14 +22,18 @@ var (
|
|||||||
)
|
)
|
||||||
|
|
||||||
type Bitcask struct {
|
type Bitcask struct {
|
||||||
path string
|
path string
|
||||||
curr *Datafile
|
curr *Datafile
|
||||||
keydir *Keydir
|
keydir *Keydir
|
||||||
|
datafiles []*Datafile
|
||||||
|
|
||||||
maxDatafileSize int64
|
maxDatafileSize int64
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b *Bitcask) Close() error {
|
func (b *Bitcask) Close() error {
|
||||||
|
for _, df := range b.datafiles {
|
||||||
|
df.Close()
|
||||||
|
}
|
||||||
return b.curr.Close()
|
return b.curr.Close()
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -38,16 +42,18 @@ func (b *Bitcask) Sync() error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (b *Bitcask) Get(key string) ([]byte, error) {
|
func (b *Bitcask) Get(key string) ([]byte, error) {
|
||||||
|
var df *Datafile
|
||||||
|
|
||||||
item, ok := b.keydir.Get(key)
|
item, ok := b.keydir.Get(key)
|
||||||
if !ok {
|
if !ok {
|
||||||
return nil, ErrKeyNotFound
|
return nil, ErrKeyNotFound
|
||||||
}
|
}
|
||||||
|
|
||||||
df, err := NewDatafile(b.path, item.FileID, true)
|
if item.FileID == b.curr.id {
|
||||||
if err != nil {
|
df = b.curr
|
||||||
return nil, err
|
} else {
|
||||||
|
df = b.datafiles[item.FileID]
|
||||||
}
|
}
|
||||||
defer df.Close()
|
|
||||||
|
|
||||||
e, err := df.ReadAt(item.Index)
|
e, err := df.ReadAt(item.Index)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@@ -100,6 +106,9 @@ func (b *Bitcask) put(key string, value []byte) (int64, error) {
|
|||||||
return -1, err
|
return -1, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
df, err := NewDatafile(b.path, b.curr.id, true)
|
||||||
|
b.datafiles = append(b.datafiles, df)
|
||||||
|
|
||||||
id := b.curr.id + 1
|
id := b.curr.id + 1
|
||||||
curr, err := NewDatafile(b.path, id, false)
|
curr, err := NewDatafile(b.path, id, false)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@@ -266,8 +275,6 @@ func Open(path string, options ...func(*Bitcask) error) (*Bitcask, error) {
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
keydir := NewKeydir()
|
|
||||||
|
|
||||||
fns, err := getDatafiles(path)
|
fns, err := getDatafiles(path)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
@@ -278,7 +285,16 @@ func Open(path string, options ...func(*Bitcask) error) (*Bitcask, error) {
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
keydir := NewKeydir()
|
||||||
|
var datafiles []*Datafile
|
||||||
|
|
||||||
for i, fn := range fns {
|
for i, fn := range fns {
|
||||||
|
df, err := NewDatafile(path, ids[i], true)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
datafiles = append(datafiles, df)
|
||||||
|
|
||||||
if filepath.Ext(fn) == ".hint" {
|
if filepath.Ext(fn) == ".hint" {
|
||||||
f, err := os.Open(filepath.Join(path, fn))
|
f, err := os.Open(filepath.Join(path, fn))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@@ -296,11 +312,6 @@ func Open(path string, options ...func(*Bitcask) error) (*Bitcask, error) {
|
|||||||
keydir.Add(key, item.FileID, item.Index, item.Timestamp)
|
keydir.Add(key, item.FileID, item.Index, item.Timestamp)
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
df, err := NewDatafile(path, ids[i], true)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
for {
|
for {
|
||||||
e, err := df.Read()
|
e, err := df.Read()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@@ -325,15 +336,17 @@ func Open(path string, options ...func(*Bitcask) error) (*Bitcask, error) {
|
|||||||
if len(ids) > 0 {
|
if len(ids) > 0 {
|
||||||
id = ids[(len(ids) - 1)]
|
id = ids[(len(ids) - 1)]
|
||||||
}
|
}
|
||||||
|
|
||||||
curr, err := NewDatafile(path, id, false)
|
curr, err := NewDatafile(path, id, false)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
bitcask := &Bitcask{
|
bitcask := &Bitcask{
|
||||||
path: path,
|
path: path,
|
||||||
curr: curr,
|
curr: curr,
|
||||||
keydir: keydir,
|
keydir: keydir,
|
||||||
|
datafiles: datafiles,
|
||||||
|
|
||||||
maxDatafileSize: DefaultMaxDatafileSize,
|
maxDatafileSize: DefaultMaxDatafileSize,
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user