一度に複数のスレッドを実行しようとするまで、私の FTP スクリプトはうまく機能していました。FtpWebRequest
過剰なデバッグの後、他の 2 つのスレッドが既に何かを実行している場合、単純にタイムアウトになることが判明しました。(アップロード、ファイル/ディレクトリが存在するかどうかの確認、またはディレクトリの作成。)
ftp クラスにロックを実装して、一度に 1 つのスレッドしか作成できないようにFtpWebRequest
しました (そして、ofc の応答を取得したときにロックを閉じます) が、それは役に立ちませんでした。
各リクエストは独自のFtpWebRequest
オブジェクトを使用するため、なぜこれが起こっているのかよくわかりません。クライアントを使用すると、同じ FTP サーバーに 10 個のファイルを同時にアップロードFileZilla
できるので、サーバー側の問題とは思えません。
この問題の原因となっている .NET の静的な舞台裏はありますか?
2 スレッド以上でタイムアウトする関数の例:
public class ftp
{
private string host = null;
private string user = null;
private string pass = null;
private int bufferSize = 2048;
/* Construct Object */
public ftp(string hostIP, string userName, string password) { host = hostIP; user = userName; pass = password; }
private object fileFolderCheckLock = new object(); //Only check if a file/dir exists one thread at a time
private object requestLock = new object(); //Don't create multiple ftprequests simultaneously. Exit this lock when the response is being received.
/* Create a New Directory on the FTP Server */
public bool CreateDirectory(string newDirectory)
{
FtpWebRequest ftpRequest = null;
FtpWebResponse ftpResponse = null;
try
{
lock(requestLock)
{
if(!newDirectory.EndsWith("/")) newDirectory += "/";
//Console.WriteLine("chk: "+host + "/" + newDirectory);
Uri theuri = new Uri(host + "/" + newDirectory);
//Console.WriteLine("theuri: "+theuri.ToString());
/* Create an FTP Request */
ftpRequest = (FtpWebRequest)WebRequest.Create(theuri);
/* Log in to the FTP Server with the User Name and Password Provided */
ftpRequest.Credentials = new NetworkCredential(user, pass);
/* When in doubt, use these options */
ftpRequest.UseBinary = true;
ftpRequest.UsePassive = true;
ftpRequest.KeepAlive = true;
ftpRequest.Timeout = 10000;
/* Specify the Type of FTP Request */
ftpRequest.Method = WebRequestMethods.Ftp.MakeDirectory;
/* Establish Return Communication with the FTP Server */
ftpResponse = (FtpWebResponse)ftpRequest.GetResponse();
}
}
catch (Exception ex){ Console.WriteLine("CreateDirectory Exception"+ex.ToString()); }
finally
{
/* Resource Cleanup */
try{ftpResponse.Close();}catch(Exception){}//??
ftpRequest = null;
}
return true;
}
}
なぜこれが起こるのか誰か教えてもらえますか?