2
2
mirror of https://github.com/octoleo/restic.git synced 2024-11-02 19:49:44 +00:00

layout: Allow passing in a default layout

This commit is contained in:
Alexander Neumann 2017-04-02 19:53:55 +02:00
parent f7c4b3a922
commit 54465c92cc
2 changed files with 22 additions and 12 deletions

View File

@ -108,6 +108,10 @@ func hasSubdirBackendFile(fs Filesystem, dir string) (bool, error) {
return false, nil return false, nil
} }
// ErrLayoutDetectionFailed is returned by DetectLayout() when the layout
// cannot be detected automatically.
var ErrLayoutDetectionFailed = errors.New("auto-detecting the filesystem layout failed")
// DetectLayout tries to find out which layout is used in a local (or sftp) // DetectLayout tries to find out which layout is used in a local (or sftp)
// filesystem at the given path. If repo is nil, an instance of LocalFilesystem // filesystem at the given path. If repo is nil, an instance of LocalFilesystem
// is used. // is used.
@ -164,12 +168,12 @@ func DetectLayout(repo Filesystem, dir string) (Layout, error) {
}, nil }, nil
} }
return nil, errors.New("auto-detecting the filesystem layout failed") return nil, ErrLayoutDetectionFailed
} }
// ParseLayout parses the config string and returns a Layout. When layout is // ParseLayout parses the config string and returns a Layout. When layout is
// the empty string, DetectLayout is used. // the empty string, DetectLayout is used. If that fails, defaultLayout is used.
func ParseLayout(repo Filesystem, layout, path string) (l Layout, err error) { func ParseLayout(repo Filesystem, layout, defaultLayout, path string) (l Layout, err error) {
debug.Log("parse layout string %q for backend at %v", layout, path) debug.Log("parse layout string %q for backend at %v", layout, path)
switch layout { switch layout {
case "default": case "default":
@ -188,7 +192,12 @@ func ParseLayout(repo Filesystem, layout, path string) (l Layout, err error) {
Join: repo.Join, Join: repo.Join,
} }
case "": case "":
return DetectLayout(repo, path) l, err = DetectLayout(repo, path)
// use the default layout if auto detection failed
if errors.Cause(err) == ErrLayoutDetectionFailed && defaultLayout != "" {
return ParseLayout(repo, defaultLayout, "", path)
}
default: default:
return nil, errors.Errorf("unknown backend layout string %q, may be one of default/cloud/s3", layout) return nil, errors.Errorf("unknown backend layout string %q, may be one of default/cloud/s3", layout)
} }

View File

@ -258,20 +258,21 @@ func TestParseLayout(t *testing.T) {
defer cleanup() defer cleanup()
var tests = []struct { var tests = []struct {
layoutName string layoutName string
want string defaultLayoutName string
want string
}{ }{
{"default", "*backend.DefaultLayout"}, {"default", "", "*backend.DefaultLayout"},
{"cloud", "*backend.CloudLayout"}, {"cloud", "", "*backend.CloudLayout"},
{"s3", "*backend.S3Layout"}, {"s3", "", "*backend.S3Layout"},
{"", "*backend.CloudLayout"}, {"", "", "*backend.CloudLayout"},
} }
SetupTarTestFixture(t, path, filepath.Join("testdata", "repo-layout-cloud.tar.gz")) SetupTarTestFixture(t, path, filepath.Join("testdata", "repo-layout-cloud.tar.gz"))
for _, test := range tests { for _, test := range tests {
t.Run(test.layoutName, func(t *testing.T) { t.Run(test.layoutName, func(t *testing.T) {
layout, err := ParseLayout(&LocalFilesystem{}, test.layoutName, filepath.Join(path, "repo")) layout, err := ParseLayout(&LocalFilesystem{}, test.layoutName, test.defaultLayoutName, filepath.Join(path, "repo"))
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@ -303,7 +304,7 @@ func TestParseLayoutInvalid(t *testing.T) {
for _, name := range invalidNames { for _, name := range invalidNames {
t.Run(name, func(t *testing.T) { t.Run(name, func(t *testing.T) {
layout, err := ParseLayout(nil, name, path) layout, err := ParseLayout(nil, name, "", path)
if err == nil { if err == nil {
t.Fatalf("expected error not found for layout name %v, layout is %v", name, layout) t.Fatalf("expected error not found for layout name %v, layout is %v", name, layout)
} }