3

The Invoke-WebRequest cmdlet can fail if Internet Explorer is not available*:

The response content cannot be parsed because the Internet Explorer engine is not available, or Internet Explorer's first-launch configuration is not complete. Specify the UseBasicParsing parameter and try again.

If I'm on a computer that has a working Internet Explorer, -UseBasicParsing is not required. I want to test that my script will work on computers that either haven't run IE or where IE has been uninstalled. In my test environment, how can I deliberately create the conditions in which the above error will happen?

* Before PowerShell 6.0.0.

Jay Bazuzi
  • 45,157
  • 15
  • 111
  • 168

1 Answers1

6

If I'm on a computer that has a working Internet Explorer, -UseBasicParsing is not required.

Even if it isn't required to avoid errors, you should use this switch, unless you truly need parsing the response into a DOM, accessible via the .ParsedHTML property. -UseBasicParsing prevents the overhead resulting from this unnecessary parsing.

Thus, if you don't need the Internet Explorer-mediated DOM parsing, always using
-UseBasicParsing is fine, and even works in cross-edition scenarios
:
While -UseBasicParsing is never needed in PowerShell (Core) (v6+) - where parsing into a DOM isn't even available - you can still use it there, without ill effects.


If you want to avoid having to pass the -UseBasicParsing switch to each and every call, you can preset -UseBasicParsing session-wide, via the $PSDefaultParameterValues preference variable:

# Note: '*' targets *all* commands that have a -UseBasicParsing parameter
#       While you could 'Invoke-WebRequest' instead of '*',
#       '*' ensures that 'Invoke-RestMethod' is covered too.
$PSDefaultParameterValues['*:UseBasicParsing'] = $true

If you want to scope this preset to a given script (and scripts / functions called from it), use the technique shown in this answer.


how can I deliberately create the conditions in which the above error will happen?

If you want to run tests against your code that simulate the error condition, so as to ensure that all your code uses -UseBasicParsing:

  • Install the Pester module, e.g. with Install-Module -Scope CurrentUser Pester. Pester is a widely used test framework for PowerShell.

  • Use Pester's mocking capabilities to simulate an error whenever an Invoke-WebRequest or Invoke-RestMethod call is made without -UseBasicParsing.

Here's a simple example (save to, say, EnforceBasicParsing.Tests.ps1 and invoke with .\EnforceBasicParsing.Tests.ps1):

Describe 'Enforce -UseBasicParsing' {
  BeforeAll {
    # Set up mocks for Invoke-WebRequest and Invoke-RestMethod
    # that throw whenever -UseBasicParsing isn't passed.
    $exceptionMessageAndErrorId = "Missing -UseBasicParsing"
    'Invoke-WebRequest', 'Invoke-RestMethod' | ForEach-Object {
      Mock -CommandName $_  `
           -ParameterFilter { -not $UseBasicParsing } `
           -MockWith{ throw $exceptionMessageAndErrorId } 
    }
  }
  It 'Fails if -UseBasicParsing is NOT used with Invoke-WebRequest' {
    { Invoke-WebRequest http://example.org } |
      Should -Throw -ErrorId $exceptionMessageAndErrorId
  }
  It 'Fails if -UseBasicParsing is NOT used with Invoke-RestMethod' {
    { Invoke-RestMethod http://example.org } |
      Should -Throw -ErrorId $exceptionMessageAndErrorId
  }
  It 'Deliberately failing test' {
    { Invoke-RestMethod http://example.org } |
      Should -Not -Throw -ErrorId $exceptionMessageAndErrorId
  }
}

The first two tests succeed, whereas the third one is deliberately made to fail, showing what would happen if the test ran against real code not using -UseBasicParsing.

See also: the Pester documentation.

mklement0
  • 382,024
  • 64
  • 607
  • 775
  • This doesn't help me. I agree that I want to always use `-UseBasicParsing` argument. I'm looking for a way to ensure that I do that everywhere. – Jay Bazuzi Mar 02 '23 at 23:56
  • That's a really interesting edit, but it's *still* not quite what I'm asking. My goal is "I want to test that my script will work on computers that either haven't run IE or where IE has been uninstalled." My specific question is "how do I create these conditions, such that a bad script will fail?" – Jay Bazuzi Mar 03 '23 at 14:47
  • @JayBazuzi, see my update re testing using Pester. – mklement0 Mar 03 '23 at 15:55
  • Monkey patching might be the best I can do. – Jay Bazuzi Mar 04 '23 at 18:55