5

I have a work computer running on Windows in a corporate environment with an authenticating proxy server for outgoing connections to the internet. I don't know how it's configured, but many tools fail to connect, mainly that type like npm (packages in the Atom editor), NuGet, PowerShellGet, etc. I even had to configure my browser (Vivaldi) to use the direct connection, because I couldn't, for example, sign in on some websites, even though it was working in MS Edge.

The HTTP error is usually (407) Proxy Authentication Required.

The system-wide proxy server in Windows is being configured by some periodically executed script and I cannot do anything about it.

The solution, or rather a workaround, is to individually configure all applications that have issues with connections to bypass the proxy (use the direct connection to the internet). I have managed to do that for almost everything I needed, but I didn't succeed with Powershell Core so far.

BTW I'm not sure what's the point of that proxy when you can simply bypass it, it's just making regular work harder on that computer and it's wasting my time and company's money.

So far, I have found out the following.

PowerShellGet's Find-Module fails with the error:

Unable to resolve package source 'https://www.powershellgallery.com/api/v2'

A simple web request fails with the error "Cache Access Denied":

Invoke-WebRequest https://google.com

But succeeds when it's forced to bypass the proxy:

Invoke-WebRequest https://google.com -NoProxy

netsh winhttp show proxy says "Direct access (no proxy server).", but the following command returns an actual proxy:

([System.Net.WebRequest]::GetSystemWebproxy()).GetProxy("https://google.com")

Also, the following command returns false:

([System.Net.WebRequest]::GetSystemWebproxy()).IsBypassed("https://google.com")

I have done quite extensive research and found out that it should be possible to configure WebRequest to use the direct connection by setting the default proxy to null, but it didn't help:

[System.Net.WebRequest]::DefaultWebProxy = $null

I would appreciate if anyone has any other idea.

Update

I have found out that I can actually use my domain account to authenticate on the proxy server:

Invoke-WebRequest https://google.com -ProxyUseDefaultCredentials -Proxy http://proxy

So that would be an alternative to the proxy bypass configuration. I just don't know how to set credentials for all requests made by Powershell. I don't understand why the Windows system proxy is not configured to use my account to authenticate.

I have tried to configure WebRequest::DefaultWebProxy to use the proxy server and authenticate on it using my domain account credentials, but it didn't work:

[System.Net.WebRequest]::DefaultWebProxy 
    = New-Object System.Net.WebProxy('http://proxy')
[System.Net.WebRequest]::DefaultWebProxy.Credentials
    = [System.Net.CredentialCache]::DefaultNetworkCredentials
3
  • Just some notes: WinHTTP is not what you’re looking for. Not everything in PS uses WebRequest to do HTTP requests. Even then, they may set a proxy “manually”. If you can bypass the corporate proxy by just disabling the proxy settings, the proxy is pointless and should be removed.
    – Daniel B
    Commented May 18, 2021 at 8:04
  • Exactly! I also see that proxy completely pointless with the current network configuration. I guess, I'll keep silent, so they don't make it even worse. 😉 As I have found out (see my answer), Powershell (possibly just the Core) is using System.Net.Http.HttpClient rather than System.Net.WebRequest to make web requests. A proper configuration of the HttpClient.DefaultProxy has fixed my issue. Commented May 18, 2021 at 13:04
  • Since it seems, by your discovery, your org/ent is really not controlling traffic, then this is, as noted security theater, potentially just to tick off a policy checkbox; thus they should just have a transparent proxy set vs auth. I see this all the time in my engagements/pen-tests/audits or just inexperienced/misguided admins. Yet, not informing them, if the risk is an issue, it not really prudent, as someone can cause real damage with some activities. As long as your org/ent accepts that risk, that's on them, not you.
    – postanote
    Commented May 18, 2021 at 21:16

3 Answers 3

4

Finally, after several hours of researching and messing around, I was able to solve my issue thanks to this GitHub issue comment!

I don't know the background, but it looks like Powershell Core is actually using System.Net.Http.HttpClient rather than System.Net.WebRequest for making web requests.

When I have learned that, it was quite easy to configure HttpClient's default proxy.

1. Manually Configure HttpClient.DefaultProxy

Proxy Bypassing

To bypass the proxy (use the direct connection), set it to null:

[System.Net.Http.HttpClient]::DefaultProxy = New-Object System.Net.WebProxy($null)

I have added it to my Powershell profile and all connections made by Powershell started to work.

Configure Specific Proxy Server

To configure an actuall proxy server instead, use the following command:

[System.Net.Http.HttpClient]::DefaultProxy = New-Object System.Net.WebProxy('http://proxy', $true)

Configure Proxy Authentication

In case it's an authenticating proxy, you have to configure credentials to be used for the proxy authentication. The following command will use the credentials of your domain account under which you're currently logged in to Windows:

