2012-03-03 3 views
2

У меня есть сценарий Powershell, который использует System.Net.HttpWebRequest для связи с удаленным хостом.Обработка ошибок в System.Net.HttpWebRequest :: GetResponse()

Я создаю запрос, задаю свойства соответствующим образом и позвонил getresponse() и getresponsestream(), чтобы прочитать весь отклик сервера на строку. Это отлично работает, пока сервер отвечает сообщением «200 OK».

Если сервер отвечает «400 Bad Request» или любым другим кодом ошибки, getresponse() и getresponsestream() исключают исключения и не возвращают ничего. Моя проблема заключается в том, что в заголовок ответа содержится более подробная информация об ошибках, которая мне нужна, поэтому я могу выполнять свою собственную обработку ошибок.

Как я могу получить этот сигнал 400 Bad Request?

+0

Вы уже поймали объект исключения и посмотрел на $ _. Exception.Message недвижимость? И исследовал объект $ _. Exception? –

ответ

5

Edit: Я понял вопрос сначала, но оказывается, что вы можете получить заголовок ответа с помощью метода HttpWebResponse.GetResponseHeader(). Если происходит исключение, метод возвращает HttpWebRequest.GetResponse()$null, и вы должны использовать этот код, чтобы получить объект HttpWebResponse, так что вы можете назвать GetResponseHeader() на нем:

# If an exception occurs, get the HttpWebResponse object from the WebException object 
$HttpWebResponse = $Error[0].Exception.InnerException.Response; 

Я уверен, что вы» Я хочу придерживаться System.Net.HttpWebRequest вместо объекта System.Net.WebClient. Вот пример, подобный тому, что вы, вероятно, уже есть:

# Create a HttpWebRequest using the Create() static method 
$HttpWebRequest = [System.Net.HttpWebRequest]::Create("http://www.google.com/"); 

# Get an HttpWebResponse object 
$HttpWebResponse = $HttpWebRequest.GetResponse(); 

# Get the integer value of the HttpStatusCode enumeration 
Write-Host -Object $HttpWebResponse.StatusCode.value__; 

Метод GetResponse() возвращает HttpWebResponse объект, который имеет свойство с именем StatusCode, что указывает на значение в HttpStatusCode .NET перечисления. Как только вы получите ссылку на перечисление, мы используем свойство value__, чтобы получить целое число, связанное с возвращаемым значением перечисления.

Если вы получили нулевое значение из метода GetResponse(), то вам нужно будет прочитать самое последнее сообщение об ошибке в блоке catch {..}. Свойство Exception.ErrorRecord должно быть наиболее полезным.

try { 
    $HttpWebResponse = $null; 
    $HttpWebRequest = [System.Net.HttpWebRequest]::Create("http://www.asdf.com/asdf"); 
    $HttpWebResponse = $HttpWebRequest.GetResponse(); 
    if ($HttpWebResponse) { 
    Write-Host -Object $HttpWebResponse.StatusCode.value__; 
    Write-Host -Object $HttpWebResponse.GetResponseHeader("X-Detailed-Error"); 
    } 
} 
catch { 
    $ErrorMessage = $Error[0].Exception.ErrorRecord.Exception.Message; 
    $Matched = ($ErrorMessage -match '[0-9]{3}') 
    if ($Matched) { 
    Write-Host -Object ('HTTP status code was {0} ({1})' -f $HttpStatusCode, $matches.0); 
    } 
    else { 
    Write-Host -Object $ErrorMessage; 
    } 

    $HttpWebResponse = $Error[0].Exception.InnerException.Response; 
    $HttpWebResponse.GetResponseHeader("X-Detailed-Error"); 
} 

http://msdn.microsoft.com/en-us/library/system.net.httpwebrequest.aspx

http://msdn.microsoft.com/en-us/library/system.net.httpstatuscode.aspx

http://msdn.microsoft.com/en-us/library/system.net.httpwebresponse.aspx

+0

3-значный код состояния HTTP ничего не делает для меня. Мне нужно получить доступ к настраиваемому заголовку« X-Detailed-Error »из ответа удаленного хоста. Нет ли способа вызвать getresponse() и вернуть его объект, независимо от кода состояния? – Justin

+0

Я обновил этот пример. В случае возникновения исключения вам нужно захватить объект «HttpWebResponse», используя: '$ Error [0] .Exception.InnerException.Response' , а затем вы можете вызвать метод GetResponseHeader («X-Detailed-Error»). ' –

+0

Это отлично работает, спасибо! – Justin

0

Вы когда-нибудь пробовали заявления о попытке и уловить? Это отлично работает для меня.

например:

$webclient = new-object system.net.webclient 
try { 
    $domain = $webclient.downloadstring("http://xrsolis.com") # get a non existent domain 
} catch { 
    write-host "domain inaccessible" 
} 
+0

Это действительно не помогает, потому что он не позволяет мне получить полный ответ от сервера. После того, как сервер отправляет общий код статуса HTTP, он также отправляет пользовательский заголовок (X-Detail-Error) с точной причиной, по которой запрос не обрабатывался. Мне нужно иметь доступ к этому заголовку. $ _. Exception возвращает одно и то же сообщение об исключении, которое я видел бы на консоли без инструкции catch ( Exception, вызывающий «GetResponse» с аргументами «0»: «Удаленный сервер возвратил ошибку: (403) Запрещено.") – Justin

Смежные вопросы