首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >SSH.Net异步文件下载

SSH.Net异步文件下载
EN

Stack Overflow用户
提问于 2015-12-02 18:01:15
回答 1查看 11.3K关注 0票数 10

我正在尝试使用SSH.NET从SFTP服务器异步下载文件。如果我是同步的,它工作得很好,但是当我异步的时候,我得到的是空文件。这是我的代码:

代码语言:javascript
复制
var port = 22;
string host = "localhost";
string username = "user";
string password = "password";
string localPath = @"C:\temp";

using (var client = new SftpClient(host, port, username, password))
{
    client.Connect();
    var files = client.ListDirectory("");

    var tasks = new List<Task>();

    foreach (var file in files)
    {                        
        using (var saveFile = File.OpenWrite(localPath + "\\" + file.Name))
        {
            //sftp.DownloadFile(file.FullName,saveFile); <-- This works fine
            tasks.Add(Task.Factory.FromAsync(client.BeginDownloadFile(file.FullName, saveFile), client.EndDownloadFile));
        }                        
    }

    await Task.WhenAll(tasks);
    client.Disconnect();

}
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2015-12-02 18:05:53

因为saveFile是在using块中声明的,所以它会在您启动任务后立即关闭,因此无法完成下载。实际上,我很惊讶你没有得到一个例外。

您可以将代码提取到单独的方法中进行下载,如下所示:

代码语言:javascript
复制
var port = 22;
string host = "localhost";
string username = "user";
string password = "password";
string localPath = @"C:\temp";

using (var client = new SftpClient(host, port, username, password))
{
    client.Connect();
    var files = client.ListDirectory("");

    var tasks = new List<Task>();

    foreach (var file in files)
    {                        
        tasks.Add(DownloadFileAsync(file.FullName, localPath + "\\" + file.Name));
    }

    await Task.WhenAll(tasks);
    client.Disconnect();

}

...

async Task DownloadFileAsync(string source, string destination)
{
    using (var saveFile = File.OpenWrite(destination))
    {
        var task = Task.Factory.FromAsync(client.BeginDownloadFile(source, saveFile), client.EndDownloadFile);
        await task;
    }
}

这样,在您完成文件下载之前,文件不会关闭。

查看SSH.NET源代码,看起来DownloadFile的异步版本并没有使用“真正的”异步IO (使用IO完成端口),而只是在一个新线程中执行下载。因此,使用BeginDownloadFile/EndDownloadFile没有什么真正的好处;您也可以在自己创建的线程中使用DownloadFile

代码语言:javascript
复制
Task DownloadFileAsync(string source, string destination)
{
    return Task.Run(() =>
    {
        using (var saveFile = File.OpenWrite(destination))
        {
            client.DownloadFile(source, saveFile);
        }
    }
}
票数 12
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34039810

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档