如何在C#中发送任意FTP命令

cch*_*ion 8 c# ftp ftpwebrequest

我已经实现了使用FtpWebRequestC#中的类上传,下载,删除等功能.这是相当直接的.

我现在需要做的是支持发送任意FTP命令,如

quote SITE LRECL=132 RECFM=FB
or 
quote SYST
Run Code Online (Sandbox Code Playgroud)

以下是我们的示例配置app.config:

<!-- The following commands will be executed before any uploads occur -->
<extraCommands>
     <command>quote SITE LRECL=132 RECFM=FB</command>
</extraCommands>
Run Code Online (Sandbox Code Playgroud)

我还在研究如何使用它FtpWebRequest.我接下来可能会WebClient上课.任何人都可以更快地指出我正确的方向?谢谢!

更新:我得出了同样的结论,因为.NET Framework 3.5 FtpWebRequest不支持除了内容之外的任何内容WebRequestMethods.Ftp.*.我会尝试一些其他帖子推荐的第三方应用.谢谢您的帮助!

Tho*_*que 9

我不认为它可以用FtpWebRequest...指定FTP命令的唯一方法是通过Method属性,文档说明:

请注意,WebRequestMethods.Ftp类中定义的字符串是Method属性唯一支持的选项.将该Method属性设置为任何其他值将导致ArgumentException异常.

SITE和SYST不属于预定义的选项,所以我猜你被卡住了......

不要浪费时间去尝试这个WebClient课程,它会给你更少的灵活性FtpWebRequest.

但是,有很多第三方FTP实现,开源或商业,我很确定其中一些可以处理自定义命令...


Rys*_*gan 6

FtpWebRequest为不会帮助你托马斯Levesque的他说的答案.您可以使用一些第三方解决方案或以下TcpClient基于简化的代码,我已经使用Visual Basic编写答案进行了重构:

public static void SendFtpCommand()
{
    var serverName = "[FTP_SERVER_NAME]";
    var port = 21;
    var userName = "[FTP_USER_NAME]";
    var password = "[FTP_PASSWORD]"
    var command = "SITE CHMOD 755 [FTP_FILE_PATH]";

    var tcpClient = new TcpClient();
    try
    {
        tcpClient.Connect(serverName, port);
        Flush(tcpClient);

        var response = TransmitCommand(tcpClient, "user " + userName);
        if (response.IndexOf("331", StringComparison.OrdinalIgnoreCase) < 0)
            throw new Exception(string.Format("Error \"{0}\" while sending user name \"{1}\".", response, userName));

        response = TransmitCommand(tcpClient, "pass " + password);
        if (response.IndexOf("230", StringComparison.OrdinalIgnoreCase) < 0)
            throw new Exception(string.Format("Error \"{0}\" while sending password.", response));

        response = TransmitCommand(tcpClient, command);
        if (response.IndexOf("200", StringComparison.OrdinalIgnoreCase) < 0)
            throw new Exception(string.Format("Error \"{0}\" while sending command \"{1}\".", response, command));
    }
    finally
    {
        if (tcpClient.Connected)
            tcpClient.Close();
    }
}

private static string TransmitCommand(TcpClient tcpClient, string cmd)
{
    var networkStream = tcpClient.GetStream();
    if (!networkStream.CanWrite || !networkStream.CanRead)
        return string.Empty;

    var sendBytes = Encoding.ASCII.GetBytes(cmd + "\r\n");
    networkStream.Write(sendBytes, 0, sendBytes.Length);

    var streamReader = new StreamReader(networkStream);
    return streamReader.ReadLine();
}

private static string Flush(TcpClient tcpClient)
{
    try
    {
        var networkStream = tcpClient.GetStream();
        if (!networkStream.CanWrite || !networkStream.CanRead)
            return string.Empty;

        var receiveBytes = new byte[tcpClient.ReceiveBufferSize];
        networkStream.ReadTimeout = 10000;
        networkStream.Read(receiveBytes, 0, tcpClient.ReceiveBufferSize);

        return Encoding.ASCII.GetString(receiveBytes);
    }
    catch
    {
        // Ignore all irrelevant exceptions
    }

    return string.Empty;
}
Run Code Online (Sandbox Code Playgroud)

通过FTP时,您可以期待以下流程:

220 (vsFTPd 2.2.2)
user [FTP_USER_NAME]
331 Please specify the password.
pass [FTP_PASSWORD]
230 Login successful.
SITE CHMOD 755 [FTP_FILE_PATH]
200 SITE CHMOD command ok.
Run Code Online (Sandbox Code Playgroud)