2

我在 Windows 服务中遇到 ftp 问题。我已经安排了一个通过 ftp 发送文件的作业。偶尔我会超时(频率每周一次或每月一次),它会一直持续到我重新启动我的 Windows 服务。

System.Net.WebException:操作已超时。

我正在处理异常,最后我关闭了所有打开的 ftp 会话。

try
        {
            string uri = String.Format("ftp://{0}/{1}/{2}", server, download, file);
            Uri serverUri = new Uri(uri);
            if (serverUri.Scheme != Uri.UriSchemeFtp)
            {
                return;
            }
            FtpWebRequest reqFTP = (FtpWebRequest)FtpWebRequest.Create(new Uri(uri));
            reqFTP.Credentials = new NetworkCredential(username, password);
            reqFTP.KeepAlive = false;
            reqFTP.Method = WebRequestMethods.Ftp.DownloadFile;
            reqFTP.EnableSsl = false;
            reqFTP.Proxy = null;
            reqFTP.UsePassive = true;
            reqFTP.Timeout = Settings.Default.TimeOut;
            reqFTP.ReadWriteTimeout = Settings.Default.TimeOut;

            response = (FtpWebResponse)reqFTP.GetResponse();
            responseStream = response.GetResponseStream();

            using (FileStream writeStream = new FileStream(path + file, FileMode.Create))
            {
                int Length = 10240;
                Byte[] buffer = new Byte[Length];
                int bytesRead = responseStream.Read(buffer, 0, Length);
                while (bytesRead > 0)
                {
                    writeStream.Write(buffer, 0, bytesRead);
                    bytesRead = responseStream.Read(buffer, 0, Length);
                }
            }

            response.Close();
        }
        catch (WebException wEx)
        {
            LogDatabase.WriteLog("Download File", wEx.ToString(), "Download File");
        }
        finally
        {
            if (response != null)
            {
                response.Close();
            }
            if (responseStream != null)
            {
                responseStream.Close();
            }
        }

有任何想法吗 ?

提前谢谢。

4

1 回答 1

0

为什么你不能把这一切都放在一个循环中?然后,如果您有错误,则循环将返回并再次尝试。

另外,您为什么将KeepAlive选项设置为false

我玩了一会儿这个,然后把它放到一个类中,这样我可以更好地看到它,但没有对其进行任何测试。我的班级在后台线程中进行 FTP 调用,如果您希望能够与之通信,这当然是您想要做的事情。

我当然不能保证这至少不会出现一些故障!

class FtpRequests {

  private const int BUF_SIZE = 10240;
  private const string PASSWORD = "password";
  private const string USERNAME = "username";
  private const string SERVER = "yourserver.com";
  private string path;

  public FtpRequests() {
    Cancel = false;
    path = Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData);
  }

  public bool Cancel { get; set; }

  public bool Complete { get; set; }

  public Thread Thread1 { get; set; }

  public int Timeout { get; set; }

  public int ReadWriteTimeout { get; set; }

  public void StartFtpDownload(string download, string file) {
    string objString = string.Format("{0};{1}", download, file);
    Thread1 = new Thread(startFtpThread);
    Thread1.Name = string.Format("{0} download", file);
    Thread1.IsBackground = true;
    Thread1.Start(objString);
  }

  private void startFtpThread(object obj) {
    Complete = false;
    string objString = obj.ToString();
    string[] split = objString.Split(';');
    string download = split[0];
    string file = split[1];
    do {
      try {
        string uri = String.Format("ftp://{0}/{1}/{2}", SERVER, download, file);
        Uri serverUri = new Uri(uri);
        if (serverUri.Scheme != Uri.UriSchemeFtp) {
          Cancel = true;
          return;
        }
        FtpWebRequest reqFTP = (FtpWebRequest)FtpWebRequest.Create(new Uri(uri));
        reqFTP.Credentials = new NetworkCredential(USERNAME, PASSWORD);
        reqFTP.KeepAlive = true;
        reqFTP.Method = WebRequestMethods.Ftp.DownloadFile;
        reqFTP.EnableSsl = false;
        reqFTP.Proxy = null;
        reqFTP.UsePassive = true;
        reqFTP.Timeout = Timeout;
        reqFTP.ReadWriteTimeout = ReadWriteTimeout;
        using (FtpWebResponse response = (FtpWebResponse)reqFTP.GetResponse()) {
          using (Stream responseStream = response.GetResponseStream()) {
            using (FileStream writeStream = new FileStream(path + file, FileMode.Create)) {
              Byte[] buffer = new Byte[BUF_SIZE];
              int bytesRead = responseStream.Read(buffer, 0, BUF_SIZE);
              while (0 < bytesRead) {
                writeStream.Write(buffer, 0, bytesRead);
                bytesRead = responseStream.Read(buffer, 0, BUF_SIZE);
              }
            }
            responseStream.Close();
          }
          response.Close();
          Complete = true;
        }
      } catch (WebException wEx) {
        LogDatabase.WriteLog("Download File", wEx.ToString(), "Download File");
      }
    } while (!Cancel && !Complete);
  }

}
于 2012-04-06T15:28:30.830 回答