Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

db: no need to entirely lock DB unless needed #339

Merged
merged 1 commit into from
Aug 11, 2015
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 0 additions & 26 deletions cmd/drive/main.go
Original file line number Diff line number Diff line change
@@ -409,8 +409,6 @@ func (cmd *indexCmd) Run(args []string) {
byId := *cmd.byId
byMatches := *cmd.matches
sources, context, path := preprocessArgsByToggle(args, byMatches || byId)
exitWithError(context.OpenDB())
defer context.CloseDB()

options := &drive.Options{
Sources: sources,
@@ -497,8 +495,6 @@ func (cmd *pullCmd) Flags(fs *flag.FlagSet) *flag.FlagSet {

func (cmd *pullCmd) Run(args []string) {
sources, context, path := preprocessArgsByToggle(args, (*cmd.byId || *cmd.matches))
exitWithError(context.OpenDB())
defer context.CloseDB()

excludes := drive.NonEmptyTrimmedStrings(strings.Split(*cmd.excludeOps, ",")...)
excludeCrudMask := drive.CrudAtoi(excludes...)
@@ -593,8 +589,6 @@ func (cmd *pushCmd) Run(args []string) {
cmd.pushMounted(args)
} else {
sources, context, path := preprocessArgs(args)
exitWithError(context.OpenDB())
defer context.CloseDB()

options := cmd.createPushOptions()
options.Path = path
@@ -627,8 +621,6 @@ func (cmd *touchCmd) Flags(fs *flag.FlagSet) *flag.FlagSet {

func (cmd *touchCmd) Run(args []string) {
sources, context, path := preprocessArgsByToggle(args, *cmd.matches || *cmd.byId)
exitWithError(context.OpenDB())
defer context.CloseDB()

opts := drive.Options{
Hidden: *cmd.hidden,
@@ -706,8 +698,6 @@ func (cmd *pushCmd) pushMounted(args []string) {

rest = drive.NonEmptyStrings(rest...)
context, path := discoverContext(contextArgs)
exitWithError(context.OpenDB())
defer context.CloseDB()

contextAbsPath, err := filepath.Abs(path)
exitWithError(err)
@@ -787,8 +777,6 @@ func (cmd *diffCmd) Flags(fs *flag.FlagSet) *flag.FlagSet {

func (cmd *diffCmd) Run(args []string) {
sources, context, path := preprocessArgs(args)
exitWithError(context.OpenDB())
defer context.CloseDB()

exitWithError(drive.New(context, &drive.Options{
Recursive: true,
@@ -866,8 +854,6 @@ func (cmd *deleteCmd) Flags(fs *flag.FlagSet) *flag.FlagSet {

func (cmd *deleteCmd) Run(args []string) {
sources, context, path := preprocessArgsByToggle(args, *cmd.matches || *cmd.byId)
exitWithError(context.OpenDB())
defer context.CloseDB()

opts := drive.Options{
Path: path,
@@ -899,8 +885,6 @@ func (cmd *trashCmd) Flags(fs *flag.FlagSet) *flag.FlagSet {

func (cmd *trashCmd) Run(args []string) {
sources, context, path := preprocessArgsByToggle(args, *cmd.matches || *cmd.byId)
exitWithError(context.OpenDB())
defer context.CloseDB()

opts := drive.Options{
Path: path,
@@ -928,8 +912,6 @@ func (cmd *newCmd) Flags(fs *flag.FlagSet) *flag.FlagSet {

func (cmd *newCmd) Run(args []string) {
sources, context, path := preprocessArgs(args)
exitWithError(context.OpenDB())
defer context.CloseDB()

opts := drive.Options{
Path: path,
@@ -975,8 +957,6 @@ func (cmd *copyCmd) Run(args []string) {
dest := args[end]

sources, context, path := preprocessArgsByToggle(args, *cmd.byId)
exitWithError(context.OpenDB())
defer context.CloseDB()

// Unshift by the end path
sources = sources[:len(sources)-1]
@@ -1011,8 +991,6 @@ func (cmd *untrashCmd) Flags(fs *flag.FlagSet) *flag.FlagSet {

func (cmd *untrashCmd) Run(args []string) {
sources, context, path := preprocessArgsByToggle(args, *cmd.byId || *cmd.matches)
exitWithError(context.OpenDB())
defer context.CloseDB()

opts := drive.Options{
Path: path,
@@ -1091,8 +1069,6 @@ func (cmd *moveCmd) Run(args []string) {
exitWithError(fmt.Errorf("move: expecting a path or more"))
}
sources, context, path := preprocessArgsByToggle(args, *cmd.byId)
exitWithError(context.OpenDB())
defer context.CloseDB()

// Unshift by the end path
sources = sources[:len(sources)-1]
@@ -1130,8 +1106,6 @@ func (cmd *renameCmd) Run(args []string) {
}
rest, last := args[:argc-1], args[argc-1]
sources, context, path := preprocessArgsByToggle(rest, *cmd.byId)
exitWithError(context.OpenDB())
defer context.CloseDB()

sources = append(sources, last)
exitWithError(drive.New(context, &drive.Options{
76 changes: 56 additions & 20 deletions config/config.go
Original file line number Diff line number Diff line change
@@ -33,6 +33,7 @@ var (

ErrNoDriveContext = errors.New("no drive context found; run `drive init` or go into one of the directories (sub directories) that you performed `drive init`")
ErrDerefNilIndex = errors.New("cannot dereference a nil index")
ErrDerefNilDB = errors.New("cannot dereference a nil db")
ErrEmptyFileIdForIndex = errors.New("fileId for index must be non-empty")
ErrNoSuchDbKey = errors.New("no such db key exists")
ErrNoSuchDbBucket = errors.New("no such bucket exists")
@@ -52,7 +53,6 @@ type Context struct {
ClientSecret string `json:"client_secret"`
RefreshToken string `json:"refresh_token"`
AbsPath string `json:"-"`
DB *bolt.DB `json:"-"`
}

type Index struct {
@@ -111,9 +111,16 @@ func (c *Context) DeserializeIndex(key string) (*Index, error) {
return nil, creationErr
}

db, err := c.OpenDB()
if err != nil {
return nil, err
}

defer db.Close()

var data []byte

err := c.DB.View(func(tx *bolt.Tx) error {
err = db.View(func(tx *bolt.Tx) error {
bucket := tx.Bucket(byteify(IndicesKey))
if bucket == nil {
return ErrNoSuchDbBucket
@@ -143,12 +150,19 @@ func (c *Context) ListKeys(dir, bucketName string) (chan string, error) {
return keysChan, creationErr
}

db, err := c.OpenDB()
if err != nil {
close(keysChan)
return keysChan, err
}

go func() {
defer func() {
db.Close()
close(keysChan)
}()

c.DB.View(func(tx *bolt.Tx) error {
db.View(func(tx *bolt.Tx) error {
bucket := tx.Bucket(byteify(bucketName))
if bucket == nil {
return ErrNoSuchDbBucket
@@ -172,7 +186,13 @@ func (c *Context) PopIndicesKey(key string) error {
}

func (c *Context) popDbKey(bucketName, key string) error {
return c.DB.Update(func(tx *bolt.Tx) error {
db, err := c.OpenDB()
if err != nil {
return err
}
defer db.Close()

return db.Update(func(tx *bolt.Tx) error {
bucket, err := tx.CreateBucketIfNotExists(byteify(IndicesKey))
if err != nil {
return err
@@ -193,7 +213,13 @@ func (c *Context) RemoveIndex(index *Index, p string) error {
return ErrEmptyFileIdForIndex
}

return c.DB.Update(func(tx *bolt.Tx) error {
db, err := c.OpenDB()
if err != nil {
return err
}
defer db.Close()

return db.Update(func(tx *bolt.Tx) error {
bucket, err := tx.CreateBucketIfNotExists(byteify(IndicesKey))
if err != nil {
return err
@@ -206,7 +232,13 @@ func (c *Context) RemoveIndex(index *Index, p string) error {
}

func (c *Context) CreateIndicesBucket() error {
return c.DB.Update(func(tx *bolt.Tx) error {
db, err := c.OpenDB()
if err != nil {
return err
}
defer db.Close()

return db.Update(func(tx *bolt.Tx) error {
bucket, err := tx.CreateBucketIfNotExists(byteify(IndicesKey))
if err != nil {
return err
@@ -220,11 +252,19 @@ func (c *Context) CreateIndicesBucket() error {

func (c *Context) SerializeIndex(index *Index) (err error) {
var data []byte
var db *bolt.DB

if data, err = json.Marshal(index); err != nil {
return
}

return c.DB.Update(func(tx *bolt.Tx) error {
db, err = c.OpenDB()
if err != nil {
return err
}
defer db.Close()

return db.Update(func(tx *bolt.Tx) error {
bucket, err := tx.CreateBucketIfNotExists(byteify(IndicesKey))
if err != nil {
return err
@@ -268,23 +308,19 @@ func (c *Context) DeInitialize(prompter func(...interface{}) bool, returnOnAnyEr
return nil
}

func (c *Context) OpenDB() error {
func (c *Context) OpenDB() (db *bolt.DB, err error) {
dbPath := DbSuffixedPath(c.AbsPathOf(""))
db, err := bolt.Open(dbPath, O_RWForAll, nil)
if err != nil {
return err
}
db, err = bolt.Open(dbPath, O_RWForAll, nil)

c.DB = db
return nil
}
if err != nil {
return db, err
}

func (c *Context) CloseDB() error {
if c.DB == nil {
return errors.New("nil dereference of db")
}
if db == nil {
return db, ErrDerefNilDB
}

return c.DB.Close()
return db, nil
}

// Discovers the gd directory, if no gd directory or credentials