Package proxy provides support for a variety of protocols to proxy network data.
import "golang.org/x/net/proxy"// Direct implements Dialer by making network connections directly
var Direct = direct{}Direct implements Dialer by making network connections directly using net.Dial or net.DialContext.
// Dialer is a means to establish a connection
type Dialer interface {
Dial(network, addr string) (c net.Conn, err error)
}
// ContextDialer dials using a context
type ContextDialer interface {
DialContext(ctx context.Context, network, address string) (net.Conn, error)
}
// Auth contains authentication parameters that specific Dialers may require
type Auth struct {
User string
Password string
}// PerHost directs connections to a default Dialer unless the host name matches an exception
type PerHost struct {
// Has unexported fields
}
func NewPerHost(defaultDialer, bypass Dialer) *PerHost
func (p *PerHost) AddFromString(s string)
func (p *PerHost) AddHost(host string)
func (p *PerHost) AddIP(ip net.IP)
func (p *PerHost) AddNetwork(net *net.IPNet)
func (p *PerHost) AddZone(zone string)
func (p *PerHost) Dial(network, addr string) (c net.Conn, err error)
func (p *PerHost) DialContext(ctx context.Context, network, addr string) (c net.Conn, err error)// Dial works like DialContext but using a dialer returned by FromEnvironment
func Dial(ctx context.Context, network, address string) (net.Conn, error)
// FromEnvironment returns the dialer specified by proxy-related environment variables
func FromEnvironment() Dialer
// FromEnvironmentUsing returns the dialer using the provided forwarding Dialer
func FromEnvironmentUsing(forward Dialer) Dialer
// FromURL returns a Dialer given a URL specification and an underlying Dialer
func FromURL(u *url.URL, forward Dialer) (Dialer, error)
// SOCKS5 returns a Dialer that makes SOCKSv5 connections
func SOCKS5(network, address string, auth *Auth, forward Dialer) (Dialer, error)
// RegisterDialerType takes a URL scheme and a function to generate Dialers
func RegisterDialerType(scheme string, f func(*url.URL, Dialer) (Dialer, error))Dial works like DialContext on net.Dialer but using a dialer returned by FromEnvironment. The passed ctx is only used for returning the Conn, not the lifetime of the Conn. A Conn returned from a successful Dial after the context has been cancelled will be immediately closed.
SOCKS5 returns a Dialer that makes SOCKSv5 connections to the given address with an optional username and password. See RFC 1928 and RFC 1929.
import (
"context"
"golang.org/x/net/proxy"
"time"
)
func dialWithEnvProxy(address string) error {
// Get dialer from environment (HTTP_PROXY, HTTPS_PROXY, SOCKS_PROXY, etc.)
dialer := proxy.FromEnvironment()
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()
conn, err := dialer.Dial("tcp", address)
if err != nil {
return err
}
defer conn.Close()
// Use connection...
return nil
}func connectViaSOCKS5(targetAddr string) error {
// Create SOCKS5 dialer
auth := &proxy.Auth{
User: "username",
Password: "password",
}
dialer, err := proxy.SOCKS5("tcp", "proxy.example.com:1080", auth, proxy.Direct)
if err != nil {
return err
}
// Connect to target through SOCKS5 proxy
conn, err := dialer.Dial("tcp", targetAddr)
if err != nil {
return err
}
defer conn.Close()
// Use connection...
return nil
}func setupPerHostProxy() (proxy.Dialer, error) {
// Create SOCKS5 dialer for proxy
proxyDialer, err := proxy.SOCKS5("tcp", "proxy.example.com:1080", nil, proxy.Direct)
if err != nil {
return nil, err
}
// Create per-host dialer
perHost := proxy.NewPerHost(proxyDialer, proxy.Direct)
// Add exceptions (these will bypass the proxy)
perHost.AddHost("localhost")
perHost.AddZone("internal.company.com")
perHost.AddIP(net.ParseIP("192.168.1.100"))
perHost.AddFromString("10.0.0.0/8,172.16.0.0/12,192.168.0.0/16")
return perHost, nil
}
// Usage:
// dialer, err := setupPerHostProxy()
// conn, err := dialer.Dial("tcp", "example.com:80") // Uses proxy
// conn, err := dialer.Dial("tcp", "internal.company.com:80") // Bypasses proxyfunc registerCustomProxy() {
proxy.RegisterDialerType("myproxy", func(u *url.URL, forward proxy.Dialer) (proxy.Dialer, error) {
// Return custom dialer implementation
return &myCustomDialer{
proxyURL: u,
forward: forward,
}, nil
})
}
// Now "myproxy://..." URLs can be used with FromURLimport "net/url"
func dialViaURL(proxyURL, targetAddr string) error {
u, err := url.Parse(proxyURL)
if err != nil {
return err
}
dialer, err := proxy.FromURL(u, proxy.Direct)
if err != nil {
return err
}
conn, err := dialer.Dial("tcp", targetAddr)
if err != nil {
return err
}
defer conn.Close()
// Use connection...
return nil
}
// Usage:
// dialViaURL("socks5://proxy.example.com:1080", "target.example.com:80")