System.Net.WebException HTTP durum kodu


Yanıtlar:


248

Belki böyle bir şey ...

try
{
    // ...
}
catch (WebException ex)
{
    if (ex.Status == WebExceptionStatus.ProtocolError)
    {
        var response = ex.Response as HttpWebResponse;
        if (response != null)
        {
            Console.WriteLine("HTTP Status Code: " + (int)response.StatusCode);
        }
        else
        {
            // no http status code available
        }
    }
    else
    {
        // no http status code available
    }
}

ancak webexception "connectfailure" istisna durumunda, ben null olarak yanıt almak, bu durumda nasıl httpstatus kodu alabilirim
Rusty

8
@rusty: Yapamazsın. Bir bağlantı hatası varsa, HTTP durumu kodu alınamaz.
LukeH

4
Hata bir ProtocolError ise, yanıtın null olup olmadığını denetlemenize gerek yoktur. Bu MSDN sayfasındaki
Andras Toth

5
@AndrasToth Ancak boş kontrolü atlarsanız ReSharper gibi araçlar size bir uyarı verecektir. Ve her durumda, defansif kodlama yapmak iyi bir uygulamadır.
Tom Lint

1
HTTP Substatus değeri nasıl alınır ? Örneğin, 404.13 İçerik Uzunluğu Çok Büyük Referans : docs.microsoft.com/en-us/iis/configuration/system.webServer/…
Kiquenet

27

Kullanarak boş-şartlı operatörü ( ?.) Eğer tek bir kod satırı ile HTTP durum kodu alabilirsiniz:

 HttpStatusCode? status = (ex.Response as HttpWebResponse)?.StatusCode;

Değişken statusiçerecektir HttpStatusCode. Hiçbir HTTP durum kodunun gönderilmediği bir ağ hatası gibi daha genel bir hata statusolduğunda, null olur. Bu durumda ex.Statusalmak için inceleyebilirsiniz WebExceptionStatus.

Arıza durumunda yalnızca açıklayıcı bir dizenin günlüğe kaydedilmesini istiyorsanız , ilgili hatayı almak için null birleştirme operatörünü ( ??) kullanabilirsiniz:

string status = (ex.Response as HttpWebResponse)?.StatusCode.ToString()
    ?? ex.Status.ToString();

404 HTTP durum kodunun bir sonucu olarak istisna atılırsa, dize "NotFound" içerecektir. Öte yandan, sunucu çevrimdışıysa dizede "ConnectFailure" vb. Bulunacaktır.

(Ve HTTP alt durum kodunun nasıl alınacağını bilmek isteyen herkes için. Bu mümkün değil. Sadece sunucuda oturum açmış ve istemciye hiç gönderilmemiş bir Microsoft IIS konseptidir.)


?.Önizleme sürümü sırasında operatörün başlangıçta boş yayılma operatörü veya boş koşullu operatör olarak adlandırıldığından emin değilim . Ancak Atlassian yeniden birleştirici, bu tür senaryolarda boş yayılma operatörü kullanmak için bir uyarı verir. Boş koşullu operatör olarak da adlandırıldığını bilmek güzel.
RBT

1
Bu partiye biraz geç, ancak null koşullu operatörün bir C # 6.0 özelliği olduğuna dair adil bir uyarı, bu yüzden onu destekleyen bir derleyici kullanması gerekiyor. Daha fazla ayrıntıyla Yığın Taşması yanıtı . VS 2015+ varsayılan olarak buna sahiptir, ancak biri sadece "makineleri" dışında herhangi bir tür oluşturma / yerleştirme ortamı kullanıyorsa, diğer şeylerin dikkate alınması gerekebilir.
CodeHxr

9

bu yalnızca WebResponse bir HttpWebResponse ise çalışır.

try
{
    ...
}
catch (System.Net.WebException exc)
{
    var webResponse = exc.Response as System.Net.HttpWebResponse;
    if (webResponse != null && 
        webResponse.StatusCode == System.Net.HttpStatusCode.Unauthorized)
    {
        MessageBox.Show("401");
    }
    else
        throw;
}

neden tüm olası HTTP hata durum kodları yerine yalnızca 401 Yetkisiz ile ilgileniyorsunuz? bu en kötü cevap
ympostor

4
@ ympostor Bu sadece bir örnek. Herhangi bir makul geliştirici bunu anlar. Yorumunuz burada okuduğum en düşüncesiz.
pr0gg3r

9

(Sorunun eski olduğunu, ancak Google'daki en popüler isabetler arasında olduğunu fark ediyorum.)

Yanıt kodunu bilmek istediğiniz yaygın bir durum istisna işlemedir. C # 7'den itibaren, yalnızca istisna yükleminizle eşleşiyorsa yakalama yan tümcesini girmek için desen eşleştirmeyi kullanabilirsiniz:

catch (WebException ex) when (ex.Response is HttpWebResponse response)
{
     doSomething(response.StatusCode)
}

Bu WebException, aslında bir başkasının iç istisnasının olduğu bu durumda (ve yalnızca ilgilendiğimiz gibi 404) daha ileri seviyelere kolayca genişletilebilir :

catch (StorageException ex) when (ex.InnerException is WebException wex && wex.Response is HttpWebResponse r && r.StatusCode == HttpStatusCode.NotFound)

Son olarak: kriterlere uymadığında istisnayı yakalama maddesine nasıl atmaya gerek olmadığına dikkat edin, çünkü yukarıdaki çözüme ilk etapta madde girmiyoruz.


4

WebException'dan HTTP durum kodu almak için bu kodu deneyebilirsiniz. Silverlight'ta da çalışır, çünkü SL'de WebExceptionStatus.ProtocolError tanımlanmamıştır.

HttpStatusCode GetHttpStatusCode(WebException we)
{
    if (we.Response is HttpWebResponse)
    {
        HttpWebResponse response = (HttpWebResponse)we.Response;
        return response.StatusCode;
    }
    return null;
}

1
return 0? ya da daha iyisi HttpStatusCode?( boş )
Kiquenet

Bu işe yarayacak mı? var code = GetHttpStatusCode(ex); if (code != HttpStatusCode.InternalServerError) {EventLog.WriteEntry( EventLog.WriteEntry("MyApp", code, System.Diagnostics.EventLogEntryType.Information, 1);}
FMFF

Bu örnekte ne yapmak istediğinizi anlayamıyorum. Hangi durumlarda etkinliğin günlüğe kaydedilmesini istersiniz?
Sergey

1

Orada olup olmadığından emin değilim ama böyle bir özellik olsaydı güvenilir sayılmazdı. A WebException, basit ağ hataları dahil HTTP hata kodları dışındaki nedenlerle tetiklenebilir. Bunların eşleşen http hata kodu yok.

Bize bu kodla neyi başarmaya çalıştığınız hakkında biraz daha bilgi verebilir misiniz? İhtiyacınız olan bilgiyi almanın daha iyi bir yolu olabilir.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.