[System.Net.Http.HttpClient]::DefaultProxy.Credentials = [System.Net.CredentialCache]::DefaultCredentials

2. Configure Default Proxy using Environment Variable

An alternative solution is to use an environment variable. According to the documentation, HttpClient is actually using the following variables to initialize the default proxy, if they're defined:

  • HTTP_PROXY for HTTP requests
  • HTTPS_PROXY for HTTPS requests
  • ALL_PROXY for both HTTP and HTTPS
  • NO_PROXY may contain a comma-separated list of hostnames excluded from proxying

An example usage:

ALL_PROXY='http://proxy:1234'

And if you need to pass credentials:

ALL_PROXY='http://username:password@proxy:1234'

This solution is supported by a wider range of applications, so if it's better or worse than the previous solution depends on what exactly you want to configure, just Powershell or also other applications.

1
  • Decision made above our pay grade often forces creative approaches. I really tell customers, sure, protect your org and users, but if you make stuff hard without focus, then they will try to figure a way to work around what you did, and thus what you did becomes moot. It's better for risk management/security teams to survey dev teams specifically for their needs and have a plan to allow them to do their needed work. In my engagements, I use 'Server and Domain Isolation' techniques to make sure each zone can do what they need, without impact to others or the org-wide.
    – postanote
    Commented May 18, 2021 at 21:26
3

Based on David Ferenczy Rogožan's excellent answer and research, I was able to get it working, but in my case I had to do (note the slight difference from above):

[System.Net.HttpWebRequest]::DefaultWebProxy = New-Object System.Net.WebProxy($null)
0

As for this… it should be possible to configure WebRequest to use the direct connection by setting the default proxy to null …, as you've found, not in your corporate infrastructure.

What you have is a GPO, that is forced onto your workstation, that forces all internet egress network traffic thru a filtering/proxied gateway.

See this How to Force Proxy Settings Via Group Policy - TechNet Articles - United States (English) - TechNet Wiki (microsoft.com) for details. https://social.technet.microsoft.com/wiki/contents/articles/5156.how-to-force-proxy-settings-via-group-policy.aspx

Your employer is controlling and monitoring potentially all ingress/egress network traffic from all domain-joined systems.

Risk Management/Security policy will rule. Any modern filtering gateway has specific controls that your organization/enterprise uses for their defined risk control reasons.

So, this is not a PowerShell feature or code issue; it’s a network restriction. So, no getting around it. Regardless of what tool you are using. You must provide identity/credentials to be allowed outbound.

You can look at your browser settings to see the proxy informant or they could be using PAC files as well.

See this: What is a PAC file? (websense.com) for details. https://www.websense.com/content/support/library/web/v76/pac_file_best_practices/PAC_explained.aspx

The reason you do not get this prompt doing normal browsing is that your cased credentials/network token is used. If you try and go around that, you get prompted, per corporate policy.

Trying to circumvent your employer's risk management/security policies will generate RPE/CLM (resume producing event / career-limiting move) for you, and potentially legal action, depending on what you were doing.

7
  • 1
    OP indicates that bypassing the proxy does, in fact, work: “I have managed to do that for almost everything I needed”
    – Daniel B
    Commented May 18, 2021 at 8:06
  • The OP specifically said ... I can actually use my domain account to authenticate on the proxy server: This is not bypassing. It's explicit authentication to the proxy vs implicit auth vs internal token. OP can only disable proxy if it is not enforced. by GPO. The OP could try and set needed credentials in the Windows Credential Store and call from there as needed.
    – postanote
    Commented May 18, 2021 at 10:25
  • You’re confusing two statements; one is about other software, the one you cite is about experiments in PowerShell. You cannot enforce a proxy in third-party software using a GPO. Neither can all software use NTLM authentication with proxies.
    – Daniel B
    Commented May 18, 2021 at 11:55
  • @postanote Thanks for your opinion. Applications can successfully connect to the internet when I configure them to: 1. bypass the proxy (use the direct connection) OR 2. use my domain credentials to authenticate on the already configured (system-wide) proxy server. Sometimes it wasn't easy or straitforward, but I have managed to successfully configure several applications. My issue was that I was unable to do that in Powershell 7. Fortunately, after several hours of investigation, I have found the way, see my answer. Commented May 18, 2021 at 12:11
  • I don't understand what's the point of such a network configuration. It would make sense to have an authenticating proxy for all outgoing connections and have all direct connections forbidden. What's the point of such proxy, when it's so easy to go around (bypass) it? Also, they configured my system to use the proxy, but not to use my domain credentials for authentication. That's actually causing applications to fail to connect. I have to configure every application individually. Is there any reason for that or is it just a misconfiguration? Commented May 18, 2021 at 12:24

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .