Install Internet Explorer 11 with WSUS

Internet Explorer support/lifecycle: better safe than sorry

You should proably know that your browser should stay up-to-date not only because of security issues being fixed or any security or non-security related improvements introduced. Now, it will have to be aligned with the the lastest supported major version of Internet Explorer. The end-of-life of Internet Explorer on a per-OS basis has changed. Microsoft announced in August 2014 that:

Any guidance available?

Let’s have a look at the guidance on how to deploy Internet Explorer 11 on Windows 7 with WSUS.

I found the following technet page but it’s not exactly what I was looking for:
Install Internet Explorer 11 (IE11) – Windows Server Update Services (WSUS)

You may not know but it’s recommended to uninstalll previous IE9 before installing Internet Explorer 11

This page shows how to uninstall Internet Explorer from the commandline.

That’s it for the official guidance 😦 If you’ve a better link – an official one pointing to Microsoft’s website – , please feel free to post it in the comments, I may update this article to share it 🙂

Approve the Internet Explorer 11 on WSUS

Internet Explorer 11 is classified in the “Update Rollup” category. This category should be selected in the WSUS settings and the catalog should have been synchronised.

You cannot actually directly approve Internet Explorer 11 like any security update. If you try, you’ll get an error message saying:
“This Update has Microsoft Software License Terms that must be accepted before it can be deployed.”

If I list all the properties of the Internet Explorer 11, we can that the license has not been approved yet:

Fortunately, there’s a license approval method named ‘AcceptLicenseAgreement’ 🙂

Once the IE11 license has been approved, the properties are:

Here’s the piece of code I used to approve all required updates for Internet Explorer 11

(Get-WsusServer).SearchUpdates("Internet Explorer 11")| 
Where {
 -not($_.IsSuperseded) -and
 -not($_.isApproved)   -and 
 $_.Title -match "Windows\s7\sfor\sx64\-(based|Edition)" 
} | ForEach-Object {
 if($_.RequiresLicenseAgreementAcceptance) {
  Write-Verbose -Message "License accepted for $($_.Title)" -Verbose

Any post-installation updates required?
If you deploy Internet Explorer 11, you’ll have to apply post-installation security updates
Currently (on August 14) this is what is approved updates on WSUS

(Get-WsusServer).SearchUpdates("Internet Explorer 11")| ? {
    ($_.isApproved)   -and 
    $_.Title -match "Windows\s7\sfor\sx64\-(based|Edition)" 
} |
Select Title,isApproved,isSuperseded,SecurityBulletins,
@{l='Revision';e={$_.Id.RevisionNumber}},CreationDate,UpdateClassificationTitle | 
ft -AutoSize


What’s the client ‘experience’?
On the Windows 7 client, some prerequisites updates have been approved and installed along with Internet Explorer 11:

To confirm that Internet Explorer 11 was installed on the client, you can watch for the event ID 19.

$HT= @{
 LogName = 'System' ;
 ProviderName = 'Microsoft-Windows-WindowsUpdateClient';
Get-WinEvent -FilterHashtable $HT -MaxEvents 10

Once Internet Explorer 11 has been installed and Windows 7 restarted, a bunch of post-installation updates are still required to be installed on the Windows 7 client

Conclusion: When you deploy Internet Explorer 11 through WSUS, it’s fairly easy but it requires unfortunately 2 scans/installs + reboot to finally get a fully secured and up-to-date version of Internet Explorer 11 🙂
If it’s manually deployed, you can achieve the same thing with a single reboot. Thanks to DISM, you can chain the uninstallation of IE9, the installation of the prerequisites, IE11 itself plus its post-installation updates and reboot.

Bonus: Here are two useful links if you manage IE11 in a corporate environment

Windows Assessment and Deployment Kit (Windows ADK) 10 RTM available


I’ve updated the script on github that downloads ADK files for Windows 10

I’ve also added a new file that contains the checksums of files.
If you’ve downloaded the files into C:\ADK\v10, you can use the following code to check the integrity of these files:

$uri = ''
Invoke-WebRequest -URI $uri -OutFile ~/documents\SHA256SUMS.csv
Import-Csv  ~/documents\SHA256SUMS.csv -Delimiter ";" | Foreach-Object {
 if ( (Get-FileHash -Path (Join-Path -Path C:\ADK\v10 -ChildPath $($_.File))).Hash -eq $_.Hash) {
  Write-Verbose -Message "OK: $($_.File)" -Verbose
 } else {
  Write-Warning -Message "NOK: $($_.File)"

NB: the installation log of the ADK says it’s verifying packages before installing themADK.setup.log.verified.packages

Enjoy 😀

Scripting Games 2015 event 2

The Scripting Games are back :-D, excellent!

The puzzle of August is live at

First, you should copy/paste the URL proposed in the puzzle – – into a browser to see what it looks like.

We can see a pretty straight-forward reply formatted in JSON. Nice! This allows PowerShell versions as of 3.0 to use the built-in Invoke-WebRequest cmdlet to get the content of this webpage and the built-in *-Json cmdlets to convert the JSON content into a PowerShell object.
This also allows to solve the puzzle with a simple one-liner:

(iwr "").Content|
ConvertFrom-Json|ft *tude,con*,t*

With all commands and parameter names spelled out:

(Invoke-WebRequest -URI "").Content|
ConvertFrom-Json|Format-Table -Property *tude,con*,t*

That’s fairly easy if you have a recent version of PowerShell, isn’t it. Now, let’s think 2 minutes what you’d have done if you only had PowerShell version 2.0.

#requires -version 2.0
$o = New-Object -TypeName psobject
$raw = (New-Object Net.WebClient).DownloadString('')
$raw -split',' | ForEach-Object {
$r = ([regex]'{?"(?<property>.*)":"?(?<value>[a-zA-Z_0-9\.\s\\/]*)"?}?$').Matches($_) |
Select -Expand Groups | Select -Last 2 -Property Value
$o | Add-Member -Type NoteProperty -Name $(($r[0]).Value) -Value $(($r[1]).Value) -Force
$o | Format-Table -Property *tude,con*,t*
view raw SG201508.ps1 hosted with ❤ by GitHub

Fun? Ugly? Having a recent PowerShell version saves you a lot of time.

If you go to , you can read how to interact with the endpoint and that it offers a REST API, which means you can go down another route and use the built-in Invoke-RestMethod cmdlet.