From cfc8911b77d2080a35046328721a35dbe5e7209e Mon Sep 17 00:00:00 2001 From: Jan-Lukas Else Date: Mon, 20 Apr 2020 20:53:45 +0200 Subject: [PATCH] Use mutex for file operations --- config.go | 2 ++ go.mod | 3 ++- go.sum | 4 ++++ storage.go | 26 +++++++++++++++++++------- 4 files changed, 27 insertions(+), 8 deletions(-) diff --git a/config.go b/config.go index d4d8b4d..a787658 100644 --- a/config.go +++ b/config.go @@ -6,6 +6,7 @@ import ( "log" "os" "strings" + "sync" ) var ( @@ -152,6 +153,7 @@ func initConfig() (err error) { password: cfg.Git.Password, name: cfg.Git.AuthorName, email: cfg.Git.AuthorEmail, + lock: &sync.Mutex{}, } } return nil diff --git a/go.mod b/go.mod index 36653ac..900e63d 100644 --- a/go.mod +++ b/go.mod @@ -10,8 +10,9 @@ require ( github.com/google/go-cmp v0.4.0 // indirect github.com/pkg/errors v0.9.1 // indirect github.com/stretchr/testify v1.5.1 // indirect - golang.org/x/crypto v0.0.0-20200323165209-0ec3e9974c59 // indirect + golang.org/x/crypto v0.0.0-20200420104511-884d27f42877 // indirect golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e // indirect + golang.org/x/sys v0.0.0-20200420163511-1957bb5e6d1f // indirect gopkg.in/yaml.v2 v2.2.8 willnorris.com/go/webmention v0.0.0-20200126231626-5a55fff6bf71 ) diff --git a/go.sum b/go.sum index cd58e09..98e7587 100644 --- a/go.sum +++ b/go.sum @@ -70,6 +70,8 @@ golang.org/x/crypto v0.0.0-20200302210943-78000ba7a073 h1:xMPOj6Pz6UipU1wXLkrtqp golang.org/x/crypto v0.0.0-20200302210943-78000ba7a073/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20200323165209-0ec3e9974c59 h1:3zb4D3T4G8jdExgVU/95+vQXfpEPiMdCaZgmGVxjNHM= golang.org/x/crypto v0.0.0-20200323165209-0ec3e9974c59/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20200420104511-884d27f42877 h1:IhZPbxNd1UjBCaD5AfpSSbJTRlp+ZSuyuH5uoksNS04= +golang.org/x/crypto v0.0.0-20200420104511-884d27f42877/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/net v0.0.0-20180218175443-cbe0f9307d01/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180911220305-26e67e76b6c3/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= @@ -84,6 +86,8 @@ golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527 h1:uYVVQ9WP/Ds2ROhcaGPeIdVq0 golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd h1:xhmwyvizuTgC2qz7ZlMluP20uW+C3Rm0FD/WLDX8884= golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200420163511-1957bb5e6d1f h1:gWF768j/LaZugp8dyS4UwsslYCYz9XgFxvlgsn0n9H8= +golang.org/x/sys v0.0.0-20200420163511-1957bb5e6d1f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2 h1:tW2bmiBqwgJj/UpqtC8EpXEZVYOwU0yG4iWbprSVAcs= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= diff --git a/storage.go b/storage.go index 1f95b1b..cefa621 100644 --- a/storage.go +++ b/storage.go @@ -8,6 +8,7 @@ import ( "io/ioutil" "os" "path" + "sync" "time" ) @@ -24,9 +25,10 @@ type Git struct { password string name string email string + lock *sync.Mutex } -func (g Git) init() (r *git.Repository, w *git.Worktree, err error) { +func (g *Git) init() (r *git.Repository, w *git.Worktree, err error) { // Open repo r, err = git.PlainOpen(g.filepath) if err == nil { @@ -72,11 +74,11 @@ func (g Git) init() (r *git.Repository, w *git.Worktree, err error) { return } -func (g Git) destroyRepo() { +func (g *Git) destroyRepo() { _ = os.RemoveAll(g.filepath) } -func (g Git) push(repository *git.Repository) error { +func (g *Git) push(repository *git.Repository) error { err := repository.Push(&git.PushOptions{ Auth: &gitHttp.BasicAuth{ Username: g.username, @@ -92,7 +94,9 @@ func (g Git) push(repository *git.Repository) error { } } -func (g Git) CreateFile(filepath string, file string, message string) (err error) { +func (g *Git) CreateFile(filepath string, file string, message string) (err error) { + g.lock.Lock() + defer g.lock.Unlock() _, _, err = g.init() if err != nil { err = errors.New("failed to initialize repo") @@ -102,11 +106,17 @@ func (g Git) CreateFile(filepath string, file string, message string) (err error if _, e := os.Stat(joinedPath); e == nil { return errors.New("file already exists") } else { - return g.UpdateFile(filepath, file, message) + return g.unsafeUpdateFile(filepath, file, message) } } -func (g Git) UpdateFile(filepath string, file string, message string) error { +func (g *Git) UpdateFile(filepath string, file string, message string) error { + g.lock.Lock() + defer g.lock.Unlock() + return g.unsafeUpdateFile(filepath, file, message) +} + +func (g *Git) unsafeUpdateFile(filepath string, file string, message string) error { repo, w, err := g.init() if err != nil { return errors.New("failed to initialize repo") @@ -137,7 +147,9 @@ func (g Git) UpdateFile(filepath string, file string, message string) error { return g.push(repo) } -func (g Git) DeleteFile(filepath string, message string) (err error) { +func (g *Git) DeleteFile(filepath string, message string) (err error) { + g.lock.Lock() + defer g.lock.Unlock() repo, w, err := g.init() if err != nil { return errors.New("failed to initialize repo")