Marcelo Barganha
Marcelo Barganha

Reputation: 379

How can I prevent UI freezing while using HttpWebRequest?

I have a progressBar on my form and a button. When user clicks this button, the progressBar should be styled as "marquee" and the program begins to check is an URL is valid or not.. OK.

But when I click the button, the UI freezes until the HttpStatusCode returns true or false...

Here is the check code:

private bool RemoteFileExists(string url)
{
   try
   {
      HttpWebRequest request = WebRequest.Create(url) as HttpWebRequest;
      request.Method = "HEAD";
      HttpWebResponse response = request.GetResponse() as HttpWebResponse;
      return (response.StatusCode == HttpStatusCode.OK);
   }
   catch
   {
      return false;
   }
}

And here is the button click code:

private async void button1_Click(object sender, EventArgs e)
{
   this.progressBar1.Style = System.Windows.Forms.ProgressBarStyle.Marquee;
   var result = RemoteFileExists("http://www.google.com/");
   if (Completed)
   {
      //ok
   }
   else
   {
      //not ok
   }
}

Upvotes: 1

Views: 2007

Answers (2)

confusedMind
confusedMind

Reputation: 2653

Putting it simple just use this:

private void button1_Click(object sender, EventArgs e)
{
      this.progressBar1.Style = System.Windows.Forms.ProgressBarStyle.Marquee;
      Thread thread = new Thread(() => RemoteFileExists("http://www.google.com/"));
      thread.IsBackground = true;
      thread.SetApartmentState(ApartmentState.STA);
      thread.Start();


}

And do the check inside RemoteFileExists .

Upvotes: 0

TorbenJ
TorbenJ

Reputation: 4582

The UI freezes because you are executing the RemoteFileExists method on the UI thread and receiving a response from a HttpWebRequest takes some time.
To solve this you have to execute RemoteFileExists in a different thread than the UI thread.
As your button1_Click method is already declared async the easiest way would be to declare RemoteFileExists as async too.
Then you can use the HttpWebRequest.GetResponseAsync method to asynchronously receive the response object.

private async Task<bool> RemoteFileExists(string url)
{
   try
   {
      HttpWebRequest request = WebRequest.CreateHttp(url);
      request.Method = "HEAD";

      using(var response = (HttpWebResponse) await request.GetResponseAsync())
      {
          return (response.StatusCode == HttpStatusCode.OK);
      }
   }
   catch
   {
      return false;
   }
}

Also when dealing with IDisposables you should take care of releasing all used resources by using the using statement or calling Dispose().
If you are using .NET Framework 4+ you can also use WebRequest.CreateHttp(string) to create your HttpWebRequest.

Upvotes: 1

Related Questions