Kae Travis

Using PowerShell and Invoke-WebRequest to Send a HTTP Request

PowerShell is a powerful scripting language that provides the tools to automate various tasks on Windows systems. One of its handy features is the ability to send HTTP requests using the Invoke-WebRequest cmdlet. In this blog post, we’ll explore using PowerShell and Invoke-WebRequest to send a HTTP Request, interact with web services, and retrieve data from websites.

Why Use PowerShell for HTTP Requests?

PowerShell’s Invoke-WebRequest cmdlet is a versatile tool for sending HTTP requests.  We can use it to:

  • Retrieve data from web services or websites.
  • Automate interactions with REST APIs.
  • Monitor website availability and response times.
  • Download files from the internet.
  • Submit data to web forms.

Basic Usage of Sending a GET request using Invoke-WebRequest

You might want to refer to how to using PowerShell to read and write JSON for how to process the response.

But in this first example we use Invoke-WebRequest to send a simple GET request to a web page, and view the response.  We pass in a GET argument called “company” with a value of “alkane”.

#pass GET parameter called "company" with a value of "alkane"
$response = Invoke-WebRequest -Uri "https://httpbin.org/get?company=alkane" 

#convert the response into JSON so we can access the response
$jsonResponse = $response.Content | ConvertFrom-Json

#write our the GET parameter that we passed in
write-host $jsonResponse.args.company

Basic Usage of Sending a POST request using Invoke-WebRequest

If we need to send more complex data to a web service, we can use Invoke-WebRequest to send POST requests too.  In this example, since i prefer working with JSON, so we convert our $data hashtable to JSON and send it as the -Body paramater.  Note that in this case we must specify the -ContentType "application/json"

# Define the data to be sent 
$data = @{ 
    "alkane" = @{ 
        "address" = "100 Alkane Street"
        "phone" = "016161616161"
    }    
} 

$json = $data | ConvertTo-Json

# Send a POST request with data 
$response = Invoke-WebRequest -Uri "https://httpbin.org/post" -Method POST -Body $json -ContentType "application/json"

#convert the response into JSON so we can access the response
$jsonResponse = $response.Content | ConvertFrom-Json

#write our the GET parameter that we passed in
write-host $jsonResponse.json.alkane.address
write-host $jsonResponse.json.alkane.phone

Error Handling

When sending HTTP requests, it’s important to handle errors gracefully. Unfortunately PowerShell’s Invoke-WebRequest does a poor job of handling non-200 HTTP responses very well.  So we need to use a try/catch block instead:

try {
    $response = Invoke-WebRequest -Uri "https://httpbin.org/status/404" -Method GET
} catch {
    $statusCode = $_.Exception.Response.StatusCode.Value__
    write-host "The request failed with a status code $statusCode"
}

Handling Authentication

When interacting with web services that require (basic in this case) authentication, we can include credentials in our request:

try {
    #supply the sample username and password
    $creds = [System.Convert]::ToBase64String([System.Text.Encoding]::UTF8.GetBytes('AlkaneUser:AlkanePassword'))

    #this test API has an endpoint where we can specify what the username/password 'should' be when it does a fake authentication
    $response = Invoke-WebRequest 'http://httpbin.org/basic-auth/AlkaneUser/AlkanePassword' -Headers @{ 'Authorization' = 'Basic ' + $creds }

    #convert the response into JSON so we can access the response 
    $jsonResponse = $response.Content | ConvertFrom-Json 
    
    write-host $jsonResponse.authenticated
    write-host $jsonResponse.user

} catch { 
    $statusCode = $_.Exception.Response.StatusCode.Value__ 
    write-host "The request failed with a status code $statusCode" 
}

Handling Headers

We can add custom headers to our requests as well. For instance, there we include headers called “Accept” and “company”:

$header = @{
    "Accept" = "application/json"; 
    "Company" = "Alkane";
}

# Send a GET request with headers 
$response = Invoke-WebRequest -Uri "https://httpbin.org/headers" -Method GET -Headers $header

#convert the response into JSON so we can access the response
$jsonResponse = $response.Content | ConvertFrom-Json

#read headers
write-host $jsonResponse.headers.Company

PowerShell’s Invoke-WebRequest cmdlet is a valuable tool for sending HTTP requests, making it easier to interact with web services, retrieve data, and automate tasks involving web resources. Whether we need to scrape data from websites, interact with REST APIs, or perform various web-related tasks, PowerShell can simplify the process.

Using PowerShell and Invoke-WebRequest to Send a HTTP Request
Using PowerShell and Invoke-WebRequest to Send a HTTP Request

Leave a Reply