gpt4 book ai didi

.net - 如何从 .NET 应用程序中的 FTP 协议(protocol)获取目录文件大小

转载 作者:可可西里 更新时间:2023-11-01 09:31:09 26 4
gpt4 key购买 nike

我目前正在制作一个小型 .NET 控制台应用程序,用于将我的一些文件自动备份到我的服务器上。我遇到的问题是我这边遇到了一些恶劣的天气,导致了一些电力和网络中断。在此期间,我注意到我的大部分文件没有通过或损坏了。我想知道是否有办法获取另一端文件夹的大小,并查看文件名、文件数和总目录大小是否匹配。我已经尝试使用 WinSCP 和 NcFTP 作为传输文件的方法,但我还没有看到任何有关获得适当文件大小的信息。

这几乎是一个窗口到窗口的传输,所以如果有一个命令行参数可以通过 FTP 客户端返回一个大小,那就太好了。

最佳答案

没有标准的 FTP 命令来检索目录大小。

您必须递归地迭代所有子目录和文件并对大小求和。

这对于 .NET framework/FtpWebRequest 并不容易,因为它不支持 MLSD 命令,这是唯一可移植的检索具有文件属性的目录列表的方法在 FTP 协议(protocol)中。

您所能做的就是使用 LIST 命令 (ListDirectoryDe​​tails) 并尝试解析特定于服务器的列表。许多 FTP 服务器使用 *nix 风格的列表。但是许多服务器使用不同的格式。以下示例使用 *nix 格式:

static long CalculateFtpDirectorySize(string url, NetworkCredential credentials)
{
FtpWebRequest listRequest = (FtpWebRequest)WebRequest.Create(url);
listRequest.Method = WebRequestMethods.Ftp.ListDirectoryDetails;
listRequest.Credentials = credentials;

List<string> lines = new List<string>();

using (var listResponse = (FtpWebResponse)listRequest.GetResponse())
using (Stream listStream = listResponse.GetResponseStream())
using (StreamReader listReader = new StreamReader(listStream))
{
while (!listReader.EndOfStream)
{
lines.Add(listReader.ReadLine());
}
}

long result = 0;
foreach (string line in lines)
{
string[] tokens =
line.Split(new[] { ' ' }, 9, StringSplitOptions.RemoveEmptyEntries);
string name = tokens[8];
string permissions = tokens[0];

string fileUrl = url + name;

if (permissions[0] == 'd')
{
result += CalculateFtpDirectorySize(fileUrl + "/", credentials);
}
else
{
result += long.Parse(tokens[4]);
}
}

return result;
}

像这样使用它:

var credentials = new NetworkCredential("username", "password");
long size = CalculateFtpDirectorySize("ftp://ftp.example.com/", credentials);

如果您的服务器使用 DOS/Windows 列表格式,请参阅 C# class to parse WebRequestMethods.Ftp.ListDirectoryDetails FTP response


或者,您可以使用支持现代 MLSD 命令的第 3 方 FTP 客户端实现。

例如WinSCP .NET assembly支持这一点。

它甚至还有方便的 Session.EnumerateRemoteFiles方法,这使得计算目录大小变得容易:

var opts = EnumerationOptions.AllDirectories;
var files = session.EnumerateRemoteFiles("/", null, opts);
long size = files.Select(fileInfo => fileInfo.Length).Sum();

完整的代码如下:

SessionOptions sessionOptions = new SessionOptions
{
Protocol = Protocol.Ftp,
HostName = "ftp.example.com",
UserName = "username",
Password = "password",
};

using (Session session = new Session())
{
// Connect
session.Open(sessionOptions);

var opts = EnumerationOptions.AllDirectories;
var files = session.EnumerateRemoteFiles("/", null, opts);
long size = files.Select(fileInfo => fileInfo.Length).Sum();
}

(我是 WinSCP 的作者)

关于.net - 如何从 .NET 应用程序中的 FTP 协议(protocol)获取目录文件大小,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7891677/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com