Product: PowerShell Universal
Version: 5.5.2
I’m running PSU on Windows Server 2022 and I’m having trouble connecting to the web as we are using a web proxy in our company. I’ve managed to pin down the issue a bit but it feels very much like a hack solution and there must be a proper way to solve this. Hope someone here has the answer.
The problem
In short, without the proxy configuration, powershell and PSU can’t connect to the internet. I noticed this in the error log
[WRN][Universal.Server.Services.UpdateCheckService] Failed to check for updates.
System.Net.Http.HttpRequestException: A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond. (imsreleases.blob.core.windows.net:443)
---> System.Net.Sockets.SocketException (10060): A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond.
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.ThrowException(SocketError error, CancellationToken cancellationToken)
but also in the Module section, as I can’t search the PSGallery for modules (show no results).
Lastly, I cannot run Invoke-WebRequests in Powershell, unless I specificy run them like this.
Invoke-WebRequest -Proxy "http://proxy:3128" "https://google.com"
The partial solution
I come from a linux background so forgive me if I am missing something simple but setting the proxy system wide doesn’t seem to be straightforward in windows.
The following changes had no impact on the PSU service or scripts, despite multiple blogs / articles claiming otherwise.
- Setting the proxy with
netsh winhttp proxy
- it’s set but it doesn’t affect PSU - Verifying the proxy is set with
Get-WinHttpProxy
- again, it’s set but no dice. - Setting global ENV vars for
http_proxy
,https_proxy
,no_proxy
both lower and upper case
The only thing that changed something was settting the proxy as registry settings in HKLM to make them system wide (instead of Current User, which is what happens if you use the GUI).
$proxy="HKLM:\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings"
Set-ItemProperty -Path $proxy -Name ProxySettingsPerUser -Value 0
Set-ItemProperty -Path $proxy -Name ProxyEnable -Value 1
Set-ItemProperty -Path $proxy -Name ProxyServer -Value "http://proxy:3128"
Set-ItemProperty -Path $proxy -Name ProxyOverride -Value "localhost;127.0.0.1;*.internaldomain.tld;<local>"
Set-ItemProperty -Path $proxy -Name AutoDetect -Value 0
Get-Item $proxy
Hive: HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion
Name Property
---- --------
Internet Settings CallLegacyWCMPolicies : 0
ProxySettingsPerUser : 0
AutoDetect : 0
ProxyServer : http://proxy:3128
ProxyOverride : localhost;127.0.0.1;*.internaldomain.tld;<local>
ProxyEnable : 1
This had the effect, that searches in the Module section are working, meaning that the PSU service now seems to connect to the internet / PSgallery just fine.
The hack solution
The remaining issue is, that the powershell scripts are not using none of these settings for reasons I have yet to figure out.
Setting the proxy in powershel manually with the following command seems to solve the issue.
#[System.Net.Http.HttpClient]::DefaultProxy = New-Object System.Net.WebProxy('http://proxy:3128',$true,"localhost;127.0.0.1;*.internaldomain.tld;<local>")
In the same way, the following command shows if the proxy is set (for powershell). Before I tried the command above, the [System.Net.Http.HttpClient]::DefaultProxy
would always return nothing.
[System.Net.Http.HttpClient]::DefaultProxy
Address : http://proxy:3128/
BypassProxyOnLocal : True
BypassList : {localhost;127.0.0.1;*.internaldomain.tld;<local>}
BypassArrayList : {localhost;127.0.0.1;*.internaldomain.tld;<local>}
Credentials :
UseDefaultCredentials : False
Adding the command above to a Environment startup script doesn’t solve the problem. For now I have to run this command in every script that connects to the internet (or use the -proxy switch for Invoke-WebRequest) which is not a real solution.
The real solution?
I’m hoping for a solution that will set the proxy system wide in a way that powershell honors it, regardless of user, environment, version or whatelse there could be.
If anyone encountered this or has an idea, I’m all ears!