forked from TrueCloudLab/restic
Merge pull request #916 from restic/fix-915
Ignore empty lines in excludes file, allow multiple files
This commit is contained in:
commit
76f6a9e597
3 changed files with 30 additions and 13 deletions
|
@ -44,7 +44,7 @@ type BackupOptions struct {
|
||||||
Parent string
|
Parent string
|
||||||
Force bool
|
Force bool
|
||||||
Excludes []string
|
Excludes []string
|
||||||
ExcludeFile string
|
ExcludeFiles []string
|
||||||
ExcludeOtherFS bool
|
ExcludeOtherFS bool
|
||||||
Stdin bool
|
Stdin bool
|
||||||
StdinFilename string
|
StdinFilename string
|
||||||
|
@ -68,7 +68,7 @@ func init() {
|
||||||
f.StringVar(&backupOptions.Parent, "parent", "", "use this parent snapshot (default: last snapshot in the repo that has the same target files/directories)")
|
f.StringVar(&backupOptions.Parent, "parent", "", "use this parent snapshot (default: last snapshot in the repo that has the same target files/directories)")
|
||||||
f.BoolVarP(&backupOptions.Force, "force", "f", false, `force re-reading the target files/directories (overrides the "parent" flag)`)
|
f.BoolVarP(&backupOptions.Force, "force", "f", false, `force re-reading the target files/directories (overrides the "parent" flag)`)
|
||||||
f.StringSliceVarP(&backupOptions.Excludes, "exclude", "e", nil, "exclude a `pattern` (can be specified multiple times)")
|
f.StringSliceVarP(&backupOptions.Excludes, "exclude", "e", nil, "exclude a `pattern` (can be specified multiple times)")
|
||||||
f.StringVar(&backupOptions.ExcludeFile, "exclude-file", "", "read exclude patterns from a file")
|
f.StringSliceVar(&backupOptions.ExcludeFiles, "exclude-file", nil, "read exclude patterns from a `file` (can be specified multiple times)")
|
||||||
f.BoolVarP(&backupOptions.ExcludeOtherFS, "one-file-system", "x", false, "exclude other file systems")
|
f.BoolVarP(&backupOptions.ExcludeOtherFS, "one-file-system", "x", false, "exclude other file systems")
|
||||||
f.BoolVar(&backupOptions.Stdin, "stdin", false, "read backup from stdin")
|
f.BoolVar(&backupOptions.Stdin, "stdin", false, "read backup from stdin")
|
||||||
f.StringVar(&backupOptions.StdinFilename, "stdin-filename", "stdin", "file name to use when reading from stdin")
|
f.StringVar(&backupOptions.StdinFilename, "stdin-filename", "stdin", "file name to use when reading from stdin")
|
||||||
|
@ -406,17 +406,28 @@ func runBackup(opts BackupOptions, gopts GlobalOptions, args []string) error {
|
||||||
Verbosef("scan %v\n", target)
|
Verbosef("scan %v\n", target)
|
||||||
|
|
||||||
// add patterns from file
|
// add patterns from file
|
||||||
if opts.ExcludeFile != "" {
|
if len(opts.ExcludeFiles) > 0 {
|
||||||
file, err := fs.Open(opts.ExcludeFile)
|
for _, filename := range opts.ExcludeFiles {
|
||||||
if err != nil {
|
file, err := fs.Open(filename)
|
||||||
Warnf("error reading exclude patterns: %v", err)
|
if err != nil {
|
||||||
return nil
|
Warnf("error reading exclude patterns: %v", err)
|
||||||
}
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
scanner := bufio.NewScanner(file)
|
||||||
|
for scanner.Scan() {
|
||||||
|
line := strings.TrimSpace(scanner.Text())
|
||||||
|
|
||||||
|
// ignore empty lines
|
||||||
|
if line == "" {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
// strip comments
|
||||||
|
if strings.HasPrefix(line, "#") {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
scanner := bufio.NewScanner(file)
|
|
||||||
for scanner.Scan() {
|
|
||||||
line := scanner.Text()
|
|
||||||
if !strings.HasPrefix(line, "#") {
|
|
||||||
line = os.ExpandEnv(line)
|
line = os.ExpandEnv(line)
|
||||||
opts.Excludes = append(opts.Excludes, line)
|
opts.Excludes = append(opts.Excludes, line)
|
||||||
}
|
}
|
||||||
|
|
|
@ -100,9 +100,14 @@ func match(patterns, strs []string) (matched bool, err error) {
|
||||||
return false, nil
|
return false, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// List returns true if str matches one of the patterns.
|
// List returns true if str matches one of the patterns. Empty patterns are
|
||||||
|
// ignored.
|
||||||
func List(patterns []string, str string) (matched bool, err error) {
|
func List(patterns []string, str string) (matched bool, err error) {
|
||||||
for _, pat := range patterns {
|
for _, pat := range patterns {
|
||||||
|
if pat == "" {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
matched, err = Match(pat, str)
|
matched, err = Match(pat, str)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
|
|
|
@ -152,6 +152,7 @@ var filterListTests = []struct {
|
||||||
{[]string{"?", "x"}, "/foo/bar/x", true},
|
{[]string{"?", "x"}, "/foo/bar/x", true},
|
||||||
{[]string{"/*/*/bar/test.*"}, "/foo/bar/test.go", false},
|
{[]string{"/*/*/bar/test.*"}, "/foo/bar/test.go", false},
|
||||||
{[]string{"/*/*/bar/test.*", "*.go"}, "/foo/bar/test.go", true},
|
{[]string{"/*/*/bar/test.*", "*.go"}, "/foo/bar/test.go", true},
|
||||||
|
{[]string{"", "*.c"}, "/foo/bar/test.go", false},
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestMatchList(t *testing.T) {
|
func TestMatchList(t *testing.T) {
|
||||||
|
|
Loading…
Reference in a new issue