Better throwing on long path in filesystems
This commit is contained in:
@@ -304,7 +304,13 @@ namespace Umbraco.Core.IO
|
||||
// permissions to reach that path, but it may nevertheless be outside of
|
||||
// our root path, due to relative segments, so better check
|
||||
if (IOHelper.PathStartsWith(path, _rootPath, Path.DirectorySeparatorChar))
|
||||
{
|
||||
// this says that 4.7.2 supports long paths - but Windows does not
|
||||
// https://docs.microsoft.com/en-us/dotnet/api/system.io.pathtoolongexception?view=netframework-4.7.2
|
||||
if (path.Length > 260)
|
||||
throw new PathTooLongException($"Path {path} is too long.");
|
||||
return path;
|
||||
}
|
||||
|
||||
// nothing prevents us to reach the file, security-wise, yet it is outside
|
||||
// this filesystem's root - throw
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using NUnit.Framework;
|
||||
@@ -44,6 +42,34 @@ namespace Umbraco.Tests.IO
|
||||
return "/Media/" + path;
|
||||
}
|
||||
|
||||
private string Repeat(string pattern, int count)
|
||||
{
|
||||
var text = new StringBuilder();
|
||||
for (var i = 0; i < count; i++)
|
||||
text.Append(pattern);
|
||||
return text.ToString();
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void SaveFileTest()
|
||||
{
|
||||
var basePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "FileSysTests");
|
||||
|
||||
using (var ms = new MemoryStream(Encoding.UTF8.GetBytes("foo")))
|
||||
_fileSystem.AddFile("sub/f3.txt", ms);
|
||||
|
||||
Assert.IsTrue(File.Exists(Path.Combine(basePath, "sub/f3.txt")));
|
||||
|
||||
var path = Repeat("bah/bah/", 50);
|
||||
Assert.Less(260, path.Length);
|
||||
|
||||
Assert.Throws<PathTooLongException>(() =>
|
||||
{
|
||||
using (var ms = new MemoryStream(Encoding.UTF8.GetBytes("foo")))
|
||||
_fileSystem.AddFile(path + "f3.txt", ms);
|
||||
});
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void GetFullPathTest()
|
||||
{
|
||||
@@ -60,14 +86,31 @@ namespace Umbraco.Tests.IO
|
||||
// - does properly normalize separators
|
||||
// - does throw on invalid paths
|
||||
|
||||
// works
|
||||
var path = _fileSystem.GetFullPath("foo.tmp");
|
||||
Assert.AreEqual(Path.Combine(basePath, @"foo.tmp"), path);
|
||||
|
||||
// a very long relative path, which ends up being a short path, works
|
||||
path = Repeat("bah/../", 50);
|
||||
Assert.Less(260, path.Length);
|
||||
path = _fileSystem.GetFullPath(path + "foo.tmp");
|
||||
Assert.AreEqual(Path.Combine(basePath, @"foo.tmp"), path);
|
||||
|
||||
// works too
|
||||
path = _fileSystem.GetFullPath("foo/bar.tmp");
|
||||
Assert.AreEqual(Path.Combine(basePath, @"foo\bar.tmp"), path);
|
||||
|
||||
// that path is invalid as it would be outside the root directory
|
||||
Assert.Throws<FileSecurityException>(() => _fileSystem.GetFullPath("../../foo.tmp"));
|
||||
|
||||
// a very long path, which ends up being very long, works
|
||||
path = Repeat("bah/bah/", 50);
|
||||
Assert.Less(260, path.Length);
|
||||
Assert.Throws<PathTooLongException>(() =>
|
||||
{
|
||||
path = _fileSystem.GetFullPath(path + "foo.tmp");
|
||||
Assert.Less(260, path.Length); // gets a >260 path and it's fine (but Windows will not like it)
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user