mirror of https://github.com/restic/restic.git
Merge pull request #3691 from greatroar/tag-filenames
Sanitize tags when used as filenames by restic mount
This commit is contained in:
commit
b4dfab002a
|
@ -6,5 +6,10 @@ formatting of the time for a snapshot is now controlled using `--time-template`
|
|||
and supports subdirectories to for example group snapshots by year. Please
|
||||
refer to the help output of the `mount` command for further details.
|
||||
|
||||
Characters in tag names which are not allowed in a filename are replaced by
|
||||
underscores `_`. For example a tag `foo/bar` will result in a directory name
|
||||
of `foo_bar`.
|
||||
|
||||
https://github.com/restic/restic/issues/2907
|
||||
https://github.com/restic/restic/pull/2913
|
||||
https://github.com/restic/restic/pull/3691
|
||||
|
|
|
@ -97,6 +97,7 @@ func pathsFromSn(pathTemplate string, timeTemplate string, sn *restic.Snapshot)
|
|||
// needs special treatment: Rebuild the string builders
|
||||
newout := make([]strings.Builder, len(out)*len(sn.Tags))
|
||||
for i, tag := range sn.Tags {
|
||||
tag = filenameFromTag(tag)
|
||||
for j := range out {
|
||||
newout[i*len(out)+j].WriteString(out[j].String() + tag)
|
||||
}
|
||||
|
@ -139,6 +140,24 @@ func pathsFromSn(pathTemplate string, timeTemplate string, sn *restic.Snapshot)
|
|||
return paths, timeSuffix
|
||||
}
|
||||
|
||||
// Some tags are problematic when used as filenames:
|
||||
//
|
||||
// ""
|
||||
// ".", ".."
|
||||
// anything containing '/'
|
||||
//
|
||||
// Replace all special character by underscores "_", an empty tag is also represented as a underscore.
|
||||
func filenameFromTag(tag string) string {
|
||||
switch tag {
|
||||
case "", ".":
|
||||
return "_"
|
||||
case "..":
|
||||
return "__"
|
||||
}
|
||||
|
||||
return strings.ReplaceAll(tag, "/", "_")
|
||||
}
|
||||
|
||||
// determine static path prefix
|
||||
func staticPrefix(pathTemplate string) (prefix string) {
|
||||
inVerb := false
|
||||
|
|
|
@ -273,3 +273,19 @@ func TestMakeEmptyDirs(t *testing.T) {
|
|||
|
||||
verifyEntries(t, expNames, expLatest, sds.entries)
|
||||
}
|
||||
|
||||
func TestFilenameFromTag(t *testing.T) {
|
||||
for _, c := range []struct {
|
||||
tag, filename string
|
||||
}{
|
||||
{"", "_"},
|
||||
{".", "_"},
|
||||
{"..", "__"},
|
||||
{"%.", "%."},
|
||||
{"foo", "foo"},
|
||||
{"foo ", "foo "},
|
||||
{"foo/bar_baz", "foo_bar_baz"},
|
||||
} {
|
||||
test.Equals(t, c.filename, filenameFromTag(c.tag))
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue