Invoke-Webrequest получает 401 на POST, но не на GET с базовой аутентификацией - PullRequest
0 голосов
/ 04 октября 2018

У меня есть сайт разработчика с включенной базовой аутентификацией.Я получаю страницу GET для добавления базовой аутентификации в заголовки:

$creds = "$($BASIC_AUTH_USER):$($BASIC_AUTH_PASS)"
$encodedCreds = [System.Convert]::ToBase64String([System.Text.Encoding]::ASCII.GetBytes($creds))
$basicAuthValue = "Basic $encodedCreds"
$headers = @{
    Authorization = $basicAuthValue
}

$login = Invoke-WebRequest $url -SessionVariable session -UseBasicParsing -Headers $headers

Но я не могу опубликовать на тот же URL:

$fields = @{ Email = $SITE_USER; Password = $SITE_PASS; }
$login = Invoke-WebRequest -Uri $url -Method POST -WebSession $session -Body $fields -UseBasicParsing -Headers $headers

Я получаю401 Несанкционированная спина.Все работает нормально, если я отключаю базовую аутентификацию на сайте.Так что я знаю, что это не проблема с сервером.Я могу POST, используя мой браузер.

Редактировать: Таким образом, кажется, что базовая аутентификация работает правильно, когда я отлаживаю на сервере.Но мой сервер возвращает перенаправление, в результате чего Invoke-Webrequest интерпретирует это как 401.

Есть идеи о том, почему это может не работать?

1 Ответ

0 голосов
/ 05 октября 2018

Вы получаете это поведение из-за перенаправления;при выполнении этого дополнительного запроса к месту перенаправления заголовок авторизации не включается.

По этой причине PowerShell 6.0.0 добавляет параметр PreserveAuthorizationOnRedirect .

Указывает, что командлет должен сохранять заголовок авторизации, если он присутствует, при перенаправлениях.
По умолчанию командлет удаляет заголовок авторизации перед перенаправлением.Указание этого параметра отключает эту логику для случаев, когда заголовок необходимо отправить в место перенаправления.

Ссылка Invoke-WebRequest


Как альтернатива , если вы не используете PowerShell 6, вы можете обойти его с помощью более низкого уровня сценария, используя System.Net.WebRequest, который определяет свойство AllowAutoRedirect, которое можно установить на False чтобы пропустить перенаправление после успешного POST, избегая ошибки 401.

Обратите внимание, что вам нужно позаботиться о таких вещах, как форматирование данных / тела (json, form-urlencoded, ...) иhttp-заголовки сами.

Сценарий будет выглядеть ниже.
Обратите внимание на строку с AllowAutoRedirect = $false.

$creds = "$($BASIC_AUTH_USER):$($BASIC_AUTH_PASS)"
$encodedCreds = [System.Convert]::ToBase64String([System.Text.Encoding]::ASCII.GetBytes($creds))
$basicAuthValue = "Basic $encodedCreds"

$url = "http://your.url"
$request = [System.Net.WebRequest]::CreateHttp($url);   
$request.Method = "post"
$request.Headers.Add("Authorization", $basicAuthValue)
$request.AllowAutoRedirect = $false

$body = "your formatted data goes here"
$bytes = [System.Text.Encoding]::UTF8.GetBytes($body);
$stream = $request.GetRequestStream()
$stream.Write($bytes, 0, $bytes.Length);
$stream.Close();

$request.GetResponse();
...