boltdb / bolt

An embedded key/value database for Go.
MIT License
14.24k stars 1.51k forks source link

concurrent writes and deadlocks #739

Open winteraz opened 6 years ago

winteraz commented 6 years ago

Only one read-write transaction is allowed at a time.

From documentation I understand that concurrent writes are not allowed. I'm not sure if this is correct thus this question to clarify: is boltdb designed only for one single writer (globally)? Am I suppose to maintain a lock on any write? Use case: I want to store access logs of http requests. Does this mean that I need to use a global channel to serialise the access bolt writes ?


e.g. 

var globalChan = make(chan string, 10)

func init() {
    const bucketName = "widgets"
    tx, err := db.Begin(true)
    if err != nil {
        panic(err)
    }
    _, err = tx.CreateBucketIfNotExists([]byte(bucketName))
    if err != nil {
        return err
    }
    go func() {
        for URL := range globalCHan {
            tx, err := db.Begin(true)
            if err != nil {
                panic(err)
            }
            bk := tx.Bucket([]byte(bucketName))
            // Set the value "bar" for the key "foo".
            if err := b.Put([]byte(time.Now().String()), []byte("bar")); err != nil {
                return err
            }
        }

    }()
}

func HandleFunc(w http.ResponseWriter, r *http.Request) {
    globalChan <- r.URL.String()
}
mei-rune commented 6 years ago

tx.Commit() or tx.Rollback() is missing

gigimushroom commented 6 years ago

db uses

wlock   sync.Mutex   // Allows only one writer at a time.

You dont need a global channel, just use transaction, only one will be processing, other will block and wait