Copyright 2011 The Go Authors. All rights reserved. Use of this source code is governed by a BSD-style license that can be found in the LICENSE file.
Package proxy provides support for a variety of protocols to proxy network data.
package proxy // import "golang.org/x/net/proxy"

import (
	
	
	
	
	
)
A Dialer is a means to establish a connection. Custom dialers should also implement ContextDialer.
Dial connects to the given address via the proxy.
	Dial(network, addr string) (c net.Conn, err error)
}
Auth contains authentication parameters that specific Dialers may require.
type Auth struct {
	User, Password string
}
FromEnvironment returns the dialer specified by the proxy-related variables in the environment and makes underlying connections directly.
FromEnvironmentUsing returns the dialer specify by the proxy-related variables in the environment and makes underlying connections using the provided forwarding Dialer (for instance, a *net.Dialer with desired configuration).
func ( Dialer) Dialer {
	 := allProxyEnv.Get()
	if len() == 0 {
		return 
	}

	,  := url.Parse()
	if  != nil {
		return 
	}
	,  := FromURL(, )
	if  != nil {
		return 
	}

	 := noProxyEnv.Get()
	if len() == 0 {
		return 
	}

	 := NewPerHost(, )
	.AddFromString()
	return 
}
proxySchemes is a map from URL schemes to a function that creates a Dialer from a URL with such a scheme.
RegisterDialerType takes a URL scheme and a function to generate Dialers from a URL with that scheme and a forwarding Dialer. Registered schemes are used by FromURL.
func ( string,  func(*url.URL, Dialer) (Dialer, error)) {
	if proxySchemes == nil {
		proxySchemes = make(map[string]func(*url.URL, Dialer) (Dialer, error))
	}
	proxySchemes[] = 
}
FromURL returns a Dialer given a URL specification and an underlying Dialer for it to make network requests.
func ( *url.URL,  Dialer) (Dialer, error) {
	var  *Auth
	if .User != nil {
		 = new(Auth)
		.User = .User.Username()
		if ,  := .User.Password();  {
			.Password = 
		}
	}

	switch .Scheme {
	case "socks5", "socks5h":
		 := .Hostname()
		 := .Port()
		if  == "" {
			 = "1080"
		}
		return SOCKS5("tcp", net.JoinHostPort(, ), , )
	}
If the scheme doesn't match any of the built-in schemes, see if it was registered by another package.
	if proxySchemes != nil {
		if ,  := proxySchemes[.Scheme];  {
			return (, )
		}
	}

	return nil, errors.New("proxy: unknown scheme: " + .Scheme)
}

var (
	allProxyEnv = &envOnce{
		names: []string{"ALL_PROXY", "all_proxy"},
	}
	noProxyEnv = &envOnce{
		names: []string{"NO_PROXY", "no_proxy"},
	}
)
envOnce looks up an environment variable (optionally by multiple names) once. It mitigates expensive lookups on some platforms (e.g. Windows). (Borrowed from net/http/transport.go)
type envOnce struct {
	names []string
	once  sync.Once
	val   string
}

func ( *envOnce) () string {
	.once.Do(.init)
	return .val
}

func ( *envOnce) () {
	for ,  := range .names {
		.val = os.Getenv()
		if .val != "" {
			return
		}
	}
}
reset is used by tests
func ( *envOnce) () {
	.once = sync.Once{}
	.val = ""