C# 如何确保写入的所有文件都位于给定路径下(防止目录访问)

C# 如何确保写入的所有文件都位于给定路径下(防止目录访问),c#,directory,parent,C#,Directory,Parent,我们有一个C#应用程序,它将文件写入一个可配置的位置。文件集(和相对路径)在运行时确定 我们希望确保它不能在配置的位置之外写入文件 例如,配置的位置可能是c:\Stuff\Export,程序在c:\Stuff\Important下写入任何内容都是错误的 事实上,我认为我们可以通过两种方式实现这一目标: 1) 断言没有一个相对路径(要写入的文件)指定“父目录”(通常为“./”)-System。Path不指定“父目录”路径组件(就像它用于路径分离,即System.Path.PathSeparator

我们有一个C#应用程序,它将文件写入一个可配置的位置。文件集(和相对路径)在运行时确定

我们希望确保它不能在配置的位置之外写入文件

例如,配置的位置可能是c:\Stuff\Export,程序在c:\Stuff\Important下写入任何内容都是错误的

事实上,我认为我们可以通过两种方式实现这一目标: 1) 断言没有一个相对路径(要写入的文件)指定“父目录”(通常为“./”)-System。Path不指定“父目录”路径组件(就像它用于路径分离,即System.Path.PathSeparator)。我在检查字符串中的“./”时感到有点笨拙

2) 断言生成的所有最终绝对路径(通过将输出位置与文件相对路径相结合)都是相对于输出位置的,即位于输出位置下方。但我不确定该怎么做

Example usage:
Output directory: c:\Stuff\Export
Output path 1: "foo\bar\important.xls"
Output path 2: "foo\boo\something.csv"
Output path 3: "../../io.sys"

Expected final files
1. c:\Stuff\Export\foo\bar\important.xls
2. c:\Stuff\Export\foo\boo\something.csv
3. Should throw exception
如果在这两个路径上创建实例,则其属性应返回完全限定的规范路径。因此,如果你只是对你想要比较的两个方面都这样做,你可以这样做:

if (chosenDirectory.FullName != configuredDirectory.FullName)
{
    throw new InvalidOperationException(
        String.Format("Invalid path {0}.", chosenDirectory));
}
由于
FullName
只是一个字符串,您可以在路径上进行常规字符串比较,如:

if (!chosenDirectory.FullName.StartsWith(configuredDirectory.FullName,
    StringComparison.InvariantCultureIgnoreCase))
{
    throw new InvalidOperationException(
        String.Format("Invalid path {0}.", chosenDirectory));
}
如果不希望在配置的目录中允许子目录,也可以使用该属性并将其
全名
与所选目录进行比较:

if (!chosenDirectory.Parent.FullName.Equals(configuredDirectory.FullName,
    StringComparison.InvariantCultureIgnoreCase))
{
    throw new InvalidOperationException(
        String.Format("Invalid path {0}.", chosenDirectory));
}

下面是一个快速解决方案:

string chroot = @"C:\root\child";
string requestedPath = @"..\";
string path = Path.GetFullPath(Path.Combine(chroot, requestedPath));
if (!path.StartsWith(chroot, StringComparison.Ordinal))
    throw new Exception("Oops, caught ya!");
编辑:
如果您想知道给定路径是否为有效目录:
directory.Exists(path)

请不要在标题前加上“C”。我们在上使用标记来实现此目的。您能给出一个目录示例来编写文件和文件输入吗?这可能会有所帮助-