7

我正在使用 Renci SSH.NET 访问 unix 服务器上的文件和文件夹。我想通过指定基本目录来删除整个目录树,但是当我调用 时sftp.DeleteDirectory(destination),只有当我传递一个空目录时,该调用才会成功。

但是,我还希望能够删除包含文件或其他文件夹的目录。大多数 .NET 类都会自动处理,如何在 SSH.NET 中完成?

4

3 回答 3

16

SSH.NET 库不支持任何递归操作。所以递归删除也不可用。

您必须使用该SftpClient.ListDirectory方法递归列出所有文件和子文件夹并一一删除。

private static void DeleteDirectory(SftpClient client, string path)
{
    foreach (SftpFile file in client.ListDirectory(path))
    {
        if ((file.Name != ".") && (file.Name != ".."))
        {
            if (file.IsDirectory)
            {
                DeleteDirectory(client, file.FullName);
            }
            else
            {
                client.DeleteFile(file.FullName);
            }
        }
    }

    client.DeleteDirectory(path);
}

或者使用另一个 SFTP 库。

例如使用WinSCP .NET 程序集,您可以使用可以递归删除目录的Session.RemoveFiles方法。

// Setup session options
SessionOptions sessionOptions = new SessionOptions
{
    Protocol = Protocol.Sftp,
    HostName = "example.com",
    UserName = "user",
    Password = "mypassword",
    SshHostKeyFingerprint = "ssh-rsa 2048 xxxxxxxxxxx...="
};

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

    // Delete the directory recursively
    session.RemoveFiles("/directory/to/delete").Check();
}

WinSCP GUI 可以为您生成代码模板

(我是WinSCP的作者)

于 2016-04-12T09:15:46.560 回答
3

尝试在 SSH 中执行命令,而不是使用 sftp rm -rf 或 rm -r。

代码可能如下所示:

Renci.SshClient ssh1 = new SshCLient("server","user","password");
ssh1.connect();
ssh1.RunCommand("cd LandingZone;rm -rf <directoryName>");
ssh1.Disconnect();
于 2016-04-12T09:27:29.080 回答
-2

您可以通过使用以下两种方法指定远程路径,使用 SSH.NET 库(无论它是否为空目录)动态删除目录树或文件:

  public bool DeleteRemoteDirectoryRecursive(string RemoteDirectoryPath)
  {
        if (string.IsNullOrEmpty(RemoteDirectoryPath))
        {                
            return false;
        }

        var ConnectionInfo = new ConnectionInfo(this.sftpHost, this.sftpPort, this.sftpUser, new PasswordAuthenticationMethod(this.sftpUser, this.sftpPassword));
        using (var client = new SftpClient(ConnectionInfo))
        {                
            client.Connect();

            if (!client.Exists(RemoteDirectoryPath))
            {                   
                client.Disconnect();
                client.Dispose();
                return false;
            }

            foreach (var file in client.ListDirectory(RemoteDirectoryPath))
            {
                if (file.Name.Equals(".") || file.Name.Equals(".."))
                    continue;

                if (file.IsDirectory)
                {
                    client.Disconnect();
                    DeleteRemoteDirectoryRecursive(file.FullName);
                }
                else
                    client.DeleteFile(file.FullName);
            }

            client.DeleteDirectory(RemoteDirectoryPath);

        }

        return true;
    }

    public bool Remove(string RemotePath)
    {
        bool ReturnResult = false;

        try
        {
            if (string.IsNullOrEmpty(RemotePath))
            {
                return false;
            }

            var ConnectionInfo = new ConnectionInfo(this.sftpHost, this.sftpPort, this.sftpUser, new PasswordAuthenticationMethod(this.sftpUser, this.sftpPassword));
            using (var client = new SftpClient(ConnectionInfo))
            {
                client.Connect();

                if (!client.Exists(RemotePath))
                {
                    client.Disconnect();
                    client.Dispose();
                    return false;
                }

                try
                {
                    //  path is directory
                    client.ChangeDirectory(RemotePath);
                    try
                    {
                        DeleteRemoteDirectoryRecursive(RemotePath);
                        ReturnResult = true;
                    }
                    catch
                    {
                        ReturnResult = false;
                    }

                }
                // path is a file
                catch
                {
                    try
                    {
                        client.DeleteFile(RemotePath);
                        ReturnResult = true;
                    }
                    catch
                    {
                        ReturnResult = false;
                    }
                }
            }
        }
        catch (Exception ex)
        {                
            ReturnResult = false;
        }
        return ReturnResult;
    }
于 2018-12-05T10:09:38.110 回答