diff --git a/backend/rest/rest.go b/backend/rest/rest.go index 445a41371..ecfcc3198 100644 --- a/backend/rest/rest.go +++ b/backend/rest/rest.go @@ -56,7 +56,7 @@ func (rb *RestBlob) Close() error { // Finalize moves the data blob to the final location for type and name. func (rb *RestBlob) Finalize(t backend.Type, name string) error { if rb.final { - return errors.New("already finalized") + return errors.New("blob already finalized") } rb.final = true @@ -65,8 +65,8 @@ func (rb *RestBlob) Finalize(t backend.Type, name string) error { client := *rb.b.client resp, err := client.Post(restPath(rb.b.url, t, name), "binary/octet-stream", rb.buf) defer resp.Body.Close() - if resp.StatusCode == 409 { - err = errors.New("already exists") + if resp.StatusCode != 200 { + err = errors.New("blob not saved") } rb.b.connChan <- struct{}{} rb.buf.Reset() @@ -115,8 +115,11 @@ func (b *Rest) Create() (backend.Blob, error) { // Get returns an io.ReadCloser for the Blob with the given name of type t. func (b *Rest) Get(t backend.Type, name string) (io.ReadCloser, error) { resp, err := b.client.Get(restPath(b.url, t, name)) - if err == nil && resp.StatusCode != 200 { - err = errors.New("blob not found") + if err != nil { + return nil, err + } + if resp.StatusCode != 200 { + return nil, errors.New("blob not found") } return resp.Body, err } @@ -128,34 +131,34 @@ func (b *Rest) GetReader(t backend.Type, name string, offset, length uint) (io.R if err != nil { return nil, err } - req.Header.Add("Range", fmt.Sprintf("bytes=%d-%d", offset, offset+length)) - client := *b.client - resp, errg := client.Do(req) - if errg != nil { - return nil, errg + resp, err := client.Do(req) + if err != nil { + return nil, err + } + if resp.StatusCode != 206 { + return nil, errors.New("blob not found") } - return backend.LimitReadCloser(resp.Body, int64(length)), nil } // Test a boolean value whether a Blob with the name and type exists. func (b *Rest) Test(t backend.Type, name string) (bool, error) { - found := false - req, err := http.NewRequest("HEAD", restPath(b.url, t, name), nil) if err != nil { - return found, err + return false, err } - client := *b.client - resp, errh := client.Do(req) + resp, err := client.Do(req) defer resp.Body.Close() - if resp.StatusCode == 200 { - found = true + if err != nil { + return false, err } - return found, errh + if resp.StatusCode != 200 { + return false, nil + } + return true, nil } // Remove removes a Blob with type t and name. @@ -164,11 +167,10 @@ func (b *Rest) Remove(t backend.Type, name string) error { if err != nil { return err } - client := *b.client - resp, errd := client.Do(req) + resp, err := client.Do(req) defer resp.Body.Close() - return errd + return err } // Close the backend @@ -190,8 +192,8 @@ func (b *Rest) List(t backend.Type, done <-chan struct{}) <-chan string { return ch } - data, errd := ioutil.ReadAll(resp.Body) - if errd != nil { + data, err := ioutil.ReadAll(resp.Body) + if err != nil { close(ch) return ch } diff --git a/backend/rest_test.go b/backend/rest_test.go index 66404b8e3..75e5ec539 100644 --- a/backend/rest_test.go +++ b/backend/rest_test.go @@ -2,6 +2,7 @@ package backend_test import ( "encoding/json" + "fmt" "io/ioutil" "net/http" "net/http/httptest" @@ -21,7 +22,6 @@ func TestRestBackend(t *testing.T) { // Initializing a temporary direcory for the rest backend. path, _ := ioutil.TempDir("", "restic-repository-") defer os.RemoveAll(path) - dirs := []string{ path, filepath.Join(path, string(backend.Data)), @@ -30,7 +30,6 @@ func TestRestBackend(t *testing.T) { filepath.Join(path, string(backend.Lock)), filepath.Join(path, string(backend.Key)), } - for _, d := range dirs { os.MkdirAll(d, backend.Modes.Dir) } @@ -42,18 +41,19 @@ func TestRestBackend(t *testing.T) { file := filepath.Join(path, "config") if _, err := os.Stat(file); err != nil { http.Error(w, "404 repository not found", 404) + return } }).Methods("HEAD") // Get the configuration. r.HandleFunc("/config", func(w http.ResponseWriter, r *http.Request) { file := filepath.Join(path, "config") - if _, err := os.Stat(file); err == nil { - bytes, _ := ioutil.ReadFile(file) - w.Write(bytes) - } else { + if _, err := os.Stat(file); err != nil { http.Error(w, "404 repository not found", 404) + return } + bytes, _ := ioutil.ReadFile(file) + w.Write(bytes) }).Methods("GET") // Save the configuration. @@ -61,11 +61,10 @@ func TestRestBackend(t *testing.T) { file := filepath.Join(path, "config") if _, err := os.Stat(file); err == nil { http.Error(w, "409 repository already initialized", 409) - } else { - bytes, _ := ioutil.ReadAll(r.Body) - ioutil.WriteFile(file, bytes, 0600) - + return } + bytes, _ := ioutil.ReadAll(r.Body) + ioutil.WriteFile(file, bytes, 0600) }).Methods("POST") // List the blobs of a given type. @@ -119,11 +118,13 @@ func TestRestBackend(t *testing.T) { return } blob := filepath.Join(path, string(blobType), blobID.String()) - if file, err := os.Open(blob); err == nil { - http.ServeContent(w, r, "", time.Unix(0, 0), file) - } else { + file, err := os.Open(blob) + defer file.Close() + if err != nil { http.Error(w, "404 blob not found", 404) + return } + http.ServeContent(w, r, "", time.Unix(0, 0), file) }).Methods("GET") // Save a blob of a given type. @@ -142,10 +143,10 @@ func TestRestBackend(t *testing.T) { blob := filepath.Join(path, string(blobType), blobID.String()) if _, err := os.Stat(blob); err == nil { http.Error(w, "409 blob already uploaded", 409) - } else { - bytes, _ := ioutil.ReadAll(r.Body) - ioutil.WriteFile(blob, bytes, 0600) + return } + bytes, _ := ioutil.ReadAll(r.Body) + ioutil.WriteFile(blob, bytes, 0600) }).Methods("POST") // Delete a blob of a given type. @@ -162,17 +163,20 @@ func TestRestBackend(t *testing.T) { return } blob := filepath.Join(path, string(blobType), blobID.String()) - if _, err := os.Stat(blob); err == nil { - os.Remove(blob) - } else { + if _, err := os.Stat(blob); err != nil { http.Error(w, "404 blob not found", 404) + return + } + if err := os.Remove(blob); err != nil { + fmt.Println(err.Error()) + http.Error(w, "500 internal server error", 500) + return } }).Methods("DELETE") // Start the server and launch the tests. s := httptest.NewServer(r) defer s.Close() - u, _ := url.Parse(s.URL) backend, _ := rest.Open(u)