我们正在使用.Net FtpWebRequest类在我们的应用程序中传输文件,并且似乎我们遇到了无限等待的问题,我们认为这可能发生在.Net库代码内。
我们正在使用方法的异步版本,我们的(简化的)代码如下:
async Task DoTransfer(int id, CancellationToken cTkn)
{
try
{
FtpWebRequest request = (FtpWebRequest)WebRequest.Create(targetAddress);
request.UsePassive = true;
request.KeepAlive = true;
request.Timeout = 300000; // 5 minutes
request.Method = WebRequestMethods.Ftp.UploadFile;
using (var stream = await request.GetRequestStreamAsync())
{
...create a byte buffer of the file here
cTkn.ThrowIfCancellationRequested();
await stream.WriteAsync(buffer, 0, buffer.Length, cTkn);
}
using (var response = (FtpWebResponse)await request.GetResponseAsync())
{
cTkn.ThrowIfCancellationRequested();
...do something with status code
}
}
catch (OperationCanceledException)
{
...logging
}
catch (Exception ex)
{
...logging
}
finally
{
...code to remove this task from a concurrent dictionary using the 'id' param
}
}
最初创建任务时,我们将其添加到并发词典中进行监视(生成的随机ID)。完成后,任务将自己从此字典中删除(在finally块中)。我们遇到的问题是任务永远不会删除自身,这表明从未到达过finally块。
我们使用的取消令牌是来自“主”取消令牌的链接令牌,以及在任务启动之前(设置为5分钟)创建的新超时令牌。
由于该应用程序每分钟处理大约100个文件,我们无法隔离挂起的是哪种方法,而且这种问题很少发生,因此日志文件太大而无法手动读取。
该应用程序随时可以启动多达24个这些DoTransfer任务(通常连接到同一FTP服务器)。
是否有人知道与GetRequestStreamAsync()或GetResponseAsync()方法有关的任何问题,这些问题可能导致它们在像这样并行运行时永不返回?
或者对如何终止长时间运行的任务有任何建议(因为我们无法将取消令牌传递给这两个FtpWebRequest方法之一)?