Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -567,7 +567,7 @@ protected override void ProcessRecord()
WriteVerbose(linkVerboseMsg);
}

using (HttpRequestMessage request = GetRequest(uri))
using (HttpRequestMessage request = GetRequest(uri, isRedirect: followedRelLink > 0))
{
FillRequestStream(request);
try
Expand Down Expand Up @@ -1055,7 +1055,7 @@ internal virtual HttpClient GetHttpClient(bool handleRedirect)
return client;
}

internal virtual HttpRequestMessage GetRequest(Uri uri)
internal virtual HttpRequestMessage GetRequest(Uri uri, bool isRedirect = false)
{
Uri requestUri = PrepareUri(uri);
HttpMethod httpMethod = string.IsNullOrEmpty(CustomMethod) ? GetHttpMethod(Method) : new HttpMethod(CustomMethod);
Expand All @@ -1080,6 +1080,11 @@ internal virtual HttpRequestMessage GetRequest(Uri uri)
}
else
{
if (isRedirect && !PreserveAuthorizationOnRedirect && entry.Key is HttpKnownHeaderNames.Authorization)
{
continue;
}
Comment on lines +1083 to +1086

if (SkipHeaderValidation)
{
request.Headers.TryAddWithoutValidation(entry.Key, entry.Value);
Expand Down Expand Up @@ -1149,6 +1154,11 @@ internal virtual HttpRequestMessage GetRequest(Uri uri)
}
}

if (isRedirect && !PreserveAuthorizationOnRedirect && request.Headers.Contains(HttpKnownHeaderNames.Authorization))
{
request.Headers.Remove(HttpKnownHeaderNames.Authorization);
}

return request;
}

