Set Variables:
$username='testrobot'
$password='password'
$url='https://blog.kimconnect.com'
# Version 0.0.2 - return true or false, while keeping IE Open for further use
# This iteration also handles IE Protected mode errors
# Usage:
# 1. $ie=autologinSe "$url" "$username" "$password"
# 2. autologinSe $someUrlNoLogin
# 3. autologinSe "$url" "$username" "$password" -exitIeWhenDone $true
Run the Function:
function autologinSe{
param(
$url,
$username,
$password,
$usernameElementId='userNameInput',
$passwordElementId='passwordInput',
$submitButtonId='submitButton',
$exitIeWhenDone=$false
)
$ErrorActionPreference = 'continue'
# Initial validation
if(!$url){write-warning "No URL specified.";return $false}
function killInternetExplorer{
$ieInstances=(New-Object -COM 'Shell.Application').Windows()|?{$_.Name -like '*Internet Explorer*'}
$ieInstances|%{$_.Quit()
[Runtime.Interopservices.Marshal]::ReleaseComObject($_)
}
[GC]::Collect()
[GC]::WaitForPendingFinalizers()
}
function enableIeProtectedMode{
# $hives = 0..4|%{"HKLM:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\$_"}
$hives = 0..4|%{"HKCU:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\$_"}
$keyName='2500' # Key Name '2500' corresponds to 'Protected Mode' in IE
#Skipping zone 0 as that is the default local machine zone
$hives[1..4]|%{Set-ItemProperty -Path $_ -Name $keyName -Value 0}
$keys=$hives|%{Get-ItemProperty -Path $_}|select DisplayName, `
@{name='status';e={
if($_.$keyName -eq 0){'enabled'}
elseif($_.$keyName -eq 3){'disabled'}
else{'n/a'}
}}
write-host "IE Protected Mode Standardized Values:`r`n$($keys|out-string)"
}
function disableIeProtectedMode{
# $hives = 0..4|%{"HKLM:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\$_"}
$hives = 0..4|%{"HKCU:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\$_"}
$keyName='2500' # Key Name '2500' corresponds to 'Protected Mode' in IE
#Skipping zone 0 as that is the default local machine zone
$hives[1..4]|%{Set-ItemProperty -Path $_ -Name $keyName -Value 3}
$keys=$hives|%{Get-ItemProperty -Path $_}|select DisplayName, `
@{name='status';e={
if($_.$keyName -eq 0){'enabled'}
elseif($_.$keyName -eq 3){'disabled'}
else{'n/a'}
}}
write-host "IE Protected Mode Standardized Values:`r`n$($keys|out-string)"
}
function allowActiveX($zone='Trusted'){
#Source: https://learn.microsoft.com/en-us/previous-versions/troubleshoot/browsers/security-privacy/ie-security-zones-registry-entries
$zoneCode=switch($zone){
'My Computer'{0;break}
'Local Intranet'{1;break}
'Trusted'{2;break}
'Internet'{3;break}
'Restricted Sites'{4;break}
default{2}
}
#Reference table:
#Value Setting
#------------------------------
#0 My Computer
#1 Local Intranet Zone
#2 Trusted sites Zone
#3 Internet Zone
#4 Restricted Sites Zone
$hashMap=@{
'2702'=0 #ActiveX controls and plug-ins: Allow ActiveX Filtering = Enable (2702)
'1208'=0 #ActiveX controls and plug-ins: Allow previously unused ActiveX controls to run without prompt = Enable (1208)
'1209'=0 #ActiveX controls and plug-ins: Allow Scriptlets = Enable (1209)
'2201'=3 #ActiveX controls and plug-ins: Automatic prompting for ActiveX controls = Disable (2201)
'2000'=0 #ActiveX controls and plug-ins: Binary and script behaviors = Enable (2000)
'120A'=0 #Display video and animation on a webpage that does not use external media player = Enable (120A)
'1001'=0 #ActiveX controls and plug-ins: Download signed ActiveX controls = Enable (1001)
'1004'=0 #ActiveX controls and plug-ins: Download unsigned ActiveX controls = Enable (1004)
'1201'=0 #ActiveX controls and plug-ins: Initialize and script ActiveX controls not marked as safe for scripting = Enable (1201)
'120B'=3 #Only allow approved domains to use ActiveX without prompt = Disable (120B)
'1200'=0 #ActiveX controls and plug-ins: Run ActiveX controls and plug-ins = Enable (1200)
'1405'=0 #ActiveX controls and plug-ins: Script ActiveX controls marked as safe for scripting = Enable (1405)
}
$trustedDomains="HKCU:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\zones\$zoneCode"
$currentValues=Get-ItemProperty $trustedDomains
foreach ($item in $hashMap.GetEnumerator()) {
$key = $item.Key
$value = $item.Value
if($currentValues.$key -ne $value){
New-ItemProperty -Path $trustedDomains -Name $key -Value $value -PropertyType DWORD -Force
}
}
}
function addDomainToTrustedSites($url){
$httpType=.{[void]($url -match '^(https{0,1})');$matches[1]}
$domain=([uri]$url).Host
#$rootDomain=$domain.split('.')[-2..-1] -join '.' # This is assuming that the TLD is one-dotted (e.g. .com) not two-dotted (e.g. co.uk)
$rootDomain=.{$fragments=$domain.split('.')
$fragments[1..$($fragments.count)] -join '.'
}
write-host "Root domain detected`t: $rootDomain"
# The more advanced function to retrieve this value is at https://blog.kimconnect.com/powershell-extract-root-domain-from-url/
if ($rootDomain -notmatch '\.' -or $rootDomain -eq $env:USERDNSDOMAIN){
write-host "There's no need to add $url to the Trusted zone as it is local to this domain."
return $true
}
$dwordValue=2 # value of true correlates to 'enable'
$domainRegistryPath='HKCU:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap\Domains'
$domainRegistryPath2='HKCU:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap\EscDomains' #EscDomains key applies to those protocols that are affected by the Enhanced Security Configuration (ESC)
$null=New-Item -Path 'HKCU:\Software\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap' -ItemType File -Name 'EscDomains' -Force
$null=New-Item -Path "$domainRegistryPath" -ItemType File -Name "$rootDomain" -Force
$null=New-Item -Path "$domainRegistryPath2" -ItemType File -Name "$rootDomain" -Force
$null=Set-ItemProperty -Path "$domainRegistryPath\$rootDomain" -Name $httpType -Value $dwordValue
$null=Set-ItemProperty -Path "$domainRegistryPath2\$rootDomain" -Name $httpType -Value $dwordValue
# Also add {about:blank} record as that doesn't seem to have been added by default
if (!(test-path "$domainRegistryPath\blank")){
#New-ItemProperty -Path $trustedDomains -Name $key -Value $value -PropertyType DWORD -Force
$null=New-Item -Path "$domainRegistryPath" -ItemType File -Name 'blank'
$null=Set-ItemProperty -Path "$domainRegistryPath\blank" -Name 'about' -Value $dwordValue
}
if (!(test-path "$domainRegistryPath2\blank")){
$null=New-Item -Path "$domainRegistryPath2" -ItemType File -Name 'blank'
$null=Set-ItemProperty -Path "$domainRegistryPath2\blank" -Name 'about' -Value $dwordValue
}
# Also add {about:internet} record since it will stop a login when missing
if (!(test-path "$domainRegistryPath\internet")){
$null=New-Item -Path "$domainRegistryPath" -ItemType File -Name 'internet'
$null=Set-ItemProperty -Path "$domainRegistryPath\internet" -Name 'about' -Value $dwordValue
}
if (!(test-path "$domainRegistryPath2\internet")){
$null=New-Item -Path "$domainRegistryPath2" -ItemType File -Name 'internet'
$null=Set-ItemProperty -Path "$domainRegistryPath2\internet" -Name 'about' -Value $dwordValue
}
$valueAfterChanged=(Get-ItemProperty "$domainRegistryPath\$rootDomain")."$httpType"
$value2AfterChanged=(Get-ItemProperty "$domainRegistryPath2\$rootDomain")."$httpType"
if ($valueAfterChanged -eq 2 -and $value2AfterChanged -eq 2 ){
write-host "$rootDomain has been added to Internet Explorer"
return $true
}
else{
write-warning "$rootDomain has NOT been added to Internet Explorer."
return $false
}
}
function includeSelenium{
Import-Module Selenium -ea SilentlyContinue
if (!(get-module selenium -EA SilentlyContinue)){
Start-job {
[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
if(!(Get-PackageProvider Nuget -ea SilentlyContinue)){Install-PackageProvider -Name NuGet -Force}
# Defining $ENV:ChocotaleyInstall so that it would be called by refreshenv
$ENV:ChocolateyInstall = Convert-Path "$((Get-Command choco).Path)\..\.."
Import-Module "$env:ChocolateyInstall\helpers\chocolateyProfile.psm1"
Install-Module Selenium -Force -Confirm:$False
} |Receive-Job -Wait
Update-SessionEnvironment
Import-Module Selenium
}
}
function invokeSelenium($url,$userName,$password,$usernameElementId,$passwordElementId,$submitButtonId){
$ErrorActionPreference = "Stop"
function closeSelenium($selenium){
if($selenium){
$selenium.close()
$selenium.quit()
}
}
function noLogin($url){
$seleniumIe = New-Object "OpenQA.Selenium.IE.InternetExplorerDriver"
$seleniumIe.Navigate().GoToURL($url)
$title=$seleniumIe.Title
write-host "Page reached: '$title'"
$trustedSiteError=$title -match '^Error'
if($trustedSiteError){
write-host "An site trust issue has been detected. Adding root domain to the trusted sites list to resolve this issue."
addDomainToTrustedSites $url
closeSelenium $seleniumIe
return $false
}
else{
return $seleniumIe
}
}
function login($url,$username,$password,$usernameElementId,$passwordElementId,$submitButtonId){
$seleniumIe = New-Object "OpenQA.Selenium.IE.InternetExplorerDriver"
$seleniumIe.Navigate().GoToURL($url)
$userField=$seleniumIe.FindElementById($usernameElementId)
$userField.clear()
$userField.SendKeys($username)
$passwordField=$seleniumIe.FindElementById($passwordElementId)
$passwordField.SendKeys('')
$passwordField.clear()
$passwordField.SendKeys($password)
$submitButton=$seleniumIe.FindElementById($submitButtonId)
$submitButton.Click()
$title=$seleniumIe.Title
write-host "Page reached: '$title'"
$trustedSiteError=$title -match '^Error'
if($trustedSiteError){
write-warning "A site trust issue has been detected."
closeSelenium $seleniumIe
return $false
}else{
return $seleniumIe
}
}
try{
$null=allowActiveX
$isLogin=$userName,$password,$usernameElementId,$passwordElementId,$submitButtonId|?{!(!$_)}
if($isLogin){
write-host "Login to $url as $userName..."
$ie=login $url $userName $password $usernameElementId $passwordElementId $submitButtonId
}else{
write-host "Accesing $url without login..."
$ie=nologin $url
}
return $ie
}
catch{
Write-Warning $Error[0].Exception.Message
return $false
}
}
try{
write-host "Username`t: $username`r`nPassword`t: $(!(!$password))`r`nusernameElementId`t: $usernameElementId`r`npasswordElementId`t: $passwordElementId`r`nsubmitButtonId`t: $submitButtonId"
$null=includeSelenium
$null=disableIeProtectedMode
$null=addDomainToTrustedSites $url
if(get-module selenium -ea SilentlyContinue){
$isLogin=$userName,$password,$usernameElementId,$passwordElementId,$submitButtonId|?{!(!$_)}
if($isLogin){
$selenium=invokeSelenium $url $userName $password $usernameElementId $passwordElementId $submitButtonId
}else{
write-host "No username or password are given. Proceeding to access only the provided URL."
$selenium=invokeSelenium $url
}
}else{
write-warning "Please manually verify that the Selenium module is installed before retrying this function."
}
if($selenium){
if($exitIeWhenDone){
$null=killInternetExplorer
return $true
}else{
return $selenium
}
}else{
write-warning "There were errors preventing a successful login."
return $false
}
}
catch {
write-warning "$_"
return $false
}
# Note on a common error:
#New-Object : Exception calling ".ctor" with "0" argument(s): "Unexpected error launching Internet Explorer. Protected
#Mode settings are not the same for all zones. Enable Protected Mode must be set to the same value (enabled or
#disabled) for all zones. (SessionNotCreated)"
#At line:1 char:15
#+ $seleniumIe = New-Object "OpenQA.Selenium.IE.InternetExplorerDriver"
#+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# + CategoryInfo : InvalidOperation: (:) [New-Object], MethodInvocationException
# + FullyQualifiedErrorId : ConstructorInvokedThrowException,Microsoft.PowerShell.Commands.NewObjectCommand
# Solution: either DISABLE or ENABLE Protected mode for ALL ZONES
}
$ie=autoLoginSe $url $username $password
Deprecated version:
# Version 0.0.1 - function to return true or false, and close IE afterward
function autologinSe{
param(
$url,
$username,
$password,
$usernameElementId='userNameInput',
$passwordElementId='passwordInput',
$submitButtonId='submitButton'
)
$ErrorActionPreference = "Stop"
function killInternetExplorer{
$ieInstances=(New-Object -COM 'Shell.Application').Windows()|?{$_.Name -like '*Internet Explorer*'}
$ieInstances|%{$_.Quit()
[Runtime.Interopservices.Marshal]::ReleaseComObject($_)
}
[GC]::Collect()
[GC]::WaitForPendingFinalizers()
}
try{
killInternetExplorer|out-null
if (!(get-module selenium -EA SilentlyContinue)){
[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
Install-Module Selenium -Force
}
Import-Module Selenium
$seleniumIe = New-Object "OpenQA.Selenium.IE.InternetExplorerDriver"
$seleniumIe.Navigate().GoToURL($url)
$userField=$seleniumIe.FindElementById($usernameElementId)
$userField.SendKeys($username)
$passwordField=$seleniumIe.FindElementById($passwordElementId)
$passwordField.SendKeys($password)
$submitButton=$seleniumIe.FindElementById($submitButtonId)
$submitButton.Click()
$title=$seleniumIe.Title
write-host "Page reached: '$title'"
$seleniumIe.close()
$seleniumIe.quit()
$not404=$title -notmatch '^404|^Error'
if($not404){return $true}
else{return $false}
}
catch{
write-warning "$($error[0])"
return $false
}
# Troubleshooting:
#New-Object : Exception calling ".ctor" with "0" argument(s): "Unexpected error launching Internet Explorer. Protected
#Mode settings are not the same for all zones. Enable Protected Mode must be set to the same value (enabled or
#disabled) for all zones. (SessionNotCreated)"
#At line:1 char:15
#+ $seleniumIe = New-Object "OpenQA.Selenium.IE.InternetExplorerDriver"
#+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# + CategoryInfo : InvalidOperation: (:) [New-Object], MethodInvocationException
# + FullyQualifiedErrorId : ConstructorInvokedThrowException,Microsoft.PowerShell.Commands.NewObjectCommand
# Solution: either DISABLE or ENABLE Protected mode for ALL ZONES
}
autoLoginSe $url $username $password
# Troubleshooting:
#New-Object : Exception calling ".ctor" with "0" argument(s): "Unexpected error launching Internet Explorer. Protected
#Mode settings are not the same for all zones. Enable Protected Mode must be set to the same value (enabled or
#disabled) for all zones. (SessionNotCreated)"
#At line:1 char:15
#+ $seleniumIe = New-Object "OpenQA.Selenium.IE.InternetExplorerDriver"
#+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# + CategoryInfo : InvalidOperation: (:) [New-Object], MethodInvocationException
# + FullyQualifiedErrorId : ConstructorInvokedThrowException,Microsoft.PowerShell.Commands.NewObjectCommand
# Solution: either DISABLE or ENABLE Protected mode for ALL ZONES
Categories: