如何在F#Async.Parallel中处理HttpWebRequest超时

|| 我只是花了很长时间才弄清楚为什么这段代码对于某些URL“挂起”了:
let getImage (imageUrl:string) =
    async {
        try
            let req = WebRequest.Create(imageUrl) :?> HttpWebRequest
            req.UserAgent <- \"Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; .NET CLR 1.1.4322)\";
            req.Method <- \"GET\";
            req.AllowAutoRedirect <- true;
            req.MaximumAutomaticRedirections <- 4;
            req.Timeout <- 3000; //HAHAHA, nice try!
            let! response1 = req.AsyncGetResponse()
            let response = response1 :?> HttpWebResponse
            use stream = response.GetResponseStream()
            let ms = new MemoryStream()
            let bytesRead = ref 1
            let buffer = Array.create 0x1000 0uy
            while !bytesRead > 0 do
                bytesRead := stream.Read(buffer, 0, buffer.Length)
                ms.Write(buffer, 0, !bytesRead)
            return SuccessfulDownload(imageUrl, ms.ToArray())

        with
            ex -> return FailedDownload(imageUrl, ex.Message)
    }
在设法找出3000个网址中的哪个被挂起之后,我了解到ѭ1take并没有注意到
HttpWebRequest.Timeout
。我做了一些搜索,提出了将异步请求包装在带有计时器的线程中的建议。这对C#来说很棒,但是如果我通过
Async.Parallel |> Async.RunSynchronously
运行3000个,那么解决这个问题的最佳方法是什么?
已邀请:
我仅对此进行了粗略的测试,但是它应该具有正确的行为:
type System.Net.WebRequest with
  member req.AsyncGetResponseWithTimeout () =
    let impl = async {
      let iar = req.BeginGetResponse (null, null)
      let! success = Async.AwaitIAsyncResult (iar, req.Timeout)
      return if success then req.EndGetResponse iar
             else req.Abort ()
                  raise (System.Net.WebException \"The operation has timed out\") }
    Async.TryCancelled (impl, fun _ -> req.Abort ())
在您的代码中,调用
req.AsyncGetResponseWithTimeout()
而不是
req.AsyncGetResponse()

要回复问题请先登录注册