Expand Down Expand Up @@ -1346,7 +1356,8 @@ internal virtual HttpResponseMessage GetResponse(HttpClient client, HttpRequestM
currentUri = new Uri(request.RequestUri, response.Headers.Location);

// Continue to handle redirection
using HttpRequestMessage redirectRequest = GetRequest(currentUri);
using HttpRequestMessage redirectRequest = GetRequest(currentUri, isRedirect: true);

Comment on lines 1356 to +1360
response.Dispose();
response = GetResponse(client, redirectRequest, handleRedirect);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1153,15 +1153,29 @@ Describe "Invoke-WebRequest tests" -Tags "Feature", "RequireAdminOnWindows" {
$response.Content.Method | Should -Be $redirectedMethod
}

It "Validates Invoke-WebRequest -PreserveHttpMethodOnRedirect keeps the authorization header redirects and do remains POST when it handles the redirect: <redirectType>" -TestCases $redirectTests {
It "Validates Invoke-WebRequest -PreserveHttpMethodOnRedirect strips the authorization header and remains POST when it handles the redirect: <redirectType>" -TestCases $redirectTests {
param($redirectType)
$uri = Get-WebListenerUrl -Test 'Redirect' -Query @{type = $redirectType}
$response = ExecuteRedirectRequest -PreserveHttpMethodOnRedirect -Uri $uri -Method 'POST'

$response.Error | Should -BeNullOrEmpty
# ensure user-agent is present (i.e., no false positives )
$response.Content.Headers."User-Agent" | Should -Not -BeNullOrEmpty
# ensure Authorization header has been kept.
# ensure Authorization header has been removed.
$response.Content.Headers."Authorization" | Should -BeNullOrEmpty
# ensure POST doesn't change.
$response.Content.Method | Should -Be 'POST'
}

It "Validates Invoke-WebRequest -PreserveHttpMethodOnRedirect -PreserveAuthorizationOnRedirect keeps the authorization header and remains POST when it handles the redirect: <redirectType>" -TestCases $redirectTests {
param($redirectType)
$uri = Get-WebListenerUrl -Test 'Redirect' -Query @{type = $redirectType}
$response = ExecuteRedirectRequest -PreserveAuthorizationOnRedirect -PreserveHttpMethodOnRedirect -Uri $uri -Method 'POST'

$response.Error | Should -BeNullOrEmpty
# ensure user-agent is present (i.e., no false positives )
$response.Content.Headers."User-Agent" | Should -Not -BeNullOrEmpty
# ensure Authorization header has been preserved.
$response.Content.Headers."Authorization" | Should -BeExactly 'test'
# ensure POST doesn't change.
$response.Content.Method | Should -Be 'POST'
Expand Down Expand Up @@ -3035,6 +3049,18 @@ Describe "Invoke-RestMethod tests" -Tags "Feature", "RequireAdminOnWindows" {
1..$maxLinksToFollow | ForEach-Object { $result.Output[$_ - 1].linknumber | Should -BeExactly $_ }
}

It "Validate Invoke-RestMethod -FollowRelLink strips the authorization header on followed relation links by default" {
$uri = Get-WebListenerUrl -Test 'Link' -Query @{maxlinks = 3}
$command = "Invoke-RestMethod -Uri '$uri' -FollowRelLink -Headers @{Authorization = 'test'}"
$result = ExecuteWebCommand -command $command

$result.Error | Should -BeNullOrEmpty
$result.Output.Count | Should -BeExactly 3
$result.Output[0].headers.Authorization | Should -BeExactly 'test'
$result.Output[1].headers.Authorization | Should -BeNullOrEmpty
$result.Output[2].headers.Authorization | Should -BeNullOrEmpty
}
Comment on lines +3052 to +3062

It "Validate Invoke-RestMethod quietly ignores invalid Link Headers if -FollowRelLink is specified: <type>" -TestCases @(
@{ type = "noUrl" }
@{ type = "malformed" }
Expand Down Expand Up @@ -3240,15 +3266,29 @@ Describe "Invoke-RestMethod tests" -Tags "Feature", "RequireAdminOnWindows" {
$response.Content.Method | Should -Be $redirectedMethod
}

It "Validates Invoke-RestMethod -PreserveHttpMethodOnRedirect keeps the authorization header redirects and remains POST when it handles the redirect: <redirectType>" -TestCases $redirectTests {
It "Validates Invoke-RestMethod -PreserveHttpMethodOnRedirect strips the authorization header and remains POST when it handles the redirect: <redirectType>" -TestCases $redirectTests {
param($redirectType)
$uri = Get-WebListenerUrl -Test 'Redirect' -Query @{type = $redirectType}
$response = ExecuteRedirectRequest -PreserveHttpMethodOnRedirect -Cmdlet 'Invoke-RestMethod' -Uri $uri -Method 'POST'

$response.Error | Should -BeNullOrEmpty
# ensure user-agent is present (i.e., no false positives )
$response.Content.Headers."User-Agent" | Should -Not -BeNullOrEmpty
# ensure Authorization header has been kept.
# ensure Authorization header has been removed.
$response.Content.Headers."Authorization" | Should -BeNullOrEmpty
# ensure POST doesn't change.
$response.Content.Method | Should -Be 'POST'
}

It "Validates Invoke-RestMethod -PreserveHttpMethodOnRedirect -PreserveAuthorizationOnRedirect keeps the authorization header and remains POST when it handles the redirect: <redirectType>" -TestCases $redirectTests {
param($redirectType)
$uri = Get-WebListenerUrl -Test 'Redirect' -Query @{type = $redirectType}
$response = ExecuteRedirectRequest -PreserveAuthorizationOnRedirect -PreserveHttpMethodOnRedirect -Cmdlet 'Invoke-RestMethod' -Uri $uri -Method 'POST'

$response.Error | Should -BeNullOrEmpty
# ensure user-agent is present (i.e., no false positives )
$response.Content.Headers."User-Agent" | Should -Not -BeNullOrEmpty
# ensure Authorization header has been preserved.
$response.Content.Headers."Authorization" | Should -BeExactly 'test'
# ensure POST doesn't change.
$response.Content.Method | Should -Be 'POST'
Expand Down
Loading