├── .gitignore ├── .travis.yml ├── LICENSE ├── Makefile ├── README.md ├── cmd └── socks5proxy │ ├── gen.sh │ └── socks5.go ├── connect.go ├── connect_test.go ├── dial.go ├── glide.lock ├── glide.yaml ├── init.go ├── init_test.go ├── proxy.conf ├── proxy.sh ├── proxy_test.conf ├── socks5server └── server.go ├── test.go └── vendor ├── github.com ├── armon │ └── go-socks5 │ │ ├── .gitignore │ │ ├── .travis.yml │ │ ├── LICENSE │ │ ├── README.md │ │ ├── auth.go │ │ ├── auth_test.go │ │ ├── credentials.go │ │ ├── credentials_test.go │ │ ├── request.go │ │ ├── request_test.go │ │ ├── resolver.go │ │ ├── resolver_test.go │ │ ├── ruleset.go │ │ ├── ruleset_test.go │ │ ├── socks5.go │ │ └── socks5_test.go ├── davecgh │ └── go-spew │ │ ├── LICENSE │ │ └── spew │ │ ├── bypass.go │ │ ├── bypasssafe.go │ │ ├── common.go │ │ ├── common_test.go │ │ ├── config.go │ │ ├── doc.go │ │ ├── dump.go │ │ ├── dump_test.go │ │ ├── dumpcgo_test.go │ │ ├── dumpnocgo_test.go │ │ ├── example_test.go │ │ ├── format.go │ │ ├── format_test.go │ │ ├── internal_test.go │ │ ├── internalunsafe_test.go │ │ ├── spew.go │ │ └── spew_test.go ├── pmezard │ └── go-difflib │ │ ├── LICENSE │ │ └── difflib │ │ ├── difflib.go │ │ └── difflib_test.go └── stretchr │ └── testify │ ├── LICENCE.txt │ ├── LICENSE │ ├── assert │ ├── assertion_format.go │ ├── assertion_format.go.tmpl │ ├── assertion_forward.go │ ├── assertion_forward.go.tmpl │ ├── assertions.go │ ├── assertions_test.go │ ├── doc.go │ ├── errors.go │ ├── forward_assertions.go │ ├── forward_assertions_test.go │ ├── http_assertions.go │ └── http_assertions_test.go │ ├── require │ ├── doc.go │ ├── forward_requirements.go │ ├── forward_requirements_test.go │ ├── require.go │ ├── require.go.tmpl │ ├── require_forward.go │ ├── require_forward.go.tmpl │ ├── requirements.go │ └── requirements_test.go │ └── vendor │ └── github.com │ ├── davecgh │ └── go-spew │ │ ├── LICENSE │ │ └── spew │ │ ├── bypass.go │ │ ├── bypasssafe.go │ │ ├── common.go │ │ ├── config.go │ │ ├── doc.go │ │ ├── dump.go │ │ ├── format.go │ │ └── spew.go │ └── pmezard │ └── go-difflib │ ├── LICENSE │ └── difflib │ └── difflib.go └── golang.org └── x └── net ├── LICENSE ├── PATENTS ├── context ├── context.go ├── context_test.go ├── go17.go ├── pre_go17.go └── withtimeout_test.go └── proxy ├── direct.go ├── per_host.go ├── per_host_test.go ├── proxy.go ├── proxy_test.go └── socks5.go /.gitignore: -------------------------------------------------------------------------------- 1 | libsocks5connect.h 2 | libsocks5connect.so 3 | server 4 | nohup.out 5 | cmd/socks5proxy/bin.go 6 | cmd/socks5proxy/socks5proxy 7 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: go 2 | sudo: false 3 | services: mongodb 4 | go: 5 | - 1.6.x 6 | - 1.7.x 7 | - 1.8.x 8 | - 1.9.x 9 | - 1.10.x 10 | - 1.11.x 11 | - tip 12 | 13 | script: 14 | - make test 15 | - ./proxy.sh -f proxy_test.conf mongo --quiet --eval 'printjson(db.version())' 16 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2017 Ma Weiwei 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | GIT_VERSION := $(shell git rev-parse HEAD) 2 | all: 3 | go build -i -ldflags "-w -s -X 'main.version=git:$(GIT_VERSION)'" -buildmode=c-shared -o libsocks5connect.so 4 | cd ./cmd/socks5proxy && go generate && go build 5 | 6 | clean: 7 | rm libsocks5connect.so 8 | rm libsocks5connect.h 9 | 10 | update-dep: 11 | go get -v github.com/Masterminds/glide 12 | go get github.com/sgotti/glide-vc 13 | glide update 14 | glide vc 15 | 16 | runSocks5Server: 17 | go build socks5server/server.go 18 | ./server & 19 | 20 | export socks5_proxy:=127.0.0.1:1080 21 | export not_proxy:= 22 | export proxy_timeout_ms:=1000 23 | export proxy_no_log:=false 24 | 25 | test: all runSocks5Server 26 | ls -lh libsocks5connect.so cmd/socks5proxy/socks5proxy 27 | go test -v -tags test -cover 28 | ./proxy.sh -f proxy_test.conf python2 -c 'import urllib2;print(len(urllib2.urlopen("http://golang.org").read()))' 29 | ./proxy.sh -f proxy_test.conf curl -I -L http://golang.org 30 | ./cmd/socks5proxy/socks5proxy python2 -c 'import urllib2;print(len(urllib2.urlopen("http://golang.org").read()))' 31 | ./cmd/socks5proxy/socks5proxy curl -I -L http://golang.org 32 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # libsocks5connect 2 | 3 | [![Build Status](https://travis-ci.org/ma6174/libsocks5connect.svg?branch=master)](https://travis-ci.org/ma6174/libsocks5connect) 4 | 5 | ### install 6 | 7 | ``` 8 | git clone https://github.com/ma6174/libsocks5connect.git && cd libsocks5connect && make 9 | ``` 10 | 11 | ### config 12 | 13 | ``` 14 | $ cat proxy.conf 15 | export socks5_proxy=127.0.0.1:7070,localhost:1080 16 | export not_proxy=127.0.0.0/8,192.168.1.0/24 17 | export proxy_timeout_ms=1000 18 | export proxy_no_log=false 19 | export libsocks5connect=./libsocks5connect.so 20 | ``` 21 | 22 | ### use 23 | 24 | ``` 25 | ./proxy.sh -f proxy.conf python2 -c 'import urllib2;print(urllib2.urlopen("http://google.com").read())' 26 | ``` 27 | -------------------------------------------------------------------------------- /cmd/socks5proxy/gen.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | echo -e 'package main\n' > bin.go 4 | echo -e 'var libmd5 = "'`md5sum ../../libsocks5connect.so | awk '{print $1}'`'"' >> bin.go 5 | echo -e 'var lib = []byte{' >> bin.go 6 | cat ../../libsocks5connect.so | gzip | xxd -i | sed "s/[^,]$/}/g" >> bin.go 7 | -------------------------------------------------------------------------------- /cmd/socks5proxy/socks5.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "bytes" 5 | "compress/gzip" 6 | "io" 7 | "os" 8 | "os/exec" 9 | "path/filepath" 10 | "runtime" 11 | "syscall" 12 | ) 13 | 14 | //go:generate bash gen.sh 15 | 16 | func libExt() string { 17 | switch runtime.GOOS { 18 | case "darwin": 19 | return ".dylib" 20 | case "linux": 21 | return ".so" 22 | } 23 | return "" 24 | } 25 | 26 | var libFile = filepath.Join("/tmp", "libsocks5connect."+libmd5+libExt()) 27 | 28 | func writeLib() { 29 | _, err := os.Stat(libFile) 30 | if !os.IsNotExist(err) { 31 | return 32 | } 33 | f, err := os.OpenFile(libFile, os.O_WRONLY|os.O_CREATE|os.O_EXCL, 0666) 34 | if err != nil { 35 | return 36 | } 37 | defer f.Close() 38 | r, err := gzip.NewReader(bytes.NewReader(lib)) 39 | if err != nil { 40 | return 41 | } 42 | io.Copy(f, r) 43 | } 44 | 45 | func main() { 46 | writeLib() 47 | cmd := exec.Command(os.Args[1], os.Args[2:]...) 48 | cmd.Stdin = os.Stdin 49 | cmd.Stdout = os.Stdout 50 | cmd.Stderr = os.Stderr 51 | cmd.Env = os.Environ() 52 | switch runtime.GOOS { 53 | case "darwin": 54 | cmd.Env = append(cmd.Env, "DYLD_FORCE_FLAT_NAMESPACE=1") 55 | cmd.Env = append(cmd.Env, "DYLD_INSERT_LIBRARIES="+libFile) 56 | case "linux": 57 | cmd.Env = append(cmd.Env, "LD_PRELOAD="+libFile) 58 | } 59 | err := cmd.Run() 60 | if err != nil { 61 | if errno, ok := err.(syscall.Errno); ok { 62 | os.Exit(int(errno)) 63 | } else { 64 | os.Exit(-1) 65 | } 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /connect.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | /* 4 | #include 5 | #include 6 | #include 7 | static inline int setErrno(int err) { 8 | if (err == 0) { 9 | return 0; 10 | } 11 | errno = err; 12 | return -1; 13 | } 14 | */ 15 | import "C" 16 | import ( 17 | "log" 18 | "net" 19 | "syscall" 20 | "time" 21 | "unsafe" 22 | 23 | "golang.org/x/net/proxy" 24 | ) 25 | 26 | func errno(err error) C.int { 27 | if err == nil { 28 | return 0 29 | } 30 | if errno, ok := err.(syscall.Errno); ok { 31 | return C.int(errno) 32 | } 33 | return C.int(-1) 34 | } 35 | 36 | //export connect_proxy 37 | func connect_proxy(fdc C.int, addr *C.struct_sockaddr, sockLen C.socklen_t) (ret C.int) { 38 | fd := int(fdc) 39 | var dialAddr *net.TCPAddr 40 | var sockAddr syscall.Sockaddr 41 | goAddr := (*syscall.RawSockaddr)(unsafe.Pointer(addr)) 42 | switch goAddr.Family { 43 | case syscall.AF_INET: 44 | addr4 := (*syscall.RawSockaddrInet4)(unsafe.Pointer(addr)) 45 | dialAddr = &net.TCPAddr{ 46 | IP: addr4.Addr[:], 47 | Port: int(addr4.Port<<8 | addr4.Port>>8), 48 | } 49 | sockAddr = &syscall.SockaddrInet4{ 50 | Addr: addr4.Addr, 51 | Port: int(addr4.Port<<8 | addr4.Port>>8), 52 | } 53 | default: 54 | log.Printf("[%d] syscall connect %+v", fd, addr) 55 | _, _, ret := syscall.Syscall(syscall.SYS_CONNECT, uintptr(fdc), 56 | uintptr(unsafe.Pointer(addr)), uintptr(sockLen)) 57 | return C.setErrno(C.int(ret)) 58 | } 59 | err := syscall.SetNonblock(fd, false) 60 | if err != nil { 61 | log.Printf("[fd:%v] syscall.SetNonblock failed: %v", fd, err) 62 | return C.setErrno(errno(err)) 63 | } 64 | opt, err := syscall.GetsockoptInt(fd, syscall.SOL_SOCKET, syscall.SO_TYPE) 65 | if err != nil { 66 | log.Printf("[fd:%v] syscall.GetsockoptInt failed: %v", fd, err) 67 | return C.setErrno(errno(err)) 68 | } 69 | var errCh = make(chan error, 1) 70 | var proxyUsed *ProxyAddr 71 | conn := NewFdConn(fd) 72 | defer conn.Close() 73 | if opt != syscall.SOCK_STREAM || config.GetProxyCount() == 0 || config.ShouldNotProxy(dialAddr.IP) { 74 | go func() { 75 | err := syscall.Connect(fd, sockAddr) 76 | if err == nil { 77 | log.Printf("[fd:%v] direct connect success: %v -> %v", fd, conn.LocalAddr(), dialAddr) 78 | } 79 | errCh <- err 80 | }() 81 | } else { 82 | proxyUsed = config.GetProxyAddr() 83 | go func() { 84 | err = syscall.Connect(fd, proxyUsed.Sockaddr()) 85 | if err != nil { 86 | log.Printf("[fd:%v] syscall.Connect failed: %v", fd, err) 87 | errCh <- err 88 | return 89 | } 90 | dialer, err := proxy.SOCKS5("", "", &proxyUsed.Auth, conn) 91 | if err != nil { 92 | log.Printf("[fd:%v] proxy.SOCKS5 failed: %v", fd, err) 93 | errCh <- err 94 | return 95 | } 96 | _, err = dialer.Dial("tcp", dialAddr.String()) 97 | if err != nil { 98 | log.Printf("[fd:%v] dialer Dial %v failed: %v", fd, dialAddr, err) 99 | errCh <- err 100 | return 101 | } 102 | log.Printf("[fd:%v] proxy connect success: %v -> %v -> %v", fd, conn.LocalAddr(), proxyUsed, dialAddr) 103 | errCh <- nil 104 | }() 105 | } 106 | timer := time.NewTimer(config.GetConnectTimeouts()) 107 | select { 108 | case <-timer.C: 109 | err = syscall.ETIMEDOUT 110 | log.Printf("[fd:%v] timeout: %v", fd, err) 111 | case err = <-errCh: 112 | timer.Stop() 113 | } 114 | if err != nil { 115 | if proxyUsed == nil { 116 | log.Printf("[fd:%v] direct connect to %v failed %v", fd, dialAddr, err) 117 | } else { 118 | log.Printf("[fd:%v] connect to %v using proxy %v failed: %v", fd, dialAddr, proxyUsed, err) 119 | } 120 | return C.setErrno(errno(err)) 121 | } 122 | return 0 123 | } 124 | 125 | //export close 126 | func close(fdc C.int) C.int { 127 | fd := int(fdc) 128 | conn := NewFdConn(fd) 129 | remoteAddr := conn.RemoteAddr() // BUG: remoteAddr may be nil even if fd is not closed on Linux 130 | if opt, _ := syscall.GetsockoptInt(fd, syscall.SOL_SOCKET, syscall.SO_TYPE); opt == syscall.SOCK_STREAM { 131 | log.Printf("[fd:%v] close conn %v -> %v", fd, conn.LocalAddr(), remoteAddr) 132 | } 133 | return C.setErrno(errno(syscall.Close(fd))) 134 | } 135 | 136 | //export accept 137 | func accept(fdc C.int, addr *C.struct_sockaddr, sockLen *C.socklen_t) C.int { 138 | newFD, _, errno := syscall.Syscall(syscall.SYS_ACCEPT, uintptr(fdc), 139 | uintptr(unsafe.Pointer(addr)), uintptr(unsafe.Pointer(sockLen))) 140 | if errno != 0 { 141 | return C.setErrno(C.int(errno)) 142 | } 143 | conn := NewFdConn(int(newFD)) 144 | log.Printf("[fd:%v] accept conn %v -> %v", newFD, conn.LocalAddr(), conn.RemoteAddr()) 145 | return C.int(newFD) 146 | } 147 | -------------------------------------------------------------------------------- /connect_test.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "testing" 5 | ) 6 | 7 | // cgo not allowed in test 8 | func TestSocket(t *testing.T) { testSocket(t) } 9 | -------------------------------------------------------------------------------- /dial.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | /* 4 | #include 5 | #include 6 | int connect_proxy(int fd, const struct sockaddr *addr, socklen_t len); 7 | int connect(int fd, const struct sockaddr *addr, socklen_t len) { 8 | return connect_proxy(fd, addr, len); 9 | } 10 | */ 11 | import "C" 12 | import ( 13 | "errors" 14 | "net" 15 | "sync" 16 | "syscall" 17 | "time" 18 | ) 19 | 20 | var errClosed = errors.New("connection closed") 21 | 22 | var _ net.Conn = NewFdConn(0) 23 | 24 | func NewFdConn(fd int) *fdConn { 25 | return &fdConn{fd: fd} 26 | } 27 | 28 | type fdConn struct { 29 | fd int 30 | isClosed bool 31 | lock sync.RWMutex 32 | } 33 | 34 | func (s *fdConn) Dial(network, addr string) (c net.Conn, err error) { 35 | return s, nil 36 | } 37 | 38 | func (s *fdConn) Write(p []byte) (n int, err error) { 39 | s.lock.RLock() 40 | if s.isClosed { 41 | s.lock.RUnlock() 42 | return 0, errClosed 43 | } 44 | s.lock.RUnlock() 45 | return syscall.Write(s.fd, p) 46 | } 47 | 48 | func (s *fdConn) Read(p []byte) (n int, err error) { 49 | s.lock.RLock() 50 | if s.isClosed { 51 | s.lock.RUnlock() 52 | return 0, errClosed 53 | } 54 | s.lock.RUnlock() 55 | return syscall.Read(s.fd, p) 56 | } 57 | 58 | func (s *fdConn) Close() (err error) { 59 | s.lock.Lock() 60 | s.isClosed = true 61 | s.lock.Unlock() 62 | return 63 | } 64 | func (s *fdConn) LocalAddr() net.Addr { 65 | sa, _ := syscall.Getsockname(s.fd) 66 | return netAddr(sa) 67 | } 68 | 69 | func netAddr(sa syscall.Sockaddr) net.Addr { 70 | switch sa := sa.(type) { 71 | case *syscall.SockaddrInet4: 72 | return &net.TCPAddr{IP: sa.Addr[0:], Port: sa.Port} 73 | } 74 | return nil 75 | } 76 | 77 | func (s *fdConn) RemoteAddr() net.Addr { 78 | sa, _ := syscall.Getpeername(s.fd) 79 | return netAddr(sa) 80 | } 81 | func (s *fdConn) SetDeadline(t time.Time) error { 82 | return nil 83 | } 84 | func (s *fdConn) SetReadDeadline(t time.Time) error { 85 | return nil 86 | } 87 | func (s *fdConn) SetWriteDeadline(t time.Time) error { 88 | return nil 89 | } 90 | -------------------------------------------------------------------------------- /glide.lock: -------------------------------------------------------------------------------- 1 | hash: c73cff7729007f77ba648b06bf3a2960ed6c3ca11ba8cd349016eed86d1b04ed 2 | updated: 2017-08-20T14:20:01.864921978+08:00 3 | imports: 4 | - name: github.com/armon/go-socks5 5 | version: e75332964ef517daa070d7c38a9466a0d687e0a5 6 | - name: github.com/davecgh/go-spew 7 | version: 04cdfd42973bb9c8589fd6a731800cf222fde1a9 8 | subpackages: 9 | - spew 10 | - name: github.com/pmezard/go-difflib 11 | version: d8ed2627bdf02c080bf22230dbb337003b7aba2d 12 | subpackages: 13 | - difflib 14 | - name: github.com/stretchr/testify 15 | version: 890a5c3458b43e6104ff5da8dfa139d013d77544 16 | subpackages: 17 | - assert 18 | - require 19 | - name: golang.org/x/net 20 | version: 5f8847ae0d0e90b6a9dc8148e7ad616874625171 21 | subpackages: 22 | - context 23 | - proxy 24 | testImports: [] 25 | -------------------------------------------------------------------------------- /glide.yaml: -------------------------------------------------------------------------------- 1 | package: github.com/ma6174/libsocks5connect 2 | import: 3 | - package: golang.org/x/net 4 | subpackages: 5 | - proxy 6 | -------------------------------------------------------------------------------- /init.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "bufio" 5 | "fmt" 6 | "io/ioutil" 7 | "log" 8 | "math/rand" 9 | "net" 10 | "net/url" 11 | "os" 12 | "strconv" 13 | "strings" 14 | "sync" 15 | "syscall" 16 | "time" 17 | 18 | "golang.org/x/net/proxy" 19 | ) 20 | 21 | var version, configAddr string 22 | 23 | func init() { 24 | rand.Seed(time.Now().UnixNano()) 25 | 26 | envNoLog := os.Getenv("proxy_no_log") // false 27 | config.SetNoLog(envNoLog[strings.Index(envNoLog, "=")+1:]) 28 | log.SetFlags(log.Lshortfile | log.LstdFlags | log.Lmicroseconds) 29 | log.Println("libsocks5connect loaded, version:", version) 30 | 31 | envProxy := os.Getenv("socks5_proxy") // user:pass@192.168.1.1:1080,user:pass@192.168.1.2:1080 32 | config.SetProxyAddrs(strings.Split(envProxy[strings.Index(envProxy, "=")+1:], ",")) 33 | 34 | envNotProxies := os.Getenv("not_proxy") // 127.0.0.0/8,192.168.1.0/24 35 | config.SetNoProxies(strings.Split(envNotProxies[strings.Index(envNotProxies, "=")+1:], ",")) 36 | 37 | envConnectTimeouts := os.Getenv("proxy_timeout_ms") // 1000 38 | config.SetConnectTimeouts(envConnectTimeouts[strings.Index(envConnectTimeouts, "=")+1:]) 39 | 40 | envNoConfigServer := os.Getenv("no_config_server") // false 41 | envNoConfigServer = strings.ToLower(strings.TrimSpace( 42 | envNoConfigServer[strings.Index(envNoConfigServer, "=")+1:])) 43 | if envNoConfigServer != "true" && envNoConfigServer != "1" { 44 | go config.Listen() 45 | } 46 | } 47 | 48 | func main() { 49 | } 50 | 51 | var config = &Config{} 52 | 53 | type Config struct { 54 | lock sync.RWMutex 55 | notProxies []*net.IPNet 56 | connectTimeouts time.Duration 57 | proxyAddrs []ProxyAddr 58 | proxyNoLog bool 59 | } 60 | 61 | func (p *Config) String() string { 62 | p.lock.RLock() 63 | defer p.lock.RUnlock() 64 | return fmt.Sprintf("%v: %v\n%v=%v\n%v=%v\n%v=%v\n%v=%v\n", 65 | "version", version, 66 | "proxy_no_log", p.IsProxyNoLog(), 67 | "socks5_proxy", strings.Join(p.GetProxyAddrs(), ","), 68 | "not_proxy", strings.Join(p.GetNoProxies(), ","), 69 | "proxy_timeout_ms", uint64(p.GetConnectTimeouts()/time.Millisecond), 70 | ) 71 | } 72 | 73 | type ProxyAddr struct { 74 | proxy.Auth 75 | AddrStr string 76 | ResolvedAddr *net.TCPAddr 77 | } 78 | 79 | func (p ProxyAddr) Sockaddr() (addr syscall.Sockaddr) { 80 | naddr, err := net.ResolveTCPAddr("tcp", p.AddrStr) 81 | if err != nil { 82 | log.Println("resolve proxy addr failed", p.AddrStr, err, "use saved addr:", p.ResolvedAddr) 83 | naddr = p.ResolvedAddr 84 | } else { 85 | p.ResolvedAddr = naddr 86 | } 87 | if ip4 := naddr.IP.To4(); ip4 != nil { 88 | var proxyIp4 [4]byte 89 | copy(proxyIp4[:], ip4) 90 | return &syscall.SockaddrInet4{ 91 | Addr: proxyIp4, 92 | Port: naddr.Port, 93 | } 94 | } else if ip6 := naddr.IP.To16(); ip6 != nil { 95 | log.Println("not support ipv6 proxy addr", p.AddrStr, p.ResolvedAddr) 96 | } 97 | return 98 | } 99 | 100 | func (p ProxyAddr) String() string { 101 | if p.AddrStr == p.ResolvedAddr.String() { 102 | return p.AddrStr 103 | } 104 | return fmt.Sprintf("%v(%v)", p.AddrStr, p.ResolvedAddr) 105 | } 106 | 107 | func (p *Config) SetProxyAddrs(addrs []string) { 108 | p.lock.Lock() 109 | defer p.lock.Unlock() 110 | var proxyAddrs []ProxyAddr 111 | for _, ipAddr := range addrs { 112 | ipAddr = strings.TrimSpace(ipAddr) 113 | if len(ipAddr) == 0 { 114 | continue 115 | } 116 | var proxyAddr ProxyAddr 117 | u, err := url.Parse("socks5://" + strings.TrimSpace(ipAddr)) 118 | if err != nil { 119 | log.Println("parse proxy addr failed", ipAddr, err) 120 | continue 121 | } 122 | if u.User != nil { 123 | proxyAddr.User = u.User.Username() 124 | proxyAddr.Password, _ = u.User.Password() 125 | } 126 | naddr, err := net.ResolveTCPAddr("tcp", u.Host) 127 | if err != nil || naddr.IP.To4() == nil { 128 | log.Println("resolve proxy addr failed", ipAddr, err, naddr.IP) 129 | continue 130 | } 131 | proxyAddr.AddrStr = u.Host 132 | proxyAddr.ResolvedAddr = naddr 133 | log.Println("add proxy:", ipAddr) 134 | proxyAddrs = append(proxyAddrs, proxyAddr) 135 | } 136 | if len(proxyAddrs) != 0 { 137 | p.proxyAddrs = proxyAddrs 138 | } 139 | } 140 | 141 | func (p *Config) GetProxyCount() int { 142 | p.lock.RLock() 143 | defer p.lock.RUnlock() 144 | return len(p.proxyAddrs) 145 | } 146 | 147 | func (p *Config) GetProxyAddr() *ProxyAddr { 148 | p.lock.RLock() 149 | defer p.lock.RUnlock() 150 | tmpAddr := p.proxyAddrs[rand.Intn(len(p.proxyAddrs))] 151 | return &tmpAddr 152 | } 153 | 154 | func (p *Config) GetProxyAddrs() (addrs []string) { 155 | p.lock.RLock() 156 | defer p.lock.RUnlock() 157 | for _, addr := range p.proxyAddrs { 158 | addrs = append(addrs, addr.AddrStr) 159 | } 160 | return 161 | } 162 | 163 | func (p *Config) SetConnectTimeouts(timeout string) { 164 | p.lock.Lock() 165 | defer p.lock.Unlock() 166 | t, err := strconv.Atoi(strings.TrimSpace(timeout)) 167 | if err != nil { 168 | t = 3000 169 | } 170 | p.connectTimeouts = time.Duration(t) * time.Millisecond 171 | log.Println("set connect timeout to", p.connectTimeouts) 172 | } 173 | func (p *Config) GetConnectTimeouts() time.Duration { 174 | p.lock.RLock() 175 | defer p.lock.RUnlock() 176 | return p.connectTimeouts 177 | } 178 | 179 | func (p *Config) SetNoLog(isNoLog string) { 180 | p.lock.Lock() 181 | defer p.lock.Unlock() 182 | isNoLog = strings.ToLower(strings.TrimSpace(isNoLog)) 183 | if isNoLog == "true" || isNoLog == "1" { 184 | log.SetOutput(ioutil.Discard) 185 | p.proxyNoLog = true 186 | } else { 187 | log.SetOutput(os.Stderr) 188 | p.proxyNoLog = false 189 | } 190 | } 191 | func (p *Config) IsProxyNoLog() bool { 192 | p.lock.RLock() 193 | defer p.lock.RUnlock() 194 | return p.proxyNoLog 195 | } 196 | 197 | func (p *Config) ShouldNotProxy(ip net.IP) bool { 198 | p.lock.RLock() 199 | defer p.lock.RUnlock() 200 | for _, ipnet := range p.notProxies { 201 | if ipnet.Contains(ip) { 202 | return true 203 | } 204 | } 205 | return false 206 | } 207 | 208 | func (p *Config) SetNoProxies(addrs []string) { 209 | p.lock.Lock() 210 | defer p.lock.Unlock() 211 | var notProxies []*net.IPNet 212 | for _, addr := range addrs { 213 | addr = strings.TrimSpace(addr) 214 | if len(addr) == 0 { 215 | continue 216 | } 217 | _, ipnet, err := net.ParseCIDR(addr) 218 | if err != nil { 219 | log.Println("parse ipnet failed", err, addr) 220 | continue 221 | } 222 | log.Println("add not proxy addr:", addr) 223 | notProxies = append(notProxies, ipnet) 224 | } 225 | if len(notProxies) != 0 { 226 | p.notProxies = notProxies 227 | } 228 | } 229 | 230 | func (p *Config) GetNoProxies() (addrs []string) { 231 | p.lock.RLock() 232 | defer p.lock.RUnlock() 233 | for _, addr := range p.notProxies { 234 | addrs = append(addrs, addr.String()) 235 | } 236 | return 237 | } 238 | 239 | func (p *Config) Listen() { 240 | ln, err := net.Listen("tcp", "localhost:0") 241 | if err != nil { 242 | log.Println("listen failed", err) 243 | return 244 | } 245 | configAddr = ln.Addr().String() 246 | for { 247 | conn, err := ln.Accept() 248 | if err != nil { 249 | log.Println("Accept failed", err) 250 | continue 251 | } 252 | go p.UpdateConfigFromConn(conn) 253 | } 254 | } 255 | 256 | func (p *Config) UpdateConfigFromConn(conn net.Conn) { 257 | defer conn.Close() 258 | log.Println("config server new connection from:", conn.RemoteAddr()) 259 | fmt.Fprintf(conn, "current config:\n%v\n\n", p) 260 | scanner := bufio.NewScanner(conn) 261 | for scanner.Scan() { 262 | sp := strings.SplitN(scanner.Text(), "=", 2) 263 | if len(sp) < 2 { 264 | log.Println("invalid config") 265 | fmt.Fprintf(conn, "invalid config %#v\n", scanner.Text()) 266 | fmt.Fprintf(conn, "current config:\n%v\n\n", p) 267 | continue 268 | } 269 | switch sp[0] { 270 | case "socks5_proxy", "export socks5_proxy": 271 | config.SetProxyAddrs(strings.Split(sp[1], ",")) 272 | fmt.Fprintf(conn, "OK, current proxyaddrs: %v\n", 273 | strings.Join(config.GetProxyAddrs(), ",")) 274 | case "not_proxy", "export not_proxy": 275 | config.SetNoProxies(strings.Split(sp[1], ",")) 276 | fmt.Fprintf(conn, "OK, current no proxy addrs: %v\n", 277 | strings.Join(config.GetNoProxies(), ",")) 278 | case "proxy_timeout_ms", "export proxy_timeout_ms": 279 | config.SetConnectTimeouts(sp[1]) 280 | fmt.Fprintf(conn, "OK, current proxy timeouts: %v\n", 281 | uint64(p.GetConnectTimeouts()/time.Millisecond)) 282 | case "proxy_no_log", "export proxy_no_log": 283 | config.SetNoLog(sp[1]) 284 | fmt.Fprintf(conn, "OK, proxy_no_log: %v\n", 285 | config.IsProxyNoLog()) 286 | default: 287 | log.Println("unknown config") 288 | fmt.Fprintf(conn, "unknown config %#v\n", scanner.Text()) 289 | fmt.Fprintf(conn, "current config:\n%v\n\n", p) 290 | } 291 | } 292 | } 293 | -------------------------------------------------------------------------------- /init_test.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "fmt" 5 | "io" 6 | "net" 7 | "os" 8 | "strings" 9 | "testing" 10 | "time" 11 | 12 | "github.com/stretchr/testify/require" 13 | ) 14 | 15 | func TestInit(t *testing.T) { 16 | r := require.New(t) 17 | config.proxyAddrs = nil 18 | r.True(strings.Contains(config.String(), "proxy_timeout_ms=1000")) 19 | conn, err := net.Dial("tcp", configAddr) 20 | r.NoError(err) 21 | go io.Copy(os.Stdout, conn) 22 | 23 | _, err = fmt.Fprintln(conn, "proxy_timeout_ms=2000") 24 | r.NoError(err) 25 | time.Sleep(time.Millisecond * 10) 26 | r.True(strings.Contains(config.String(), "proxy_timeout_ms=2000")) 27 | r.Equal(2000*time.Millisecond, config.connectTimeouts) 28 | 29 | _, err = fmt.Fprintln(conn, "socks5_proxy=127.0.0.1:100,127.0.0.1:101") 30 | r.NoError(err) 31 | time.Sleep(time.Millisecond * 10) 32 | r.Equal("127.0.0.1:100", config.proxyAddrs[0].String()) 33 | r.Equal("127.0.0.1:101", config.proxyAddrs[1].String()) 34 | 35 | _, err = fmt.Fprintln(conn, "not_proxy=192.168.1.0/24") 36 | r.NoError(err) 37 | time.Sleep(time.Millisecond * 10) 38 | r.True(config.ShouldNotProxy(net.IP{192, 168, 1, 100})) 39 | r.False(config.ShouldNotProxy(net.IP{192, 168, 2, 100})) 40 | _, err = fmt.Fprintln(conn, "not_proxy=192.168.1.0/24,192.168.2.0/24") 41 | r.NoError(err) 42 | time.Sleep(time.Millisecond * 10) 43 | r.Equal(1, strings.Count(config.String(), "192.168.1.0/24")) 44 | r.Equal(1, strings.Count(config.String(), "192.168.2.0/24")) 45 | 46 | _, err = fmt.Fprintln(conn, "socks5_proxy=192.168.111.111:1000") 47 | r.NoError(err) 48 | time.Sleep(time.Millisecond * 10) 49 | r.Equal("192.168.111.111:1000", config.GetProxyAddr().String()) 50 | _, err = fmt.Fprintln(conn, "socks5_proxy=192.168.111.112:2222") 51 | r.NoError(err) 52 | time.Sleep(time.Millisecond * 10) 53 | r.Equal("192.168.111.112:2222", config.GetProxyAddr().String()) 54 | r.Equal([]string{"192.168.111.112:2222"}, config.GetProxyAddrs()) 55 | } 56 | -------------------------------------------------------------------------------- /proxy.conf: -------------------------------------------------------------------------------- 1 | export socks5_proxy=127.0.0.1:7070 2 | export not_proxy=127.0.0.0/8,192.168.1.0/24 3 | export proxy_timeout_ms=1000 4 | export proxy_no_log=false 5 | export libsocks5connect=./libsocks5connect.so 6 | -------------------------------------------------------------------------------- /proxy.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | export socks5_proxy=127.0.0.1:7070,127.0.0.1:1080 4 | export not_proxy=127.0.0.0/8 5 | export proxy_timeout_ms=1000 6 | export proxy_no_log=false 7 | export libsocks5connect=./libsocks5connect.so 8 | 9 | [[ x$1 = x"-f" ]] && source $2 && shift 2 10 | 11 | case `uname -s` in 12 | Darwin) 13 | export DYLD_FORCE_FLAT_NAMESPACE=1 14 | export DYLD_INSERT_LIBRARIES=${libsocks5connect} 15 | ;; 16 | 17 | Linux) 18 | export LD_PRELOAD=${libsocks5connect} 19 | ;; 20 | 21 | *) 22 | esac 23 | 24 | exec "$@" 25 | -------------------------------------------------------------------------------- /proxy_test.conf: -------------------------------------------------------------------------------- 1 | export socks5_proxy=127.0.0.1:1080 2 | export not_proxy= 3 | export proxy_timeout_ms=1000 4 | export proxy_no_log=false 5 | export libsocks5connect=./libsocks5connect.so 6 | -------------------------------------------------------------------------------- /socks5server/server.go: -------------------------------------------------------------------------------- 1 | package main 2 | 3 | import ( 4 | "log" 5 | 6 | socks5 "github.com/armon/go-socks5" 7 | ) 8 | 9 | func main() { 10 | svr, err := socks5.New(&socks5.Config{}) 11 | if err != nil { 12 | log.Fatal(err) 13 | } 14 | log.Fatal(svr.ListenAndServe("tcp", "127.0.0.1:1080")) 15 | } 16 | -------------------------------------------------------------------------------- /test.go: -------------------------------------------------------------------------------- 1 | // +build test 2 | 3 | package main 4 | 5 | /* 6 | #include 7 | #include 8 | #include 9 | static inline int setErrno(int err) { 10 | if (err == 0) { 11 | return 0; 12 | } 13 | errno = err; 14 | return -1; 15 | } 16 | */ 17 | import "C" 18 | import ( 19 | "log" 20 | "net" 21 | "syscall" 22 | "testing" 23 | "time" 24 | "unsafe" 25 | 26 | "github.com/armon/go-socks5" 27 | "github.com/stretchr/testify/require" 28 | ) 29 | 30 | func testSocket(t *testing.T) { 31 | // listen 32 | r := require.New(t) 33 | fdListen, err := syscall.Socket(syscall.AF_INET, syscall.SOCK_STREAM, 0) 34 | r.NoError(err) 35 | err = syscall.Bind(fdListen, &syscall.SockaddrInet4{ 36 | Port: 0, 37 | Addr: [4]byte{127, 0, 0, 1}, 38 | }) 39 | r.NoError(err) 40 | err = syscall.Listen(fdListen, 10) 41 | r.NoError(err) 42 | sa, err := syscall.Getsockname(fdListen) 43 | r.NoError(err) 44 | listenAddr := netAddr(sa).(*net.TCPAddr) 45 | r.NotNil(listenAddr) 46 | log.Println("listen:", listenAddr) 47 | // accept 48 | go func() { 49 | for { 50 | var ( 51 | addr C.struct_sockaddr 52 | sockLen C.socklen_t 53 | ) 54 | ret := accept(C.int(fdListen), &addr, &sockLen) 55 | log.Println(ret, addr, sockLen) 56 | p := make([]byte, 1) 57 | _, err := syscall.Read(int(ret), p) 58 | r.NoError(err) 59 | _, err = syscall.Write(int(ret), p) 60 | r.NoError(err) 61 | } 62 | }() 63 | socks5Ln, err := net.Listen("tcp", "127.0.0.1:0") 64 | r.NoError(err) 65 | svr, err := socks5.New(&socks5.Config{}) 66 | r.NoError(err) 67 | go svr.Serve(socks5Ln) 68 | proxyAddrs := []ProxyAddr{ProxyAddr{ 69 | AddrStr: socks5Ln.Addr().String(), 70 | ResolvedAddr: socks5Ln.Addr().(*net.TCPAddr), 71 | }} 72 | config.connectTimeouts = time.Second 73 | // proxy connect 74 | { 75 | for _, proxy := range [][]ProxyAddr{[]ProxyAddr{}, proxyAddrs} { 76 | config.proxyAddrs = proxy 77 | fd, err := syscall.Socket(syscall.AF_INET, syscall.SOCK_STREAM, 0) 78 | r.NoError(err) 79 | err = syscall.SetNonblock(fd, false) 80 | r.NoError(err) 81 | addr := (*C.struct_sockaddr)(unsafe.Pointer(&syscall.RawSockaddrInet4{ 82 | Family: syscall.AF_INET, 83 | Addr: [4]byte{127, 0, 0, 1}, 84 | Port: uint16(listenAddr.Port<<8 | listenAddr.Port>>8), 85 | })) 86 | ret := connect_proxy(C.int(fd), addr, C.socklen_t(8)) 87 | r.Equal(0, int(ret)) 88 | data := []byte("a") 89 | _, err = syscall.Write(fd, data) 90 | r.NoError(err) 91 | var out = make([]byte, 1) 92 | _, err = syscall.Read(fd, out) 93 | r.NoError(err) 94 | r.Equal(data, out) 95 | ret = close(C.int(fd)) 96 | r.Equal(0, int(ret)) 97 | } 98 | } 99 | // connect wrong port 100 | { 101 | fd, err := syscall.Socket(syscall.AF_INET, syscall.SOCK_STREAM, 0) 102 | r.NoError(err) 103 | addr := (*C.struct_sockaddr)(unsafe.Pointer(&syscall.RawSockaddrInet4{ 104 | Family: syscall.AF_INET, 105 | Addr: [4]byte{127, 0, 0, 1}, 106 | Port: uint16(listenAddr.Port<<8|listenAddr.Port>>8) + 1, 107 | })) 108 | ret := connect_proxy(C.int(fd), addr, C.socklen_t(8)) 109 | r.Equal(-1, int(ret)) 110 | ret = close(C.int(fd)) 111 | r.Equal(0, int(ret)) 112 | } 113 | } 114 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/.gitignore: -------------------------------------------------------------------------------- 1 | # Compiled Object files, Static and Dynamic libs (Shared Objects) 2 | *.o 3 | *.a 4 | *.so 5 | 6 | # Folders 7 | _obj 8 | _test 9 | 10 | # Architecture specific extensions/prefixes 11 | *.[568vq] 12 | [568vq].out 13 | 14 | *.cgo1.go 15 | *.cgo2.c 16 | _cgo_defun.c 17 | _cgo_gotypes.go 18 | _cgo_export.* 19 | 20 | _testmain.go 21 | 22 | *.exe 23 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/.travis.yml: -------------------------------------------------------------------------------- 1 | language: go 2 | go: 3 | - 1.1 4 | - tip 5 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2014 Armon Dadgar 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy of 6 | this software and associated documentation files (the "Software"), to deal in 7 | the Software without restriction, including without limitation the rights to 8 | use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of 9 | the Software, and to permit persons to whom the Software is furnished to do so, 10 | subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS 17 | FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR 18 | COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER 19 | IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 20 | CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 21 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/README.md: -------------------------------------------------------------------------------- 1 | go-socks5 [![Build Status](https://travis-ci.org/armon/go-socks5.png)](https://travis-ci.org/armon/go-socks5) 2 | ========= 3 | 4 | Provides the `socks5` package that implements a [SOCKS5 server](http://en.wikipedia.org/wiki/SOCKS). 5 | SOCKS (Secure Sockets) is used to route traffic between a client and server through 6 | an intermediate proxy layer. This can be used to bypass firewalls or NATs. 7 | 8 | Feature 9 | ======= 10 | 11 | The package has the following features: 12 | * "No Auth" mode 13 | * User/Password authentication 14 | * Support for the CONNECT command 15 | * Rules to do granular filtering of commands 16 | * Custom DNS resolution 17 | * Unit tests 18 | 19 | TODO 20 | ==== 21 | 22 | The package still needs the following: 23 | * Support for the BIND command 24 | * Support for the ASSOCIATE command 25 | 26 | 27 | Example 28 | ======= 29 | 30 | Below is a simple example of usage 31 | 32 | ```go 33 | // Create a SOCKS5 server 34 | conf := &socks5.Config{} 35 | server, err := socks5.New(conf) 36 | if err != nil { 37 | panic(err) 38 | } 39 | 40 | // Create SOCKS5 proxy on localhost port 8000 41 | if err := server.ListenAndServe("tcp", "127.0.0.1:8000"); err != nil { 42 | panic(err) 43 | } 44 | ``` 45 | 46 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/auth.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "fmt" 5 | "io" 6 | ) 7 | 8 | const ( 9 | NoAuth = uint8(0) 10 | noAcceptable = uint8(255) 11 | UserPassAuth = uint8(2) 12 | userAuthVersion = uint8(1) 13 | authSuccess = uint8(0) 14 | authFailure = uint8(1) 15 | ) 16 | 17 | var ( 18 | UserAuthFailed = fmt.Errorf("User authentication failed") 19 | NoSupportedAuth = fmt.Errorf("No supported authentication mechanism") 20 | ) 21 | 22 | // A Request encapsulates authentication state provided 23 | // during negotiation 24 | type AuthContext struct { 25 | // Provided auth method 26 | Method uint8 27 | // Payload provided during negotiation. 28 | // Keys depend on the used auth method. 29 | // For UserPassauth contains Username 30 | Payload map[string]string 31 | } 32 | 33 | type Authenticator interface { 34 | Authenticate(reader io.Reader, writer io.Writer) (*AuthContext, error) 35 | GetCode() uint8 36 | } 37 | 38 | // NoAuthAuthenticator is used to handle the "No Authentication" mode 39 | type NoAuthAuthenticator struct{} 40 | 41 | func (a NoAuthAuthenticator) GetCode() uint8 { 42 | return NoAuth 43 | } 44 | 45 | func (a NoAuthAuthenticator) Authenticate(reader io.Reader, writer io.Writer) (*AuthContext, error) { 46 | _, err := writer.Write([]byte{socks5Version, NoAuth}) 47 | return &AuthContext{NoAuth, nil}, err 48 | } 49 | 50 | // UserPassAuthenticator is used to handle username/password based 51 | // authentication 52 | type UserPassAuthenticator struct { 53 | Credentials CredentialStore 54 | } 55 | 56 | func (a UserPassAuthenticator) GetCode() uint8 { 57 | return UserPassAuth 58 | } 59 | 60 | func (a UserPassAuthenticator) Authenticate(reader io.Reader, writer io.Writer) (*AuthContext, error) { 61 | // Tell the client to use user/pass auth 62 | if _, err := writer.Write([]byte{socks5Version, UserPassAuth}); err != nil { 63 | return nil, err 64 | } 65 | 66 | // Get the version and username length 67 | header := []byte{0, 0} 68 | if _, err := io.ReadAtLeast(reader, header, 2); err != nil { 69 | return nil, err 70 | } 71 | 72 | // Ensure we are compatible 73 | if header[0] != userAuthVersion { 74 | return nil, fmt.Errorf("Unsupported auth version: %v", header[0]) 75 | } 76 | 77 | // Get the user name 78 | userLen := int(header[1]) 79 | user := make([]byte, userLen) 80 | if _, err := io.ReadAtLeast(reader, user, userLen); err != nil { 81 | return nil, err 82 | } 83 | 84 | // Get the password length 85 | if _, err := reader.Read(header[:1]); err != nil { 86 | return nil, err 87 | } 88 | 89 | // Get the password 90 | passLen := int(header[0]) 91 | pass := make([]byte, passLen) 92 | if _, err := io.ReadAtLeast(reader, pass, passLen); err != nil { 93 | return nil, err 94 | } 95 | 96 | // Verify the password 97 | if a.Credentials.Valid(string(user), string(pass)) { 98 | if _, err := writer.Write([]byte{userAuthVersion, authSuccess}); err != nil { 99 | return nil, err 100 | } 101 | } else { 102 | if _, err := writer.Write([]byte{userAuthVersion, authFailure}); err != nil { 103 | return nil, err 104 | } 105 | return nil, UserAuthFailed 106 | } 107 | 108 | // Done 109 | return &AuthContext{UserPassAuth, map[string]string{"Username": string(user)}}, nil 110 | } 111 | 112 | // authenticate is used to handle connection authentication 113 | func (s *Server) authenticate(conn io.Writer, bufConn io.Reader) (*AuthContext, error) { 114 | // Get the methods 115 | methods, err := readMethods(bufConn) 116 | if err != nil { 117 | return nil, fmt.Errorf("Failed to get auth methods: %v", err) 118 | } 119 | 120 | // Select a usable method 121 | for _, method := range methods { 122 | cator, found := s.authMethods[method] 123 | if found { 124 | return cator.Authenticate(bufConn, conn) 125 | } 126 | } 127 | 128 | // No usable method found 129 | return nil, noAcceptableAuth(conn) 130 | } 131 | 132 | // noAcceptableAuth is used to handle when we have no eligible 133 | // authentication mechanism 134 | func noAcceptableAuth(conn io.Writer) error { 135 | conn.Write([]byte{socks5Version, noAcceptable}) 136 | return NoSupportedAuth 137 | } 138 | 139 | // readMethods is used to read the number of methods 140 | // and proceeding auth methods 141 | func readMethods(r io.Reader) ([]byte, error) { 142 | header := []byte{0} 143 | if _, err := r.Read(header); err != nil { 144 | return nil, err 145 | } 146 | 147 | numMethods := int(header[0]) 148 | methods := make([]byte, numMethods) 149 | _, err := io.ReadAtLeast(r, methods, numMethods) 150 | return methods, err 151 | } 152 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/auth_test.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "bytes" 5 | "testing" 6 | ) 7 | 8 | func TestNoAuth(t *testing.T) { 9 | req := bytes.NewBuffer(nil) 10 | req.Write([]byte{1, NoAuth}) 11 | var resp bytes.Buffer 12 | 13 | s, _ := New(&Config{}) 14 | ctx, err := s.authenticate(&resp, req) 15 | if err != nil { 16 | t.Fatalf("err: %v", err) 17 | } 18 | 19 | if ctx.Method != NoAuth { 20 | t.Fatal("Invalid Context Method") 21 | } 22 | 23 | out := resp.Bytes() 24 | if !bytes.Equal(out, []byte{socks5Version, NoAuth}) { 25 | t.Fatalf("bad: %v", out) 26 | } 27 | } 28 | 29 | func TestPasswordAuth_Valid(t *testing.T) { 30 | req := bytes.NewBuffer(nil) 31 | req.Write([]byte{2, NoAuth, UserPassAuth}) 32 | req.Write([]byte{1, 3, 'f', 'o', 'o', 3, 'b', 'a', 'r'}) 33 | var resp bytes.Buffer 34 | 35 | cred := StaticCredentials{ 36 | "foo": "bar", 37 | } 38 | 39 | cator := UserPassAuthenticator{Credentials: cred} 40 | 41 | s, _ := New(&Config{AuthMethods: []Authenticator{cator}}) 42 | 43 | ctx, err := s.authenticate(&resp, req) 44 | if err != nil { 45 | t.Fatalf("err: %v", err) 46 | } 47 | 48 | if ctx.Method != UserPassAuth { 49 | t.Fatal("Invalid Context Method") 50 | } 51 | 52 | val, ok := ctx.Payload["Username"] 53 | if !ok { 54 | t.Fatal("Missing key Username in auth context's payload") 55 | } 56 | 57 | if val != "foo" { 58 | t.Fatal("Invalid Username in auth context's payload") 59 | } 60 | 61 | out := resp.Bytes() 62 | if !bytes.Equal(out, []byte{socks5Version, UserPassAuth, 1, authSuccess}) { 63 | t.Fatalf("bad: %v", out) 64 | } 65 | } 66 | 67 | func TestPasswordAuth_Invalid(t *testing.T) { 68 | req := bytes.NewBuffer(nil) 69 | req.Write([]byte{2, NoAuth, UserPassAuth}) 70 | req.Write([]byte{1, 3, 'f', 'o', 'o', 3, 'b', 'a', 'z'}) 71 | var resp bytes.Buffer 72 | 73 | cred := StaticCredentials{ 74 | "foo": "bar", 75 | } 76 | cator := UserPassAuthenticator{Credentials: cred} 77 | s, _ := New(&Config{AuthMethods: []Authenticator{cator}}) 78 | 79 | ctx, err := s.authenticate(&resp, req) 80 | if err != UserAuthFailed { 81 | t.Fatalf("err: %v", err) 82 | } 83 | 84 | if ctx != nil { 85 | t.Fatal("Invalid Context Method") 86 | } 87 | 88 | out := resp.Bytes() 89 | if !bytes.Equal(out, []byte{socks5Version, UserPassAuth, 1, authFailure}) { 90 | t.Fatalf("bad: %v", out) 91 | } 92 | } 93 | 94 | func TestNoSupportedAuth(t *testing.T) { 95 | req := bytes.NewBuffer(nil) 96 | req.Write([]byte{1, NoAuth}) 97 | var resp bytes.Buffer 98 | 99 | cred := StaticCredentials{ 100 | "foo": "bar", 101 | } 102 | cator := UserPassAuthenticator{Credentials: cred} 103 | 104 | s, _ := New(&Config{AuthMethods: []Authenticator{cator}}) 105 | 106 | ctx, err := s.authenticate(&resp, req) 107 | if err != NoSupportedAuth { 108 | t.Fatalf("err: %v", err) 109 | } 110 | 111 | if ctx != nil { 112 | t.Fatal("Invalid Context Method") 113 | } 114 | 115 | out := resp.Bytes() 116 | if !bytes.Equal(out, []byte{socks5Version, noAcceptable}) { 117 | t.Fatalf("bad: %v", out) 118 | } 119 | } 120 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/credentials.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | // CredentialStore is used to support user/pass authentication 4 | type CredentialStore interface { 5 | Valid(user, password string) bool 6 | } 7 | 8 | // StaticCredentials enables using a map directly as a credential store 9 | type StaticCredentials map[string]string 10 | 11 | func (s StaticCredentials) Valid(user, password string) bool { 12 | pass, ok := s[user] 13 | if !ok { 14 | return false 15 | } 16 | return password == pass 17 | } 18 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/credentials_test.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "testing" 5 | ) 6 | 7 | func TestStaticCredentials(t *testing.T) { 8 | creds := StaticCredentials{ 9 | "foo": "bar", 10 | "baz": "", 11 | } 12 | 13 | if !creds.Valid("foo", "bar") { 14 | t.Fatalf("expect valid") 15 | } 16 | 17 | if !creds.Valid("baz", "") { 18 | t.Fatalf("expect valid") 19 | } 20 | 21 | if creds.Valid("foo", "") { 22 | t.Fatalf("expect invalid") 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/request_test.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "bytes" 5 | "encoding/binary" 6 | "io" 7 | "log" 8 | "net" 9 | "os" 10 | "strings" 11 | "testing" 12 | ) 13 | 14 | type MockConn struct { 15 | buf bytes.Buffer 16 | } 17 | 18 | func (m *MockConn) Write(b []byte) (int, error) { 19 | return m.buf.Write(b) 20 | } 21 | 22 | func (m *MockConn) RemoteAddr() net.Addr { 23 | return &net.TCPAddr{IP: []byte{127, 0, 0, 1}, Port: 65432} 24 | } 25 | 26 | func TestRequest_Connect(t *testing.T) { 27 | // Create a local listener 28 | l, err := net.Listen("tcp", "127.0.0.1:0") 29 | if err != nil { 30 | t.Fatalf("err: %v", err) 31 | } 32 | go func() { 33 | conn, err := l.Accept() 34 | if err != nil { 35 | t.Fatalf("err: %v", err) 36 | } 37 | defer conn.Close() 38 | 39 | buf := make([]byte, 4) 40 | if _, err := io.ReadAtLeast(conn, buf, 4); err != nil { 41 | t.Fatalf("err: %v", err) 42 | } 43 | 44 | if !bytes.Equal(buf, []byte("ping")) { 45 | t.Fatalf("bad: %v", buf) 46 | } 47 | conn.Write([]byte("pong")) 48 | }() 49 | lAddr := l.Addr().(*net.TCPAddr) 50 | 51 | // Make server 52 | s := &Server{config: &Config{ 53 | Rules: PermitAll(), 54 | Resolver: DNSResolver{}, 55 | Logger: log.New(os.Stdout, "", log.LstdFlags), 56 | }} 57 | 58 | // Create the connect request 59 | buf := bytes.NewBuffer(nil) 60 | buf.Write([]byte{5, 1, 0, 1, 127, 0, 0, 1}) 61 | 62 | port := []byte{0, 0} 63 | binary.BigEndian.PutUint16(port, uint16(lAddr.Port)) 64 | buf.Write(port) 65 | 66 | // Send a ping 67 | buf.Write([]byte("ping")) 68 | 69 | // Handle the request 70 | resp := &MockConn{} 71 | req, err := NewRequest(buf) 72 | if err != nil { 73 | t.Fatalf("err: %v", err) 74 | } 75 | 76 | if err := s.handleRequest(req, resp); err != nil { 77 | t.Fatalf("err: %v", err) 78 | } 79 | 80 | // Verify response 81 | out := resp.buf.Bytes() 82 | expected := []byte{ 83 | 5, 84 | 0, 85 | 0, 86 | 1, 87 | 127, 0, 0, 1, 88 | 0, 0, 89 | 'p', 'o', 'n', 'g', 90 | } 91 | 92 | // Ignore the port for both 93 | out[8] = 0 94 | out[9] = 0 95 | 96 | if !bytes.Equal(out, expected) { 97 | t.Fatalf("bad: %v %v", out, expected) 98 | } 99 | } 100 | 101 | func TestRequest_Connect_RuleFail(t *testing.T) { 102 | // Create a local listener 103 | l, err := net.Listen("tcp", "127.0.0.1:0") 104 | if err != nil { 105 | t.Fatalf("err: %v", err) 106 | } 107 | go func() { 108 | conn, err := l.Accept() 109 | if err != nil { 110 | t.Fatalf("err: %v", err) 111 | } 112 | defer conn.Close() 113 | 114 | buf := make([]byte, 4) 115 | if _, err := io.ReadAtLeast(conn, buf, 4); err != nil { 116 | t.Fatalf("err: %v", err) 117 | } 118 | 119 | if !bytes.Equal(buf, []byte("ping")) { 120 | t.Fatalf("bad: %v", buf) 121 | } 122 | conn.Write([]byte("pong")) 123 | }() 124 | lAddr := l.Addr().(*net.TCPAddr) 125 | 126 | // Make server 127 | s := &Server{config: &Config{ 128 | Rules: PermitNone(), 129 | Resolver: DNSResolver{}, 130 | Logger: log.New(os.Stdout, "", log.LstdFlags), 131 | }} 132 | 133 | // Create the connect request 134 | buf := bytes.NewBuffer(nil) 135 | buf.Write([]byte{5, 1, 0, 1, 127, 0, 0, 1}) 136 | 137 | port := []byte{0, 0} 138 | binary.BigEndian.PutUint16(port, uint16(lAddr.Port)) 139 | buf.Write(port) 140 | 141 | // Send a ping 142 | buf.Write([]byte("ping")) 143 | 144 | // Handle the request 145 | resp := &MockConn{} 146 | req, err := NewRequest(buf) 147 | if err != nil { 148 | t.Fatalf("err: %v", err) 149 | } 150 | 151 | if err := s.handleRequest(req, resp); !strings.Contains(err.Error(), "blocked by rules") { 152 | t.Fatalf("err: %v", err) 153 | } 154 | 155 | // Verify response 156 | out := resp.buf.Bytes() 157 | expected := []byte{ 158 | 5, 159 | 2, 160 | 0, 161 | 1, 162 | 0, 0, 0, 0, 163 | 0, 0, 164 | } 165 | 166 | if !bytes.Equal(out, expected) { 167 | t.Fatalf("bad: %v %v", out, expected) 168 | } 169 | } 170 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/resolver.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "net" 5 | 6 | "golang.org/x/net/context" 7 | ) 8 | 9 | // NameResolver is used to implement custom name resolution 10 | type NameResolver interface { 11 | Resolve(ctx context.Context, name string) (context.Context, net.IP, error) 12 | } 13 | 14 | // DNSResolver uses the system DNS to resolve host names 15 | type DNSResolver struct{} 16 | 17 | func (d DNSResolver) Resolve(ctx context.Context, name string) (context.Context, net.IP, error) { 18 | addr, err := net.ResolveIPAddr("ip", name) 19 | if err != nil { 20 | return ctx, nil, err 21 | } 22 | return ctx, addr.IP, err 23 | } 24 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/resolver_test.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "testing" 5 | 6 | "golang.org/x/net/context" 7 | ) 8 | 9 | func TestDNSResolver(t *testing.T) { 10 | d := DNSResolver{} 11 | ctx := context.Background() 12 | 13 | _, addr, err := d.Resolve(ctx, "localhost") 14 | if err != nil { 15 | t.Fatalf("err: %v", err) 16 | } 17 | 18 | if !addr.IsLoopback() { 19 | t.Fatalf("expected loopback") 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/ruleset.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "golang.org/x/net/context" 5 | ) 6 | 7 | // RuleSet is used to provide custom rules to allow or prohibit actions 8 | type RuleSet interface { 9 | Allow(ctx context.Context, req *Request) (context.Context, bool) 10 | } 11 | 12 | // PermitAll returns a RuleSet which allows all types of connections 13 | func PermitAll() RuleSet { 14 | return &PermitCommand{true, true, true} 15 | } 16 | 17 | // PermitNone returns a RuleSet which disallows all types of connections 18 | func PermitNone() RuleSet { 19 | return &PermitCommand{false, false, false} 20 | } 21 | 22 | // PermitCommand is an implementation of the RuleSet which 23 | // enables filtering supported commands 24 | type PermitCommand struct { 25 | EnableConnect bool 26 | EnableBind bool 27 | EnableAssociate bool 28 | } 29 | 30 | func (p *PermitCommand) Allow(ctx context.Context, req *Request) (context.Context, bool) { 31 | switch req.Command { 32 | case ConnectCommand: 33 | return ctx, p.EnableConnect 34 | case BindCommand: 35 | return ctx, p.EnableBind 36 | case AssociateCommand: 37 | return ctx, p.EnableAssociate 38 | } 39 | 40 | return ctx, false 41 | } 42 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/ruleset_test.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "testing" 5 | 6 | "golang.org/x/net/context" 7 | ) 8 | 9 | func TestPermitCommand(t *testing.T) { 10 | ctx := context.Background() 11 | r := &PermitCommand{true, false, false} 12 | 13 | if _, ok := r.Allow(ctx, &Request{Command: ConnectCommand}); !ok { 14 | t.Fatalf("expect connect") 15 | } 16 | 17 | if _, ok := r.Allow(ctx, &Request{Command: BindCommand}); ok { 18 | t.Fatalf("do not expect bind") 19 | } 20 | 21 | if _, ok := r.Allow(ctx, &Request{Command: AssociateCommand}); ok { 22 | t.Fatalf("do not expect associate") 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/socks5.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "bufio" 5 | "fmt" 6 | "log" 7 | "net" 8 | "os" 9 | 10 | "golang.org/x/net/context" 11 | ) 12 | 13 | const ( 14 | socks5Version = uint8(5) 15 | ) 16 | 17 | // Config is used to setup and configure a Server 18 | type Config struct { 19 | // AuthMethods can be provided to implement custom authentication 20 | // By default, "auth-less" mode is enabled. 21 | // For password-based auth use UserPassAuthenticator. 22 | AuthMethods []Authenticator 23 | 24 | // If provided, username/password authentication is enabled, 25 | // by appending a UserPassAuthenticator to AuthMethods. If not provided, 26 | // and AUthMethods is nil, then "auth-less" mode is enabled. 27 | Credentials CredentialStore 28 | 29 | // Resolver can be provided to do custom name resolution. 30 | // Defaults to DNSResolver if not provided. 31 | Resolver NameResolver 32 | 33 | // Rules is provided to enable custom logic around permitting 34 | // various commands. If not provided, PermitAll is used. 35 | Rules RuleSet 36 | 37 | // Rewriter can be used to transparently rewrite addresses. 38 | // This is invoked before the RuleSet is invoked. 39 | // Defaults to NoRewrite. 40 | Rewriter AddressRewriter 41 | 42 | // BindIP is used for bind or udp associate 43 | BindIP net.IP 44 | 45 | // Logger can be used to provide a custom log target. 46 | // Defaults to stdout. 47 | Logger *log.Logger 48 | 49 | // Optional function for dialing out 50 | Dial func(ctx context.Context, network, addr string) (net.Conn, error) 51 | } 52 | 53 | // Server is reponsible for accepting connections and handling 54 | // the details of the SOCKS5 protocol 55 | type Server struct { 56 | config *Config 57 | authMethods map[uint8]Authenticator 58 | } 59 | 60 | // New creates a new Server and potentially returns an error 61 | func New(conf *Config) (*Server, error) { 62 | // Ensure we have at least one authentication method enabled 63 | if len(conf.AuthMethods) == 0 { 64 | if conf.Credentials != nil { 65 | conf.AuthMethods = []Authenticator{&UserPassAuthenticator{conf.Credentials}} 66 | } else { 67 | conf.AuthMethods = []Authenticator{&NoAuthAuthenticator{}} 68 | } 69 | } 70 | 71 | // Ensure we have a DNS resolver 72 | if conf.Resolver == nil { 73 | conf.Resolver = DNSResolver{} 74 | } 75 | 76 | // Ensure we have a rule set 77 | if conf.Rules == nil { 78 | conf.Rules = PermitAll() 79 | } 80 | 81 | // Ensure we have a log target 82 | if conf.Logger == nil { 83 | conf.Logger = log.New(os.Stdout, "", log.LstdFlags) 84 | } 85 | 86 | server := &Server{ 87 | config: conf, 88 | } 89 | 90 | server.authMethods = make(map[uint8]Authenticator) 91 | 92 | for _, a := range conf.AuthMethods { 93 | server.authMethods[a.GetCode()] = a 94 | } 95 | 96 | return server, nil 97 | } 98 | 99 | // ListenAndServe is used to create a listener and serve on it 100 | func (s *Server) ListenAndServe(network, addr string) error { 101 | l, err := net.Listen(network, addr) 102 | if err != nil { 103 | return err 104 | } 105 | return s.Serve(l) 106 | } 107 | 108 | // Serve is used to serve connections from a listener 109 | func (s *Server) Serve(l net.Listener) error { 110 | for { 111 | conn, err := l.Accept() 112 | if err != nil { 113 | return err 114 | } 115 | go s.ServeConn(conn) 116 | } 117 | return nil 118 | } 119 | 120 | // ServeConn is used to serve a single connection. 121 | func (s *Server) ServeConn(conn net.Conn) error { 122 | defer conn.Close() 123 | bufConn := bufio.NewReader(conn) 124 | 125 | // Read the version byte 126 | version := []byte{0} 127 | if _, err := bufConn.Read(version); err != nil { 128 | s.config.Logger.Printf("[ERR] socks: Failed to get version byte: %v", err) 129 | return err 130 | } 131 | 132 | // Ensure we are compatible 133 | if version[0] != socks5Version { 134 | err := fmt.Errorf("Unsupported SOCKS version: %v", version) 135 | s.config.Logger.Printf("[ERR] socks: %v", err) 136 | return err 137 | } 138 | 139 | // Authenticate the connection 140 | authContext, err := s.authenticate(conn, bufConn) 141 | if err != nil { 142 | err = fmt.Errorf("Failed to authenticate: %v", err) 143 | s.config.Logger.Printf("[ERR] socks: %v", err) 144 | return err 145 | } 146 | 147 | request, err := NewRequest(bufConn) 148 | if err != nil { 149 | if err == unrecognizedAddrType { 150 | if err := sendReply(conn, addrTypeNotSupported, nil); err != nil { 151 | return fmt.Errorf("Failed to send reply: %v", err) 152 | } 153 | } 154 | return fmt.Errorf("Failed to read destination address: %v", err) 155 | } 156 | request.AuthContext = authContext 157 | if client, ok := conn.RemoteAddr().(*net.TCPAddr); ok { 158 | request.RemoteAddr = &AddrSpec{IP: client.IP, Port: client.Port} 159 | } 160 | 161 | // Process the client request 162 | if err := s.handleRequest(request, conn); err != nil { 163 | err = fmt.Errorf("Failed to handle request: %v", err) 164 | s.config.Logger.Printf("[ERR] socks: %v", err) 165 | return err 166 | } 167 | 168 | return nil 169 | } 170 | -------------------------------------------------------------------------------- /vendor/github.com/armon/go-socks5/socks5_test.go: -------------------------------------------------------------------------------- 1 | package socks5 2 | 3 | import ( 4 | "bytes" 5 | "encoding/binary" 6 | "io" 7 | "log" 8 | "net" 9 | "os" 10 | "testing" 11 | "time" 12 | ) 13 | 14 | func TestSOCKS5_Connect(t *testing.T) { 15 | // Create a local listener 16 | l, err := net.Listen("tcp", "127.0.0.1:0") 17 | if err != nil { 18 | t.Fatalf("err: %v", err) 19 | } 20 | go func() { 21 | conn, err := l.Accept() 22 | if err != nil { 23 | t.Fatalf("err: %v", err) 24 | } 25 | defer conn.Close() 26 | 27 | buf := make([]byte, 4) 28 | if _, err := io.ReadAtLeast(conn, buf, 4); err != nil { 29 | t.Fatalf("err: %v", err) 30 | } 31 | 32 | if !bytes.Equal(buf, []byte("ping")) { 33 | t.Fatalf("bad: %v", buf) 34 | } 35 | conn.Write([]byte("pong")) 36 | }() 37 | lAddr := l.Addr().(*net.TCPAddr) 38 | 39 | // Create a socks server 40 | creds := StaticCredentials{ 41 | "foo": "bar", 42 | } 43 | cator := UserPassAuthenticator{Credentials: creds} 44 | conf := &Config{ 45 | AuthMethods: []Authenticator{cator}, 46 | Logger: log.New(os.Stdout, "", log.LstdFlags), 47 | } 48 | serv, err := New(conf) 49 | if err != nil { 50 | t.Fatalf("err: %v", err) 51 | } 52 | 53 | // Start listening 54 | go func() { 55 | if err := serv.ListenAndServe("tcp", "127.0.0.1:12365"); err != nil { 56 | t.Fatalf("err: %v", err) 57 | } 58 | }() 59 | time.Sleep(10 * time.Millisecond) 60 | 61 | // Get a local conn 62 | conn, err := net.Dial("tcp", "127.0.0.1:12365") 63 | if err != nil { 64 | t.Fatalf("err: %v", err) 65 | } 66 | 67 | // Connect, auth and connec to local 68 | req := bytes.NewBuffer(nil) 69 | req.Write([]byte{5}) 70 | req.Write([]byte{2, NoAuth, UserPassAuth}) 71 | req.Write([]byte{1, 3, 'f', 'o', 'o', 3, 'b', 'a', 'r'}) 72 | req.Write([]byte{5, 1, 0, 1, 127, 0, 0, 1}) 73 | 74 | port := []byte{0, 0} 75 | binary.BigEndian.PutUint16(port, uint16(lAddr.Port)) 76 | req.Write(port) 77 | 78 | // Send a ping 79 | req.Write([]byte("ping")) 80 | 81 | // Send all the bytes 82 | conn.Write(req.Bytes()) 83 | 84 | // Verify response 85 | expected := []byte{ 86 | socks5Version, UserPassAuth, 87 | 1, authSuccess, 88 | 5, 89 | 0, 90 | 0, 91 | 1, 92 | 127, 0, 0, 1, 93 | 0, 0, 94 | 'p', 'o', 'n', 'g', 95 | } 96 | out := make([]byte, len(expected)) 97 | 98 | conn.SetDeadline(time.Now().Add(time.Second)) 99 | if _, err := io.ReadAtLeast(conn, out, len(out)); err != nil { 100 | t.Fatalf("err: %v", err) 101 | } 102 | 103 | // Ignore the port 104 | out[12] = 0 105 | out[13] = 0 106 | 107 | if !bytes.Equal(out, expected) { 108 | t.Fatalf("bad: %v", out) 109 | } 110 | } 111 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/LICENSE: -------------------------------------------------------------------------------- 1 | ISC License 2 | 3 | Copyright (c) 2012-2013 Dave Collins 4 | 5 | Permission to use, copy, modify, and distribute this software for any 6 | purpose with or without fee is hereby granted, provided that the above 7 | copyright notice and this permission notice appear in all copies. 8 | 9 | THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 10 | WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 11 | MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 12 | ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 13 | WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 14 | ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 15 | OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 16 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/bypass.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2015 Dave Collins 2 | // 3 | // Permission to use, copy, modify, and distribute this software for any 4 | // purpose with or without fee is hereby granted, provided that the above 5 | // copyright notice and this permission notice appear in all copies. 6 | // 7 | // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | // NOTE: Due to the following build constraints, this file will only be compiled 16 | // when the code is not running on Google App Engine, compiled by GopherJS, and 17 | // "-tags safe" is not added to the go build command line. The "disableunsafe" 18 | // tag is deprecated and thus should not be used. 19 | // +build !js,!appengine,!safe,!disableunsafe 20 | 21 | package spew 22 | 23 | import ( 24 | "reflect" 25 | "unsafe" 26 | ) 27 | 28 | const ( 29 | // UnsafeDisabled is a build-time constant which specifies whether or 30 | // not access to the unsafe package is available. 31 | UnsafeDisabled = false 32 | 33 | // ptrSize is the size of a pointer on the current arch. 34 | ptrSize = unsafe.Sizeof((*byte)(nil)) 35 | ) 36 | 37 | var ( 38 | // offsetPtr, offsetScalar, and offsetFlag are the offsets for the 39 | // internal reflect.Value fields. These values are valid before golang 40 | // commit ecccf07e7f9d which changed the format. The are also valid 41 | // after commit 82f48826c6c7 which changed the format again to mirror 42 | // the original format. Code in the init function updates these offsets 43 | // as necessary. 44 | offsetPtr = uintptr(ptrSize) 45 | offsetScalar = uintptr(0) 46 | offsetFlag = uintptr(ptrSize * 2) 47 | 48 | // flagKindWidth and flagKindShift indicate various bits that the 49 | // reflect package uses internally to track kind information. 50 | // 51 | // flagRO indicates whether or not the value field of a reflect.Value is 52 | // read-only. 53 | // 54 | // flagIndir indicates whether the value field of a reflect.Value is 55 | // the actual data or a pointer to the data. 56 | // 57 | // These values are valid before golang commit 90a7c3c86944 which 58 | // changed their positions. Code in the init function updates these 59 | // flags as necessary. 60 | flagKindWidth = uintptr(5) 61 | flagKindShift = uintptr(flagKindWidth - 1) 62 | flagRO = uintptr(1 << 0) 63 | flagIndir = uintptr(1 << 1) 64 | ) 65 | 66 | func init() { 67 | // Older versions of reflect.Value stored small integers directly in the 68 | // ptr field (which is named val in the older versions). Versions 69 | // between commits ecccf07e7f9d and 82f48826c6c7 added a new field named 70 | // scalar for this purpose which unfortunately came before the flag 71 | // field, so the offset of the flag field is different for those 72 | // versions. 73 | // 74 | // This code constructs a new reflect.Value from a known small integer 75 | // and checks if the size of the reflect.Value struct indicates it has 76 | // the scalar field. When it does, the offsets are updated accordingly. 77 | vv := reflect.ValueOf(0xf00) 78 | if unsafe.Sizeof(vv) == (ptrSize * 4) { 79 | offsetScalar = ptrSize * 2 80 | offsetFlag = ptrSize * 3 81 | } 82 | 83 | // Commit 90a7c3c86944 changed the flag positions such that the low 84 | // order bits are the kind. This code extracts the kind from the flags 85 | // field and ensures it's the correct type. When it's not, the flag 86 | // order has been changed to the newer format, so the flags are updated 87 | // accordingly. 88 | upf := unsafe.Pointer(uintptr(unsafe.Pointer(&vv)) + offsetFlag) 89 | upfv := *(*uintptr)(upf) 90 | flagKindMask := uintptr((1<>flagKindShift != uintptr(reflect.Int) { 92 | flagKindShift = 0 93 | flagRO = 1 << 5 94 | flagIndir = 1 << 6 95 | 96 | // Commit adf9b30e5594 modified the flags to separate the 97 | // flagRO flag into two bits which specifies whether or not the 98 | // field is embedded. This causes flagIndir to move over a bit 99 | // and means that flagRO is the combination of either of the 100 | // original flagRO bit and the new bit. 101 | // 102 | // This code detects the change by extracting what used to be 103 | // the indirect bit to ensure it's set. When it's not, the flag 104 | // order has been changed to the newer format, so the flags are 105 | // updated accordingly. 106 | if upfv&flagIndir == 0 { 107 | flagRO = 3 << 5 108 | flagIndir = 1 << 7 109 | } 110 | } 111 | } 112 | 113 | // unsafeReflectValue converts the passed reflect.Value into a one that bypasses 114 | // the typical safety restrictions preventing access to unaddressable and 115 | // unexported data. It works by digging the raw pointer to the underlying 116 | // value out of the protected value and generating a new unprotected (unsafe) 117 | // reflect.Value to it. 118 | // 119 | // This allows us to check for implementations of the Stringer and error 120 | // interfaces to be used for pretty printing ordinarily unaddressable and 121 | // inaccessible values such as unexported struct fields. 122 | func unsafeReflectValue(v reflect.Value) (rv reflect.Value) { 123 | indirects := 1 124 | vt := v.Type() 125 | upv := unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetPtr) 126 | rvf := *(*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetFlag)) 127 | if rvf&flagIndir != 0 { 128 | vt = reflect.PtrTo(v.Type()) 129 | indirects++ 130 | } else if offsetScalar != 0 { 131 | // The value is in the scalar field when it's not one of the 132 | // reference types. 133 | switch vt.Kind() { 134 | case reflect.Uintptr: 135 | case reflect.Chan: 136 | case reflect.Func: 137 | case reflect.Map: 138 | case reflect.Ptr: 139 | case reflect.UnsafePointer: 140 | default: 141 | upv = unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + 142 | offsetScalar) 143 | } 144 | } 145 | 146 | pv := reflect.NewAt(vt, upv) 147 | rv = pv 148 | for i := 0; i < indirects; i++ { 149 | rv = rv.Elem() 150 | } 151 | return rv 152 | } 153 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/bypasssafe.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2015 Dave Collins 2 | // 3 | // Permission to use, copy, modify, and distribute this software for any 4 | // purpose with or without fee is hereby granted, provided that the above 5 | // copyright notice and this permission notice appear in all copies. 6 | // 7 | // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | // NOTE: Due to the following build constraints, this file will only be compiled 16 | // when the code is running on Google App Engine, compiled by GopherJS, or 17 | // "-tags safe" is added to the go build command line. The "disableunsafe" 18 | // tag is deprecated and thus should not be used. 19 | // +build js appengine safe disableunsafe 20 | 21 | package spew 22 | 23 | import "reflect" 24 | 25 | const ( 26 | // UnsafeDisabled is a build-time constant which specifies whether or 27 | // not access to the unsafe package is available. 28 | UnsafeDisabled = true 29 | ) 30 | 31 | // unsafeReflectValue typically converts the passed reflect.Value into a one 32 | // that bypasses the typical safety restrictions preventing access to 33 | // unaddressable and unexported data. However, doing this relies on access to 34 | // the unsafe package. This is a stub version which simply returns the passed 35 | // reflect.Value when the unsafe package is not available. 36 | func unsafeReflectValue(v reflect.Value) reflect.Value { 37 | return v 38 | } 39 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/common_test.go: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2013 Dave Collins 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | package spew_test 18 | 19 | import ( 20 | "fmt" 21 | "reflect" 22 | "testing" 23 | 24 | "github.com/davecgh/go-spew/spew" 25 | ) 26 | 27 | // custom type to test Stinger interface on non-pointer receiver. 28 | type stringer string 29 | 30 | // String implements the Stringer interface for testing invocation of custom 31 | // stringers on types with non-pointer receivers. 32 | func (s stringer) String() string { 33 | return "stringer " + string(s) 34 | } 35 | 36 | // custom type to test Stinger interface on pointer receiver. 37 | type pstringer string 38 | 39 | // String implements the Stringer interface for testing invocation of custom 40 | // stringers on types with only pointer receivers. 41 | func (s *pstringer) String() string { 42 | return "stringer " + string(*s) 43 | } 44 | 45 | // xref1 and xref2 are cross referencing structs for testing circular reference 46 | // detection. 47 | type xref1 struct { 48 | ps2 *xref2 49 | } 50 | type xref2 struct { 51 | ps1 *xref1 52 | } 53 | 54 | // indirCir1, indirCir2, and indirCir3 are used to generate an indirect circular 55 | // reference for testing detection. 56 | type indirCir1 struct { 57 | ps2 *indirCir2 58 | } 59 | type indirCir2 struct { 60 | ps3 *indirCir3 61 | } 62 | type indirCir3 struct { 63 | ps1 *indirCir1 64 | } 65 | 66 | // embed is used to test embedded structures. 67 | type embed struct { 68 | a string 69 | } 70 | 71 | // embedwrap is used to test embedded structures. 72 | type embedwrap struct { 73 | *embed 74 | e *embed 75 | } 76 | 77 | // panicer is used to intentionally cause a panic for testing spew properly 78 | // handles them 79 | type panicer int 80 | 81 | func (p panicer) String() string { 82 | panic("test panic") 83 | } 84 | 85 | // customError is used to test custom error interface invocation. 86 | type customError int 87 | 88 | func (e customError) Error() string { 89 | return fmt.Sprintf("error: %d", int(e)) 90 | } 91 | 92 | // stringizeWants converts a slice of wanted test output into a format suitable 93 | // for a test error message. 94 | func stringizeWants(wants []string) string { 95 | s := "" 96 | for i, want := range wants { 97 | if i > 0 { 98 | s += fmt.Sprintf("want%d: %s", i+1, want) 99 | } else { 100 | s += "want: " + want 101 | } 102 | } 103 | return s 104 | } 105 | 106 | // testFailed returns whether or not a test failed by checking if the result 107 | // of the test is in the slice of wanted strings. 108 | func testFailed(result string, wants []string) bool { 109 | for _, want := range wants { 110 | if result == want { 111 | return false 112 | } 113 | } 114 | return true 115 | } 116 | 117 | type sortableStruct struct { 118 | x int 119 | } 120 | 121 | func (ss sortableStruct) String() string { 122 | return fmt.Sprintf("ss.%d", ss.x) 123 | } 124 | 125 | type unsortableStruct struct { 126 | x int 127 | } 128 | 129 | type sortTestCase struct { 130 | input []reflect.Value 131 | expected []reflect.Value 132 | } 133 | 134 | func helpTestSortValues(tests []sortTestCase, cs *spew.ConfigState, t *testing.T) { 135 | getInterfaces := func(values []reflect.Value) []interface{} { 136 | interfaces := []interface{}{} 137 | for _, v := range values { 138 | interfaces = append(interfaces, v.Interface()) 139 | } 140 | return interfaces 141 | } 142 | 143 | for _, test := range tests { 144 | spew.SortValues(test.input, cs) 145 | // reflect.DeepEqual cannot really make sense of reflect.Value, 146 | // probably because of all the pointer tricks. For instance, 147 | // v(2.0) != v(2.0) on a 32-bits system. Turn them into interface{} 148 | // instead. 149 | input := getInterfaces(test.input) 150 | expected := getInterfaces(test.expected) 151 | if !reflect.DeepEqual(input, expected) { 152 | t.Errorf("Sort mismatch:\n %v != %v", input, expected) 153 | } 154 | } 155 | } 156 | 157 | // TestSortValues ensures the sort functionality for relect.Value based sorting 158 | // works as intended. 159 | func TestSortValues(t *testing.T) { 160 | v := reflect.ValueOf 161 | 162 | a := v("a") 163 | b := v("b") 164 | c := v("c") 165 | embedA := v(embed{"a"}) 166 | embedB := v(embed{"b"}) 167 | embedC := v(embed{"c"}) 168 | tests := []sortTestCase{ 169 | // No values. 170 | { 171 | []reflect.Value{}, 172 | []reflect.Value{}, 173 | }, 174 | // Bools. 175 | { 176 | []reflect.Value{v(false), v(true), v(false)}, 177 | []reflect.Value{v(false), v(false), v(true)}, 178 | }, 179 | // Ints. 180 | { 181 | []reflect.Value{v(2), v(1), v(3)}, 182 | []reflect.Value{v(1), v(2), v(3)}, 183 | }, 184 | // Uints. 185 | { 186 | []reflect.Value{v(uint8(2)), v(uint8(1)), v(uint8(3))}, 187 | []reflect.Value{v(uint8(1)), v(uint8(2)), v(uint8(3))}, 188 | }, 189 | // Floats. 190 | { 191 | []reflect.Value{v(2.0), v(1.0), v(3.0)}, 192 | []reflect.Value{v(1.0), v(2.0), v(3.0)}, 193 | }, 194 | // Strings. 195 | { 196 | []reflect.Value{b, a, c}, 197 | []reflect.Value{a, b, c}, 198 | }, 199 | // Array 200 | { 201 | []reflect.Value{v([3]int{3, 2, 1}), v([3]int{1, 3, 2}), v([3]int{1, 2, 3})}, 202 | []reflect.Value{v([3]int{1, 2, 3}), v([3]int{1, 3, 2}), v([3]int{3, 2, 1})}, 203 | }, 204 | // Uintptrs. 205 | { 206 | []reflect.Value{v(uintptr(2)), v(uintptr(1)), v(uintptr(3))}, 207 | []reflect.Value{v(uintptr(1)), v(uintptr(2)), v(uintptr(3))}, 208 | }, 209 | // SortableStructs. 210 | { 211 | // Note: not sorted - DisableMethods is set. 212 | []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})}, 213 | []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})}, 214 | }, 215 | // UnsortableStructs. 216 | { 217 | // Note: not sorted - SpewKeys is false. 218 | []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})}, 219 | []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})}, 220 | }, 221 | // Invalid. 222 | { 223 | []reflect.Value{embedB, embedA, embedC}, 224 | []reflect.Value{embedB, embedA, embedC}, 225 | }, 226 | } 227 | cs := spew.ConfigState{DisableMethods: true, SpewKeys: false} 228 | helpTestSortValues(tests, &cs, t) 229 | } 230 | 231 | // TestSortValuesWithMethods ensures the sort functionality for relect.Value 232 | // based sorting works as intended when using string methods. 233 | func TestSortValuesWithMethods(t *testing.T) { 234 | v := reflect.ValueOf 235 | 236 | a := v("a") 237 | b := v("b") 238 | c := v("c") 239 | tests := []sortTestCase{ 240 | // Ints. 241 | { 242 | []reflect.Value{v(2), v(1), v(3)}, 243 | []reflect.Value{v(1), v(2), v(3)}, 244 | }, 245 | // Strings. 246 | { 247 | []reflect.Value{b, a, c}, 248 | []reflect.Value{a, b, c}, 249 | }, 250 | // SortableStructs. 251 | { 252 | []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})}, 253 | []reflect.Value{v(sortableStruct{1}), v(sortableStruct{2}), v(sortableStruct{3})}, 254 | }, 255 | // UnsortableStructs. 256 | { 257 | // Note: not sorted - SpewKeys is false. 258 | []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})}, 259 | []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})}, 260 | }, 261 | } 262 | cs := spew.ConfigState{DisableMethods: false, SpewKeys: false} 263 | helpTestSortValues(tests, &cs, t) 264 | } 265 | 266 | // TestSortValuesWithSpew ensures the sort functionality for relect.Value 267 | // based sorting works as intended when using spew to stringify keys. 268 | func TestSortValuesWithSpew(t *testing.T) { 269 | v := reflect.ValueOf 270 | 271 | a := v("a") 272 | b := v("b") 273 | c := v("c") 274 | tests := []sortTestCase{ 275 | // Ints. 276 | { 277 | []reflect.Value{v(2), v(1), v(3)}, 278 | []reflect.Value{v(1), v(2), v(3)}, 279 | }, 280 | // Strings. 281 | { 282 | []reflect.Value{b, a, c}, 283 | []reflect.Value{a, b, c}, 284 | }, 285 | // SortableStructs. 286 | { 287 | []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})}, 288 | []reflect.Value{v(sortableStruct{1}), v(sortableStruct{2}), v(sortableStruct{3})}, 289 | }, 290 | // UnsortableStructs. 291 | { 292 | []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})}, 293 | []reflect.Value{v(unsortableStruct{1}), v(unsortableStruct{2}), v(unsortableStruct{3})}, 294 | }, 295 | } 296 | cs := spew.ConfigState{DisableMethods: true, SpewKeys: true} 297 | helpTestSortValues(tests, &cs, t) 298 | } 299 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/doc.go: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2013 Dave Collins 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | /* 18 | Package spew implements a deep pretty printer for Go data structures to aid in 19 | debugging. 20 | 21 | A quick overview of the additional features spew provides over the built-in 22 | printing facilities for Go data types are as follows: 23 | 24 | * Pointers are dereferenced and followed 25 | * Circular data structures are detected and handled properly 26 | * Custom Stringer/error interfaces are optionally invoked, including 27 | on unexported types 28 | * Custom types which only implement the Stringer/error interfaces via 29 | a pointer receiver are optionally invoked when passing non-pointer 30 | variables 31 | * Byte arrays and slices are dumped like the hexdump -C command which 32 | includes offsets, byte values in hex, and ASCII output (only when using 33 | Dump style) 34 | 35 | There are two different approaches spew allows for dumping Go data structures: 36 | 37 | * Dump style which prints with newlines, customizable indentation, 38 | and additional debug information such as types and all pointer addresses 39 | used to indirect to the final value 40 | * A custom Formatter interface that integrates cleanly with the standard fmt 41 | package and replaces %v, %+v, %#v, and %#+v to provide inline printing 42 | similar to the default %v while providing the additional functionality 43 | outlined above and passing unsupported format verbs such as %x and %q 44 | along to fmt 45 | 46 | Quick Start 47 | 48 | This section demonstrates how to quickly get started with spew. See the 49 | sections below for further details on formatting and configuration options. 50 | 51 | To dump a variable with full newlines, indentation, type, and pointer 52 | information use Dump, Fdump, or Sdump: 53 | spew.Dump(myVar1, myVar2, ...) 54 | spew.Fdump(someWriter, myVar1, myVar2, ...) 55 | str := spew.Sdump(myVar1, myVar2, ...) 56 | 57 | Alternatively, if you would prefer to use format strings with a compacted inline 58 | printing style, use the convenience wrappers Printf, Fprintf, etc with 59 | %v (most compact), %+v (adds pointer addresses), %#v (adds types), or 60 | %#+v (adds types and pointer addresses): 61 | spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2) 62 | spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 63 | spew.Fprintf(someWriter, "myVar1: %v -- myVar2: %+v", myVar1, myVar2) 64 | spew.Fprintf(someWriter, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 65 | 66 | Configuration Options 67 | 68 | Configuration of spew is handled by fields in the ConfigState type. For 69 | convenience, all of the top-level functions use a global state available 70 | via the spew.Config global. 71 | 72 | It is also possible to create a ConfigState instance that provides methods 73 | equivalent to the top-level functions. This allows concurrent configuration 74 | options. See the ConfigState documentation for more details. 75 | 76 | The following configuration options are available: 77 | * Indent 78 | String to use for each indentation level for Dump functions. 79 | It is a single space by default. A popular alternative is "\t". 80 | 81 | * MaxDepth 82 | Maximum number of levels to descend into nested data structures. 83 | There is no limit by default. 84 | 85 | * DisableMethods 86 | Disables invocation of error and Stringer interface methods. 87 | Method invocation is enabled by default. 88 | 89 | * DisablePointerMethods 90 | Disables invocation of error and Stringer interface methods on types 91 | which only accept pointer receivers from non-pointer variables. 92 | Pointer method invocation is enabled by default. 93 | 94 | * ContinueOnMethod 95 | Enables recursion into types after invoking error and Stringer interface 96 | methods. Recursion after method invocation is disabled by default. 97 | 98 | * SortKeys 99 | Specifies map keys should be sorted before being printed. Use 100 | this to have a more deterministic, diffable output. Note that 101 | only native types (bool, int, uint, floats, uintptr and string) 102 | and types which implement error or Stringer interfaces are 103 | supported with other types sorted according to the 104 | reflect.Value.String() output which guarantees display 105 | stability. Natural map order is used by default. 106 | 107 | * SpewKeys 108 | Specifies that, as a last resort attempt, map keys should be 109 | spewed to strings and sorted by those strings. This is only 110 | considered if SortKeys is true. 111 | 112 | Dump Usage 113 | 114 | Simply call spew.Dump with a list of variables you want to dump: 115 | 116 | spew.Dump(myVar1, myVar2, ...) 117 | 118 | You may also call spew.Fdump if you would prefer to output to an arbitrary 119 | io.Writer. For example, to dump to standard error: 120 | 121 | spew.Fdump(os.Stderr, myVar1, myVar2, ...) 122 | 123 | A third option is to call spew.Sdump to get the formatted output as a string: 124 | 125 | str := spew.Sdump(myVar1, myVar2, ...) 126 | 127 | Sample Dump Output 128 | 129 | See the Dump example for details on the setup of the types and variables being 130 | shown here. 131 | 132 | (main.Foo) { 133 | unexportedField: (*main.Bar)(0xf84002e210)({ 134 | flag: (main.Flag) flagTwo, 135 | data: (uintptr) 136 | }), 137 | ExportedField: (map[interface {}]interface {}) (len=1) { 138 | (string) (len=3) "one": (bool) true 139 | } 140 | } 141 | 142 | Byte (and uint8) arrays and slices are displayed uniquely like the hexdump -C 143 | command as shown. 144 | ([]uint8) (len=32 cap=32) { 145 | 00000000 11 12 13 14 15 16 17 18 19 1a 1b 1c 1d 1e 1f 20 |............... | 146 | 00000010 21 22 23 24 25 26 27 28 29 2a 2b 2c 2d 2e 2f 30 |!"#$%&'()*+,-./0| 147 | 00000020 31 32 |12| 148 | } 149 | 150 | Custom Formatter 151 | 152 | Spew provides a custom formatter that implements the fmt.Formatter interface 153 | so that it integrates cleanly with standard fmt package printing functions. The 154 | formatter is useful for inline printing of smaller data types similar to the 155 | standard %v format specifier. 156 | 157 | The custom formatter only responds to the %v (most compact), %+v (adds pointer 158 | addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb 159 | combinations. Any other verbs such as %x and %q will be sent to the the 160 | standard fmt package for formatting. In addition, the custom formatter ignores 161 | the width and precision arguments (however they will still work on the format 162 | specifiers not handled by the custom formatter). 163 | 164 | Custom Formatter Usage 165 | 166 | The simplest way to make use of the spew custom formatter is to call one of the 167 | convenience functions such as spew.Printf, spew.Println, or spew.Printf. The 168 | functions have syntax you are most likely already familiar with: 169 | 170 | spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2) 171 | spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 172 | spew.Println(myVar, myVar2) 173 | spew.Fprintf(os.Stderr, "myVar1: %v -- myVar2: %+v", myVar1, myVar2) 174 | spew.Fprintf(os.Stderr, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 175 | 176 | See the Index for the full list convenience functions. 177 | 178 | Sample Formatter Output 179 | 180 | Double pointer to a uint8: 181 | %v: <**>5 182 | %+v: <**>(0xf8400420d0->0xf8400420c8)5 183 | %#v: (**uint8)5 184 | %#+v: (**uint8)(0xf8400420d0->0xf8400420c8)5 185 | 186 | Pointer to circular struct with a uint8 field and a pointer to itself: 187 | %v: <*>{1 <*>} 188 | %+v: <*>(0xf84003e260){ui8:1 c:<*>(0xf84003e260)} 189 | %#v: (*main.circular){ui8:(uint8)1 c:(*main.circular)} 190 | %#+v: (*main.circular)(0xf84003e260){ui8:(uint8)1 c:(*main.circular)(0xf84003e260)} 191 | 192 | See the Printf example for details on the setup of variables being shown 193 | here. 194 | 195 | Errors 196 | 197 | Since it is possible for custom Stringer/error interfaces to panic, spew 198 | detects them and handles them internally by printing the panic information 199 | inline with the output. Since spew is intended to provide deep pretty printing 200 | capabilities on structures, it intentionally does not return any errors. 201 | */ 202 | package spew 203 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/dumpcgo_test.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013 Dave Collins 2 | // 3 | // Permission to use, copy, modify, and distribute this software for any 4 | // purpose with or without fee is hereby granted, provided that the above 5 | // copyright notice and this permission notice appear in all copies. 6 | // 7 | // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | // NOTE: Due to the following build constraints, this file will only be compiled 16 | // when both cgo is supported and "-tags testcgo" is added to the go test 17 | // command line. This means the cgo tests are only added (and hence run) when 18 | // specifially requested. This configuration is used because spew itself 19 | // does not require cgo to run even though it does handle certain cgo types 20 | // specially. Rather than forcing all clients to require cgo and an external 21 | // C compiler just to run the tests, this scheme makes them optional. 22 | // +build cgo,testcgo 23 | 24 | package spew_test 25 | 26 | import ( 27 | "fmt" 28 | 29 | "github.com/davecgh/go-spew/spew/testdata" 30 | ) 31 | 32 | func addCgoDumpTests() { 33 | // C char pointer. 34 | v := testdata.GetCgoCharPointer() 35 | nv := testdata.GetCgoNullCharPointer() 36 | pv := &v 37 | vcAddr := fmt.Sprintf("%p", v) 38 | vAddr := fmt.Sprintf("%p", pv) 39 | pvAddr := fmt.Sprintf("%p", &pv) 40 | vt := "*testdata._Ctype_char" 41 | vs := "116" 42 | addDumpTest(v, "("+vt+")("+vcAddr+")("+vs+")\n") 43 | addDumpTest(pv, "(*"+vt+")("+vAddr+"->"+vcAddr+")("+vs+")\n") 44 | addDumpTest(&pv, "(**"+vt+")("+pvAddr+"->"+vAddr+"->"+vcAddr+")("+vs+")\n") 45 | addDumpTest(nv, "("+vt+")()\n") 46 | 47 | // C char array. 48 | v2, v2l, v2c := testdata.GetCgoCharArray() 49 | v2Len := fmt.Sprintf("%d", v2l) 50 | v2Cap := fmt.Sprintf("%d", v2c) 51 | v2t := "[6]testdata._Ctype_char" 52 | v2s := "(len=" + v2Len + " cap=" + v2Cap + ") " + 53 | "{\n 00000000 74 65 73 74 32 00 " + 54 | " |test2.|\n}" 55 | addDumpTest(v2, "("+v2t+") "+v2s+"\n") 56 | 57 | // C unsigned char array. 58 | v3, v3l, v3c := testdata.GetCgoUnsignedCharArray() 59 | v3Len := fmt.Sprintf("%d", v3l) 60 | v3Cap := fmt.Sprintf("%d", v3c) 61 | v3t := "[6]testdata._Ctype_unsignedchar" 62 | v3t2 := "[6]testdata._Ctype_uchar" 63 | v3s := "(len=" + v3Len + " cap=" + v3Cap + ") " + 64 | "{\n 00000000 74 65 73 74 33 00 " + 65 | " |test3.|\n}" 66 | addDumpTest(v3, "("+v3t+") "+v3s+"\n", "("+v3t2+") "+v3s+"\n") 67 | 68 | // C signed char array. 69 | v4, v4l, v4c := testdata.GetCgoSignedCharArray() 70 | v4Len := fmt.Sprintf("%d", v4l) 71 | v4Cap := fmt.Sprintf("%d", v4c) 72 | v4t := "[6]testdata._Ctype_schar" 73 | v4t2 := "testdata._Ctype_schar" 74 | v4s := "(len=" + v4Len + " cap=" + v4Cap + ") " + 75 | "{\n (" + v4t2 + ") 116,\n (" + v4t2 + ") 101,\n (" + v4t2 + 76 | ") 115,\n (" + v4t2 + ") 116,\n (" + v4t2 + ") 52,\n (" + v4t2 + 77 | ") 0\n}" 78 | addDumpTest(v4, "("+v4t+") "+v4s+"\n") 79 | 80 | // C uint8_t array. 81 | v5, v5l, v5c := testdata.GetCgoUint8tArray() 82 | v5Len := fmt.Sprintf("%d", v5l) 83 | v5Cap := fmt.Sprintf("%d", v5c) 84 | v5t := "[6]testdata._Ctype_uint8_t" 85 | v5s := "(len=" + v5Len + " cap=" + v5Cap + ") " + 86 | "{\n 00000000 74 65 73 74 35 00 " + 87 | " |test5.|\n}" 88 | addDumpTest(v5, "("+v5t+") "+v5s+"\n") 89 | 90 | // C typedefed unsigned char array. 91 | v6, v6l, v6c := testdata.GetCgoTypdefedUnsignedCharArray() 92 | v6Len := fmt.Sprintf("%d", v6l) 93 | v6Cap := fmt.Sprintf("%d", v6c) 94 | v6t := "[6]testdata._Ctype_custom_uchar_t" 95 | v6s := "(len=" + v6Len + " cap=" + v6Cap + ") " + 96 | "{\n 00000000 74 65 73 74 36 00 " + 97 | " |test6.|\n}" 98 | addDumpTest(v6, "("+v6t+") "+v6s+"\n") 99 | } 100 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/dumpnocgo_test.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013 Dave Collins 2 | // 3 | // Permission to use, copy, modify, and distribute this software for any 4 | // purpose with or without fee is hereby granted, provided that the above 5 | // copyright notice and this permission notice appear in all copies. 6 | // 7 | // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | // NOTE: Due to the following build constraints, this file will only be compiled 16 | // when either cgo is not supported or "-tags testcgo" is not added to the go 17 | // test command line. This file intentionally does not setup any cgo tests in 18 | // this scenario. 19 | // +build !cgo !testcgo 20 | 21 | package spew_test 22 | 23 | func addCgoDumpTests() { 24 | // Don't add any tests for cgo since this file is only compiled when 25 | // there should not be any cgo tests. 26 | } 27 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/example_test.go: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2013 Dave Collins 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | package spew_test 18 | 19 | import ( 20 | "fmt" 21 | 22 | "github.com/davecgh/go-spew/spew" 23 | ) 24 | 25 | type Flag int 26 | 27 | const ( 28 | flagOne Flag = iota 29 | flagTwo 30 | ) 31 | 32 | var flagStrings = map[Flag]string{ 33 | flagOne: "flagOne", 34 | flagTwo: "flagTwo", 35 | } 36 | 37 | func (f Flag) String() string { 38 | if s, ok := flagStrings[f]; ok { 39 | return s 40 | } 41 | return fmt.Sprintf("Unknown flag (%d)", int(f)) 42 | } 43 | 44 | type Bar struct { 45 | data uintptr 46 | } 47 | 48 | type Foo struct { 49 | unexportedField Bar 50 | ExportedField map[interface{}]interface{} 51 | } 52 | 53 | // This example demonstrates how to use Dump to dump variables to stdout. 54 | func ExampleDump() { 55 | // The following package level declarations are assumed for this example: 56 | /* 57 | type Flag int 58 | 59 | const ( 60 | flagOne Flag = iota 61 | flagTwo 62 | ) 63 | 64 | var flagStrings = map[Flag]string{ 65 | flagOne: "flagOne", 66 | flagTwo: "flagTwo", 67 | } 68 | 69 | func (f Flag) String() string { 70 | if s, ok := flagStrings[f]; ok { 71 | return s 72 | } 73 | return fmt.Sprintf("Unknown flag (%d)", int(f)) 74 | } 75 | 76 | type Bar struct { 77 | data uintptr 78 | } 79 | 80 | type Foo struct { 81 | unexportedField Bar 82 | ExportedField map[interface{}]interface{} 83 | } 84 | */ 85 | 86 | // Setup some sample data structures for the example. 87 | bar := Bar{uintptr(0)} 88 | s1 := Foo{bar, map[interface{}]interface{}{"one": true}} 89 | f := Flag(5) 90 | b := []byte{ 91 | 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 92 | 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 93 | 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 94 | 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30, 95 | 0x31, 0x32, 96 | } 97 | 98 | // Dump! 99 | spew.Dump(s1, f, b) 100 | 101 | // Output: 102 | // (spew_test.Foo) { 103 | // unexportedField: (spew_test.Bar) { 104 | // data: (uintptr) 105 | // }, 106 | // ExportedField: (map[interface {}]interface {}) (len=1) { 107 | // (string) (len=3) "one": (bool) true 108 | // } 109 | // } 110 | // (spew_test.Flag) Unknown flag (5) 111 | // ([]uint8) (len=34 cap=34) { 112 | // 00000000 11 12 13 14 15 16 17 18 19 1a 1b 1c 1d 1e 1f 20 |............... | 113 | // 00000010 21 22 23 24 25 26 27 28 29 2a 2b 2c 2d 2e 2f 30 |!"#$%&'()*+,-./0| 114 | // 00000020 31 32 |12| 115 | // } 116 | // 117 | } 118 | 119 | // This example demonstrates how to use Printf to display a variable with a 120 | // format string and inline formatting. 121 | func ExamplePrintf() { 122 | // Create a double pointer to a uint 8. 123 | ui8 := uint8(5) 124 | pui8 := &ui8 125 | ppui8 := &pui8 126 | 127 | // Create a circular data type. 128 | type circular struct { 129 | ui8 uint8 130 | c *circular 131 | } 132 | c := circular{ui8: 1} 133 | c.c = &c 134 | 135 | // Print! 136 | spew.Printf("ppui8: %v\n", ppui8) 137 | spew.Printf("circular: %v\n", c) 138 | 139 | // Output: 140 | // ppui8: <**>5 141 | // circular: {1 <*>{1 <*>}} 142 | } 143 | 144 | // This example demonstrates how to use a ConfigState. 145 | func ExampleConfigState() { 146 | // Modify the indent level of the ConfigState only. The global 147 | // configuration is not modified. 148 | scs := spew.ConfigState{Indent: "\t"} 149 | 150 | // Output using the ConfigState instance. 151 | v := map[string]int{"one": 1} 152 | scs.Printf("v: %v\n", v) 153 | scs.Dump(v) 154 | 155 | // Output: 156 | // v: map[one:1] 157 | // (map[string]int) (len=1) { 158 | // (string) (len=3) "one": (int) 1 159 | // } 160 | } 161 | 162 | // This example demonstrates how to use ConfigState.Dump to dump variables to 163 | // stdout 164 | func ExampleConfigState_Dump() { 165 | // See the top-level Dump example for details on the types used in this 166 | // example. 167 | 168 | // Create two ConfigState instances with different indentation. 169 | scs := spew.ConfigState{Indent: "\t"} 170 | scs2 := spew.ConfigState{Indent: " "} 171 | 172 | // Setup some sample data structures for the example. 173 | bar := Bar{uintptr(0)} 174 | s1 := Foo{bar, map[interface{}]interface{}{"one": true}} 175 | 176 | // Dump using the ConfigState instances. 177 | scs.Dump(s1) 178 | scs2.Dump(s1) 179 | 180 | // Output: 181 | // (spew_test.Foo) { 182 | // unexportedField: (spew_test.Bar) { 183 | // data: (uintptr) 184 | // }, 185 | // ExportedField: (map[interface {}]interface {}) (len=1) { 186 | // (string) (len=3) "one": (bool) true 187 | // } 188 | // } 189 | // (spew_test.Foo) { 190 | // unexportedField: (spew_test.Bar) { 191 | // data: (uintptr) 192 | // }, 193 | // ExportedField: (map[interface {}]interface {}) (len=1) { 194 | // (string) (len=3) "one": (bool) true 195 | // } 196 | // } 197 | // 198 | } 199 | 200 | // This example demonstrates how to use ConfigState.Printf to display a variable 201 | // with a format string and inline formatting. 202 | func ExampleConfigState_Printf() { 203 | // See the top-level Dump example for details on the types used in this 204 | // example. 205 | 206 | // Create two ConfigState instances and modify the method handling of the 207 | // first ConfigState only. 208 | scs := spew.NewDefaultConfig() 209 | scs2 := spew.NewDefaultConfig() 210 | scs.DisableMethods = true 211 | 212 | // Alternatively 213 | // scs := spew.ConfigState{Indent: " ", DisableMethods: true} 214 | // scs2 := spew.ConfigState{Indent: " "} 215 | 216 | // This is of type Flag which implements a Stringer and has raw value 1. 217 | f := flagTwo 218 | 219 | // Dump using the ConfigState instances. 220 | scs.Printf("f: %v\n", f) 221 | scs2.Printf("f: %v\n", f) 222 | 223 | // Output: 224 | // f: 1 225 | // f: flagTwo 226 | } 227 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/internal_test.go: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2013 Dave Collins 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | /* 18 | This test file is part of the spew package rather than than the spew_test 19 | package because it needs access to internals to properly test certain cases 20 | which are not possible via the public interface since they should never happen. 21 | */ 22 | 23 | package spew 24 | 25 | import ( 26 | "bytes" 27 | "reflect" 28 | "testing" 29 | ) 30 | 31 | // dummyFmtState implements a fake fmt.State to use for testing invalid 32 | // reflect.Value handling. This is necessary because the fmt package catches 33 | // invalid values before invoking the formatter on them. 34 | type dummyFmtState struct { 35 | bytes.Buffer 36 | } 37 | 38 | func (dfs *dummyFmtState) Flag(f int) bool { 39 | if f == int('+') { 40 | return true 41 | } 42 | return false 43 | } 44 | 45 | func (dfs *dummyFmtState) Precision() (int, bool) { 46 | return 0, false 47 | } 48 | 49 | func (dfs *dummyFmtState) Width() (int, bool) { 50 | return 0, false 51 | } 52 | 53 | // TestInvalidReflectValue ensures the dump and formatter code handles an 54 | // invalid reflect value properly. This needs access to internal state since it 55 | // should never happen in real code and therefore can't be tested via the public 56 | // API. 57 | func TestInvalidReflectValue(t *testing.T) { 58 | i := 1 59 | 60 | // Dump invalid reflect value. 61 | v := new(reflect.Value) 62 | buf := new(bytes.Buffer) 63 | d := dumpState{w: buf, cs: &Config} 64 | d.dump(*v) 65 | s := buf.String() 66 | want := "" 67 | if s != want { 68 | t.Errorf("InvalidReflectValue #%d\n got: %s want: %s", i, s, want) 69 | } 70 | i++ 71 | 72 | // Formatter invalid reflect value. 73 | buf2 := new(dummyFmtState) 74 | f := formatState{value: *v, cs: &Config, fs: buf2} 75 | f.format(*v) 76 | s = buf2.String() 77 | want = "" 78 | if s != want { 79 | t.Errorf("InvalidReflectValue #%d got: %s want: %s", i, s, want) 80 | } 81 | } 82 | 83 | // SortValues makes the internal sortValues function available to the test 84 | // package. 85 | func SortValues(values []reflect.Value, cs *ConfigState) { 86 | sortValues(values, cs) 87 | } 88 | -------------------------------------------------------------------------------- /vendor/github.com/davecgh/go-spew/spew/internalunsafe_test.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2013-2015 Dave Collins 2 | 3 | // Permission to use, copy, modify, and distribute this software for any 4 | // purpose with or without fee is hereby granted, provided that the above 5 | // copyright notice and this permission notice appear in all copies. 6 | 7 | // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | // NOTE: Due to the following build constraints, this file will only be compiled 16 | // when the code is not running on Google App Engine, compiled by GopherJS, and 17 | // "-tags safe" is not added to the go build command line. The "disableunsafe" 18 | // tag is deprecated and thus should not be used. 19 | // +build !js,!appengine,!safe,!disableunsafe 20 | 21 | /* 22 | This test file is part of the spew package rather than than the spew_test 23 | package because it needs access to internals to properly test certain cases 24 | which are not possible via the public interface since they should never happen. 25 | */ 26 | 27 | package spew 28 | 29 | import ( 30 | "bytes" 31 | "reflect" 32 | "testing" 33 | "unsafe" 34 | ) 35 | 36 | // changeKind uses unsafe to intentionally change the kind of a reflect.Value to 37 | // the maximum kind value which does not exist. This is needed to test the 38 | // fallback code which punts to the standard fmt library for new types that 39 | // might get added to the language. 40 | func changeKind(v *reflect.Value, readOnly bool) { 41 | rvf := (*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(v)) + offsetFlag)) 42 | *rvf = *rvf | ((1< 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | package spew 18 | 19 | import ( 20 | "fmt" 21 | "io" 22 | ) 23 | 24 | // Errorf is a wrapper for fmt.Errorf that treats each argument as if it were 25 | // passed with a default Formatter interface returned by NewFormatter. It 26 | // returns the formatted string as a value that satisfies error. See 27 | // NewFormatter for formatting details. 28 | // 29 | // This function is shorthand for the following syntax: 30 | // 31 | // fmt.Errorf(format, spew.NewFormatter(a), spew.NewFormatter(b)) 32 | func Errorf(format string, a ...interface{}) (err error) { 33 | return fmt.Errorf(format, convertArgs(a)...) 34 | } 35 | 36 | // Fprint is a wrapper for fmt.Fprint that treats each argument as if it were 37 | // passed with a default Formatter interface returned by NewFormatter. It 38 | // returns the number of bytes written and any write error encountered. See 39 | // NewFormatter for formatting details. 40 | // 41 | // This function is shorthand for the following syntax: 42 | // 43 | // fmt.Fprint(w, spew.NewFormatter(a), spew.NewFormatter(b)) 44 | func Fprint(w io.Writer, a ...interface{}) (n int, err error) { 45 | return fmt.Fprint(w, convertArgs(a)...) 46 | } 47 | 48 | // Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were 49 | // passed with a default Formatter interface returned by NewFormatter. It 50 | // returns the number of bytes written and any write error encountered. See 51 | // NewFormatter for formatting details. 52 | // 53 | // This function is shorthand for the following syntax: 54 | // 55 | // fmt.Fprintf(w, format, spew.NewFormatter(a), spew.NewFormatter(b)) 56 | func Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) { 57 | return fmt.Fprintf(w, format, convertArgs(a)...) 58 | } 59 | 60 | // Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it 61 | // passed with a default Formatter interface returned by NewFormatter. See 62 | // NewFormatter for formatting details. 63 | // 64 | // This function is shorthand for the following syntax: 65 | // 66 | // fmt.Fprintln(w, spew.NewFormatter(a), spew.NewFormatter(b)) 67 | func Fprintln(w io.Writer, a ...interface{}) (n int, err error) { 68 | return fmt.Fprintln(w, convertArgs(a)...) 69 | } 70 | 71 | // Print is a wrapper for fmt.Print that treats each argument as if it were 72 | // passed with a default Formatter interface returned by NewFormatter. It 73 | // returns the number of bytes written and any write error encountered. See 74 | // NewFormatter for formatting details. 75 | // 76 | // This function is shorthand for the following syntax: 77 | // 78 | // fmt.Print(spew.NewFormatter(a), spew.NewFormatter(b)) 79 | func Print(a ...interface{}) (n int, err error) { 80 | return fmt.Print(convertArgs(a)...) 81 | } 82 | 83 | // Printf is a wrapper for fmt.Printf that treats each argument as if it were 84 | // passed with a default Formatter interface returned by NewFormatter. It 85 | // returns the number of bytes written and any write error encountered. See 86 | // NewFormatter for formatting details. 87 | // 88 | // This function is shorthand for the following syntax: 89 | // 90 | // fmt.Printf(format, spew.NewFormatter(a), spew.NewFormatter(b)) 91 | func Printf(format string, a ...interface{}) (n int, err error) { 92 | return fmt.Printf(format, convertArgs(a)...) 93 | } 94 | 95 | // Println is a wrapper for fmt.Println that treats each argument as if it were 96 | // passed with a default Formatter interface returned by NewFormatter. It 97 | // returns the number of bytes written and any write error encountered. See 98 | // NewFormatter for formatting details. 99 | // 100 | // This function is shorthand for the following syntax: 101 | // 102 | // fmt.Println(spew.NewFormatter(a), spew.NewFormatter(b)) 103 | func Println(a ...interface{}) (n int, err error) { 104 | return fmt.Println(convertArgs(a)...) 105 | } 106 | 107 | // Sprint is a wrapper for fmt.Sprint that treats each argument as if it were 108 | // passed with a default Formatter interface returned by NewFormatter. It 109 | // returns the resulting string. See NewFormatter for formatting details. 110 | // 111 | // This function is shorthand for the following syntax: 112 | // 113 | // fmt.Sprint(spew.NewFormatter(a), spew.NewFormatter(b)) 114 | func Sprint(a ...interface{}) string { 115 | return fmt.Sprint(convertArgs(a)...) 116 | } 117 | 118 | // Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were 119 | // passed with a default Formatter interface returned by NewFormatter. It 120 | // returns the resulting string. See NewFormatter for formatting details. 121 | // 122 | // This function is shorthand for the following syntax: 123 | // 124 | // fmt.Sprintf(format, spew.NewFormatter(a), spew.NewFormatter(b)) 125 | func Sprintf(format string, a ...interface{}) string { 126 | return fmt.Sprintf(format, convertArgs(a)...) 127 | } 128 | 129 | // Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it 130 | // were passed with a default Formatter interface returned by NewFormatter. It 131 | // returns the resulting string. See NewFormatter for formatting details. 132 | // 133 | // This function is shorthand for the following syntax: 134 | // 135 | // fmt.Sprintln(spew.NewFormatter(a), spew.NewFormatter(b)) 136 | func Sprintln(a ...interface{}) string { 137 | return fmt.Sprintln(convertArgs(a)...) 138 | } 139 | 140 | // convertArgs accepts a slice of arguments and returns a slice of the same 141 | // length with each argument converted to a default spew Formatter interface. 142 | func convertArgs(args []interface{}) (formatters []interface{}) { 143 | formatters = make([]interface{}, len(args)) 144 | for index, arg := range args { 145 | formatters[index] = NewFormatter(arg) 146 | } 147 | return formatters 148 | } 149 | -------------------------------------------------------------------------------- /vendor/github.com/pmezard/go-difflib/LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2013, Patrick Mezard 2 | All rights reserved. 3 | 4 | Redistribution and use in source and binary forms, with or without 5 | modification, are permitted provided that the following conditions are 6 | met: 7 | 8 | Redistributions of source code must retain the above copyright 9 | notice, this list of conditions and the following disclaimer. 10 | Redistributions in binary form must reproduce the above copyright 11 | notice, this list of conditions and the following disclaimer in the 12 | documentation and/or other materials provided with the distribution. 13 | The names of its contributors may not be used to endorse or promote 14 | products derived from this software without specific prior written 15 | permission. 16 | 17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS 18 | IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 19 | TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A 20 | PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 21 | HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 22 | SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 23 | TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 24 | PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 25 | LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 26 | NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 27 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/LICENCE.txt: -------------------------------------------------------------------------------- 1 | Copyright (c) 2012 - 2013 Mat Ryer and Tyler Bunnell 2 | 3 | Please consider promoting this project if you find it useful. 4 | 5 | Permission is hereby granted, free of charge, to any person 6 | obtaining a copy of this software and associated documentation 7 | files (the "Software"), to deal in the Software without restriction, 8 | including without limitation the rights to use, copy, modify, merge, 9 | publish, distribute, sublicense, and/or sell copies of the Software, 10 | and to permit persons to whom the Software is furnished to do so, 11 | subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 17 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES 18 | OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, 20 | DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT 21 | OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE 22 | OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2012 - 2013 Mat Ryer and Tyler Bunnell 2 | 3 | Please consider promoting this project if you find it useful. 4 | 5 | Permission is hereby granted, free of charge, to any person 6 | obtaining a copy of this software and associated documentation 7 | files (the "Software"), to deal in the Software without restriction, 8 | including without limitation the rights to use, copy, modify, merge, 9 | publish, distribute, sublicense, and/or sell copies of the Software, 10 | and to permit persons to whom the Software is furnished to do so, 11 | subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 17 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES 18 | OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, 20 | DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT 21 | OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE 22 | OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/assert/assertion_format.go.tmpl: -------------------------------------------------------------------------------- 1 | {{.CommentFormat}} 2 | func {{.DocInfo.Name}}f(t TestingT, {{.ParamsFormat}}) bool { 3 | return {{.DocInfo.Name}}(t, {{.ForwardedParamsFormat}}) 4 | } 5 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/assert/assertion_forward.go.tmpl: -------------------------------------------------------------------------------- 1 | {{.CommentWithoutT "a"}} 2 | func (a *Assertions) {{.DocInfo.Name}}({{.Params}}) bool { 3 | return {{.DocInfo.Name}}(a.t, {{.ForwardedParams}}) 4 | } 5 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/assert/doc.go: -------------------------------------------------------------------------------- 1 | // Package assert provides a set of comprehensive testing tools for use with the normal Go testing system. 2 | // 3 | // Example Usage 4 | // 5 | // The following is a complete example using assert in a standard test function: 6 | // import ( 7 | // "testing" 8 | // "github.com/stretchr/testify/assert" 9 | // ) 10 | // 11 | // func TestSomething(t *testing.T) { 12 | // 13 | // var a string = "Hello" 14 | // var b string = "Hello" 15 | // 16 | // assert.Equal(t, a, b, "The two words should be the same.") 17 | // 18 | // } 19 | // 20 | // if you assert many times, use the format below: 21 | // 22 | // import ( 23 | // "testing" 24 | // "github.com/stretchr/testify/assert" 25 | // ) 26 | // 27 | // func TestSomething(t *testing.T) { 28 | // assert := assert.New(t) 29 | // 30 | // var a string = "Hello" 31 | // var b string = "Hello" 32 | // 33 | // assert.Equal(a, b, "The two words should be the same.") 34 | // } 35 | // 36 | // Assertions 37 | // 38 | // Assertions allow you to easily write test code, and are global funcs in the `assert` package. 39 | // All assertion functions take, as the first argument, the `*testing.T` object provided by the 40 | // testing framework. This allows the assertion funcs to write the failings and other details to 41 | // the correct place. 42 | // 43 | // Every assertion function also takes an optional string message as the final argument, 44 | // allowing custom error messages to be appended to the message the assertion method outputs. 45 | package assert 46 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/assert/errors.go: -------------------------------------------------------------------------------- 1 | package assert 2 | 3 | import ( 4 | "errors" 5 | ) 6 | 7 | // AnError is an error instance useful for testing. If the code does not care 8 | // about error specifics, and only needs to return the error for example, this 9 | // error should be used to make the test code more readable. 10 | var AnError = errors.New("assert.AnError general error for testing") 11 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/assert/forward_assertions.go: -------------------------------------------------------------------------------- 1 | package assert 2 | 3 | // Assertions provides assertion methods around the 4 | // TestingT interface. 5 | type Assertions struct { 6 | t TestingT 7 | } 8 | 9 | // New makes a new Assertions object for the specified TestingT. 10 | func New(t TestingT) *Assertions { 11 | return &Assertions{ 12 | t: t, 13 | } 14 | } 15 | 16 | //go:generate go run ../_codegen/main.go -output-package=assert -template=assertion_forward.go.tmpl -include-format-funcs 17 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/assert/http_assertions.go: -------------------------------------------------------------------------------- 1 | package assert 2 | 3 | import ( 4 | "fmt" 5 | "net/http" 6 | "net/http/httptest" 7 | "net/url" 8 | "strings" 9 | ) 10 | 11 | // httpCode is a helper that returns HTTP code of the response. It returns -1 and 12 | // an error if building a new request fails. 13 | func httpCode(handler http.HandlerFunc, method, url string, values url.Values) (int, error) { 14 | w := httptest.NewRecorder() 15 | req, err := http.NewRequest(method, url+"?"+values.Encode(), nil) 16 | if err != nil { 17 | return -1, err 18 | } 19 | handler(w, req) 20 | return w.Code, nil 21 | } 22 | 23 | // HTTPSuccess asserts that a specified handler returns a success status code. 24 | // 25 | // assert.HTTPSuccess(t, myHandler, "POST", "http://www.google.com", nil) 26 | // 27 | // Returns whether the assertion was successful (true) or not (false). 28 | func HTTPSuccess(t TestingT, handler http.HandlerFunc, method, url string, values url.Values) bool { 29 | code, err := httpCode(handler, method, url, values) 30 | if err != nil { 31 | Fail(t, fmt.Sprintf("Failed to build test request, got error: %s", err)) 32 | return false 33 | } 34 | 35 | isSuccessCode := code >= http.StatusOK && code <= http.StatusPartialContent 36 | if !isSuccessCode { 37 | Fail(t, fmt.Sprintf("Expected HTTP success status code for %q but received %d", url+"?"+values.Encode(), code)) 38 | } 39 | 40 | return isSuccessCode 41 | } 42 | 43 | // HTTPRedirect asserts that a specified handler returns a redirect status code. 44 | // 45 | // assert.HTTPRedirect(t, myHandler, "GET", "/a/b/c", url.Values{"a": []string{"b", "c"}} 46 | // 47 | // Returns whether the assertion was successful (true) or not (false). 48 | func HTTPRedirect(t TestingT, handler http.HandlerFunc, method, url string, values url.Values) bool { 49 | code, err := httpCode(handler, method, url, values) 50 | if err != nil { 51 | Fail(t, fmt.Sprintf("Failed to build test request, got error: %s", err)) 52 | return false 53 | } 54 | 55 | isRedirectCode := code >= http.StatusMultipleChoices && code <= http.StatusTemporaryRedirect 56 | if !isRedirectCode { 57 | Fail(t, fmt.Sprintf("Expected HTTP redirect status code for %q but received %d", url+"?"+values.Encode(), code)) 58 | } 59 | 60 | return isRedirectCode 61 | } 62 | 63 | // HTTPError asserts that a specified handler returns an error status code. 64 | // 65 | // assert.HTTPError(t, myHandler, "POST", "/a/b/c", url.Values{"a": []string{"b", "c"}} 66 | // 67 | // Returns whether the assertion was successful (true) or not (false). 68 | func HTTPError(t TestingT, handler http.HandlerFunc, method, url string, values url.Values) bool { 69 | code, err := httpCode(handler, method, url, values) 70 | if err != nil { 71 | Fail(t, fmt.Sprintf("Failed to build test request, got error: %s", err)) 72 | return false 73 | } 74 | 75 | isErrorCode := code >= http.StatusBadRequest 76 | if !isErrorCode { 77 | Fail(t, fmt.Sprintf("Expected HTTP error status code for %q but received %d", url+"?"+values.Encode(), code)) 78 | } 79 | 80 | return isErrorCode 81 | } 82 | 83 | // HTTPBody is a helper that returns HTTP body of the response. It returns 84 | // empty string if building a new request fails. 85 | func HTTPBody(handler http.HandlerFunc, method, url string, values url.Values) string { 86 | w := httptest.NewRecorder() 87 | req, err := http.NewRequest(method, url+"?"+values.Encode(), nil) 88 | if err != nil { 89 | return "" 90 | } 91 | handler(w, req) 92 | return w.Body.String() 93 | } 94 | 95 | // HTTPBodyContains asserts that a specified handler returns a 96 | // body that contains a string. 97 | // 98 | // assert.HTTPBodyContains(t, myHandler, "www.google.com", nil, "I'm Feeling Lucky") 99 | // 100 | // Returns whether the assertion was successful (true) or not (false). 101 | func HTTPBodyContains(t TestingT, handler http.HandlerFunc, method, url string, values url.Values, str interface{}) bool { 102 | body := HTTPBody(handler, method, url, values) 103 | 104 | contains := strings.Contains(body, fmt.Sprint(str)) 105 | if !contains { 106 | Fail(t, fmt.Sprintf("Expected response body for \"%s\" to contain \"%s\" but found \"%s\"", url+"?"+values.Encode(), str, body)) 107 | } 108 | 109 | return contains 110 | } 111 | 112 | // HTTPBodyNotContains asserts that a specified handler returns a 113 | // body that does not contain a string. 114 | // 115 | // assert.HTTPBodyNotContains(t, myHandler, "www.google.com", nil, "I'm Feeling Lucky") 116 | // 117 | // Returns whether the assertion was successful (true) or not (false). 118 | func HTTPBodyNotContains(t TestingT, handler http.HandlerFunc, method, url string, values url.Values, str interface{}) bool { 119 | body := HTTPBody(handler, method, url, values) 120 | 121 | contains := strings.Contains(body, fmt.Sprint(str)) 122 | if contains { 123 | Fail(t, fmt.Sprintf("Expected response body for \"%s\" to NOT contain \"%s\" but found \"%s\"", url+"?"+values.Encode(), str, body)) 124 | } 125 | 126 | return !contains 127 | } 128 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/assert/http_assertions_test.go: -------------------------------------------------------------------------------- 1 | package assert 2 | 3 | import ( 4 | "fmt" 5 | "net/http" 6 | "net/url" 7 | "testing" 8 | ) 9 | 10 | func httpOK(w http.ResponseWriter, r *http.Request) { 11 | w.WriteHeader(http.StatusOK) 12 | } 13 | 14 | func httpRedirect(w http.ResponseWriter, r *http.Request) { 15 | w.WriteHeader(http.StatusTemporaryRedirect) 16 | } 17 | 18 | func httpError(w http.ResponseWriter, r *http.Request) { 19 | w.WriteHeader(http.StatusInternalServerError) 20 | } 21 | 22 | func TestHTTPSuccess(t *testing.T) { 23 | assert := New(t) 24 | 25 | mockT1 := new(testing.T) 26 | assert.Equal(HTTPSuccess(mockT1, httpOK, "GET", "/", nil), true) 27 | assert.False(mockT1.Failed()) 28 | 29 | mockT2 := new(testing.T) 30 | assert.Equal(HTTPSuccess(mockT2, httpRedirect, "GET", "/", nil), false) 31 | assert.True(mockT2.Failed()) 32 | 33 | mockT3 := new(testing.T) 34 | assert.Equal(HTTPSuccess(mockT3, httpError, "GET", "/", nil), false) 35 | assert.True(mockT3.Failed()) 36 | } 37 | 38 | func TestHTTPRedirect(t *testing.T) { 39 | assert := New(t) 40 | 41 | mockT1 := new(testing.T) 42 | assert.Equal(HTTPRedirect(mockT1, httpOK, "GET", "/", nil), false) 43 | assert.True(mockT1.Failed()) 44 | 45 | mockT2 := new(testing.T) 46 | assert.Equal(HTTPRedirect(mockT2, httpRedirect, "GET", "/", nil), true) 47 | assert.False(mockT2.Failed()) 48 | 49 | mockT3 := new(testing.T) 50 | assert.Equal(HTTPRedirect(mockT3, httpError, "GET", "/", nil), false) 51 | assert.True(mockT3.Failed()) 52 | } 53 | 54 | func TestHTTPError(t *testing.T) { 55 | assert := New(t) 56 | 57 | mockT1 := new(testing.T) 58 | assert.Equal(HTTPError(mockT1, httpOK, "GET", "/", nil), false) 59 | assert.True(mockT1.Failed()) 60 | 61 | mockT2 := new(testing.T) 62 | assert.Equal(HTTPError(mockT2, httpRedirect, "GET", "/", nil), false) 63 | assert.True(mockT2.Failed()) 64 | 65 | mockT3 := new(testing.T) 66 | assert.Equal(HTTPError(mockT3, httpError, "GET", "/", nil), true) 67 | assert.False(mockT3.Failed()) 68 | } 69 | 70 | func TestHTTPStatusesWrapper(t *testing.T) { 71 | assert := New(t) 72 | mockAssert := New(new(testing.T)) 73 | 74 | assert.Equal(mockAssert.HTTPSuccess(httpOK, "GET", "/", nil), true) 75 | assert.Equal(mockAssert.HTTPSuccess(httpRedirect, "GET", "/", nil), false) 76 | assert.Equal(mockAssert.HTTPSuccess(httpError, "GET", "/", nil), false) 77 | 78 | assert.Equal(mockAssert.HTTPRedirect(httpOK, "GET", "/", nil), false) 79 | assert.Equal(mockAssert.HTTPRedirect(httpRedirect, "GET", "/", nil), true) 80 | assert.Equal(mockAssert.HTTPRedirect(httpError, "GET", "/", nil), false) 81 | 82 | assert.Equal(mockAssert.HTTPError(httpOK, "GET", "/", nil), false) 83 | assert.Equal(mockAssert.HTTPError(httpRedirect, "GET", "/", nil), false) 84 | assert.Equal(mockAssert.HTTPError(httpError, "GET", "/", nil), true) 85 | } 86 | 87 | func httpHelloName(w http.ResponseWriter, r *http.Request) { 88 | name := r.FormValue("name") 89 | w.Write([]byte(fmt.Sprintf("Hello, %s!", name))) 90 | } 91 | 92 | func TestHttpBody(t *testing.T) { 93 | assert := New(t) 94 | mockT := new(testing.T) 95 | 96 | assert.True(HTTPBodyContains(mockT, httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "Hello, World!")) 97 | assert.True(HTTPBodyContains(mockT, httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "World")) 98 | assert.False(HTTPBodyContains(mockT, httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "world")) 99 | 100 | assert.False(HTTPBodyNotContains(mockT, httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "Hello, World!")) 101 | assert.False(HTTPBodyNotContains(mockT, httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "World")) 102 | assert.True(HTTPBodyNotContains(mockT, httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "world")) 103 | } 104 | 105 | func TestHttpBodyWrappers(t *testing.T) { 106 | assert := New(t) 107 | mockAssert := New(new(testing.T)) 108 | 109 | assert.True(mockAssert.HTTPBodyContains(httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "Hello, World!")) 110 | assert.True(mockAssert.HTTPBodyContains(httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "World")) 111 | assert.False(mockAssert.HTTPBodyContains(httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "world")) 112 | 113 | assert.False(mockAssert.HTTPBodyNotContains(httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "Hello, World!")) 114 | assert.False(mockAssert.HTTPBodyNotContains(httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "World")) 115 | assert.True(mockAssert.HTTPBodyNotContains(httpHelloName, "GET", "/", url.Values{"name": []string{"World"}}, "world")) 116 | 117 | } 118 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/require/doc.go: -------------------------------------------------------------------------------- 1 | // Package require implements the same assertions as the `assert` package but 2 | // stops test execution when a test fails. 3 | // 4 | // Example Usage 5 | // 6 | // The following is a complete example using require in a standard test function: 7 | // import ( 8 | // "testing" 9 | // "github.com/stretchr/testify/require" 10 | // ) 11 | // 12 | // func TestSomething(t *testing.T) { 13 | // 14 | // var a string = "Hello" 15 | // var b string = "Hello" 16 | // 17 | // require.Equal(t, a, b, "The two words should be the same.") 18 | // 19 | // } 20 | // 21 | // Assertions 22 | // 23 | // The `require` package have same global functions as in the `assert` package, 24 | // but instead of returning a boolean result they call `t.FailNow()`. 25 | // 26 | // Every assertion function also takes an optional string message as the final argument, 27 | // allowing custom error messages to be appended to the message the assertion method outputs. 28 | package require 29 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/require/forward_requirements.go: -------------------------------------------------------------------------------- 1 | package require 2 | 3 | // Assertions provides assertion methods around the 4 | // TestingT interface. 5 | type Assertions struct { 6 | t TestingT 7 | } 8 | 9 | // New makes a new Assertions object for the specified TestingT. 10 | func New(t TestingT) *Assertions { 11 | return &Assertions{ 12 | t: t, 13 | } 14 | } 15 | 16 | //go:generate go run ../_codegen/main.go -output-package=require -template=require_forward.go.tmpl -include-format-funcs 17 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/require/forward_requirements_test.go: -------------------------------------------------------------------------------- 1 | package require 2 | 3 | import ( 4 | "errors" 5 | "testing" 6 | "time" 7 | ) 8 | 9 | func TestImplementsWrapper(t *testing.T) { 10 | require := New(t) 11 | 12 | require.Implements((*AssertionTesterInterface)(nil), new(AssertionTesterConformingObject)) 13 | 14 | mockT := new(MockT) 15 | mockRequire := New(mockT) 16 | mockRequire.Implements((*AssertionTesterInterface)(nil), new(AssertionTesterNonConformingObject)) 17 | if !mockT.Failed { 18 | t.Error("Check should fail") 19 | } 20 | } 21 | 22 | func TestIsTypeWrapper(t *testing.T) { 23 | require := New(t) 24 | require.IsType(new(AssertionTesterConformingObject), new(AssertionTesterConformingObject)) 25 | 26 | mockT := new(MockT) 27 | mockRequire := New(mockT) 28 | mockRequire.IsType(new(AssertionTesterConformingObject), new(AssertionTesterNonConformingObject)) 29 | if !mockT.Failed { 30 | t.Error("Check should fail") 31 | } 32 | } 33 | 34 | func TestEqualWrapper(t *testing.T) { 35 | require := New(t) 36 | require.Equal(1, 1) 37 | 38 | mockT := new(MockT) 39 | mockRequire := New(mockT) 40 | mockRequire.Equal(1, 2) 41 | if !mockT.Failed { 42 | t.Error("Check should fail") 43 | } 44 | } 45 | 46 | func TestNotEqualWrapper(t *testing.T) { 47 | require := New(t) 48 | require.NotEqual(1, 2) 49 | 50 | mockT := new(MockT) 51 | mockRequire := New(mockT) 52 | mockRequire.NotEqual(2, 2) 53 | if !mockT.Failed { 54 | t.Error("Check should fail") 55 | } 56 | } 57 | 58 | func TestExactlyWrapper(t *testing.T) { 59 | require := New(t) 60 | 61 | a := float32(1) 62 | b := float32(1) 63 | c := float64(1) 64 | 65 | require.Exactly(a, b) 66 | 67 | mockT := new(MockT) 68 | mockRequire := New(mockT) 69 | mockRequire.Exactly(a, c) 70 | if !mockT.Failed { 71 | t.Error("Check should fail") 72 | } 73 | } 74 | 75 | func TestNotNilWrapper(t *testing.T) { 76 | require := New(t) 77 | require.NotNil(t, new(AssertionTesterConformingObject)) 78 | 79 | mockT := new(MockT) 80 | mockRequire := New(mockT) 81 | mockRequire.NotNil(nil) 82 | if !mockT.Failed { 83 | t.Error("Check should fail") 84 | } 85 | } 86 | 87 | func TestNilWrapper(t *testing.T) { 88 | require := New(t) 89 | require.Nil(nil) 90 | 91 | mockT := new(MockT) 92 | mockRequire := New(mockT) 93 | mockRequire.Nil(new(AssertionTesterConformingObject)) 94 | if !mockT.Failed { 95 | t.Error("Check should fail") 96 | } 97 | } 98 | 99 | func TestTrueWrapper(t *testing.T) { 100 | require := New(t) 101 | require.True(true) 102 | 103 | mockT := new(MockT) 104 | mockRequire := New(mockT) 105 | mockRequire.True(false) 106 | if !mockT.Failed { 107 | t.Error("Check should fail") 108 | } 109 | } 110 | 111 | func TestFalseWrapper(t *testing.T) { 112 | require := New(t) 113 | require.False(false) 114 | 115 | mockT := new(MockT) 116 | mockRequire := New(mockT) 117 | mockRequire.False(true) 118 | if !mockT.Failed { 119 | t.Error("Check should fail") 120 | } 121 | } 122 | 123 | func TestContainsWrapper(t *testing.T) { 124 | require := New(t) 125 | require.Contains("Hello World", "Hello") 126 | 127 | mockT := new(MockT) 128 | mockRequire := New(mockT) 129 | mockRequire.Contains("Hello World", "Salut") 130 | if !mockT.Failed { 131 | t.Error("Check should fail") 132 | } 133 | } 134 | 135 | func TestNotContainsWrapper(t *testing.T) { 136 | require := New(t) 137 | require.NotContains("Hello World", "Hello!") 138 | 139 | mockT := new(MockT) 140 | mockRequire := New(mockT) 141 | mockRequire.NotContains("Hello World", "Hello") 142 | if !mockT.Failed { 143 | t.Error("Check should fail") 144 | } 145 | } 146 | 147 | func TestPanicsWrapper(t *testing.T) { 148 | require := New(t) 149 | require.Panics(func() { 150 | panic("Panic!") 151 | }) 152 | 153 | mockT := new(MockT) 154 | mockRequire := New(mockT) 155 | mockRequire.Panics(func() {}) 156 | if !mockT.Failed { 157 | t.Error("Check should fail") 158 | } 159 | } 160 | 161 | func TestNotPanicsWrapper(t *testing.T) { 162 | require := New(t) 163 | require.NotPanics(func() {}) 164 | 165 | mockT := new(MockT) 166 | mockRequire := New(mockT) 167 | mockRequire.NotPanics(func() { 168 | panic("Panic!") 169 | }) 170 | if !mockT.Failed { 171 | t.Error("Check should fail") 172 | } 173 | } 174 | 175 | func TestNoErrorWrapper(t *testing.T) { 176 | require := New(t) 177 | require.NoError(nil) 178 | 179 | mockT := new(MockT) 180 | mockRequire := New(mockT) 181 | mockRequire.NoError(errors.New("some error")) 182 | if !mockT.Failed { 183 | t.Error("Check should fail") 184 | } 185 | } 186 | 187 | func TestErrorWrapper(t *testing.T) { 188 | require := New(t) 189 | require.Error(errors.New("some error")) 190 | 191 | mockT := new(MockT) 192 | mockRequire := New(mockT) 193 | mockRequire.Error(nil) 194 | if !mockT.Failed { 195 | t.Error("Check should fail") 196 | } 197 | } 198 | 199 | func TestEqualErrorWrapper(t *testing.T) { 200 | require := New(t) 201 | require.EqualError(errors.New("some error"), "some error") 202 | 203 | mockT := new(MockT) 204 | mockRequire := New(mockT) 205 | mockRequire.EqualError(errors.New("some error"), "Not some error") 206 | if !mockT.Failed { 207 | t.Error("Check should fail") 208 | } 209 | } 210 | 211 | func TestEmptyWrapper(t *testing.T) { 212 | require := New(t) 213 | require.Empty("") 214 | 215 | mockT := new(MockT) 216 | mockRequire := New(mockT) 217 | mockRequire.Empty("x") 218 | if !mockT.Failed { 219 | t.Error("Check should fail") 220 | } 221 | } 222 | 223 | func TestNotEmptyWrapper(t *testing.T) { 224 | require := New(t) 225 | require.NotEmpty("x") 226 | 227 | mockT := new(MockT) 228 | mockRequire := New(mockT) 229 | mockRequire.NotEmpty("") 230 | if !mockT.Failed { 231 | t.Error("Check should fail") 232 | } 233 | } 234 | 235 | func TestWithinDurationWrapper(t *testing.T) { 236 | require := New(t) 237 | a := time.Now() 238 | b := a.Add(10 * time.Second) 239 | 240 | require.WithinDuration(a, b, 15*time.Second) 241 | 242 | mockT := new(MockT) 243 | mockRequire := New(mockT) 244 | mockRequire.WithinDuration(a, b, 5*time.Second) 245 | if !mockT.Failed { 246 | t.Error("Check should fail") 247 | } 248 | } 249 | 250 | func TestInDeltaWrapper(t *testing.T) { 251 | require := New(t) 252 | require.InDelta(1.001, 1, 0.01) 253 | 254 | mockT := new(MockT) 255 | mockRequire := New(mockT) 256 | mockRequire.InDelta(1, 2, 0.5) 257 | if !mockT.Failed { 258 | t.Error("Check should fail") 259 | } 260 | } 261 | 262 | func TestZeroWrapper(t *testing.T) { 263 | require := New(t) 264 | require.Zero(0) 265 | 266 | mockT := new(MockT) 267 | mockRequire := New(mockT) 268 | mockRequire.Zero(1) 269 | if !mockT.Failed { 270 | t.Error("Check should fail") 271 | } 272 | } 273 | 274 | func TestNotZeroWrapper(t *testing.T) { 275 | require := New(t) 276 | require.NotZero(1) 277 | 278 | mockT := new(MockT) 279 | mockRequire := New(mockT) 280 | mockRequire.NotZero(0) 281 | if !mockT.Failed { 282 | t.Error("Check should fail") 283 | } 284 | } 285 | 286 | func TestJSONEqWrapper_EqualSONString(t *testing.T) { 287 | mockT := new(MockT) 288 | mockRequire := New(mockT) 289 | 290 | mockRequire.JSONEq(`{"hello": "world", "foo": "bar"}`, `{"hello": "world", "foo": "bar"}`) 291 | if mockT.Failed { 292 | t.Error("Check should pass") 293 | } 294 | } 295 | 296 | func TestJSONEqWrapper_EquivalentButNotEqual(t *testing.T) { 297 | mockT := new(MockT) 298 | mockRequire := New(mockT) 299 | 300 | mockRequire.JSONEq(`{"hello": "world", "foo": "bar"}`, `{"foo": "bar", "hello": "world"}`) 301 | if mockT.Failed { 302 | t.Error("Check should pass") 303 | } 304 | } 305 | 306 | func TestJSONEqWrapper_HashOfArraysAndHashes(t *testing.T) { 307 | mockT := new(MockT) 308 | mockRequire := New(mockT) 309 | 310 | mockRequire.JSONEq("{\r\n\t\"numeric\": 1.5,\r\n\t\"array\": [{\"foo\": \"bar\"}, 1, \"string\", [\"nested\", \"array\", 5.5]],\r\n\t\"hash\": {\"nested\": \"hash\", \"nested_slice\": [\"this\", \"is\", \"nested\"]},\r\n\t\"string\": \"foo\"\r\n}", 311 | "{\r\n\t\"numeric\": 1.5,\r\n\t\"hash\": {\"nested\": \"hash\", \"nested_slice\": [\"this\", \"is\", \"nested\"]},\r\n\t\"string\": \"foo\",\r\n\t\"array\": [{\"foo\": \"bar\"}, 1, \"string\", [\"nested\", \"array\", 5.5]]\r\n}") 312 | if mockT.Failed { 313 | t.Error("Check should pass") 314 | } 315 | } 316 | 317 | func TestJSONEqWrapper_Array(t *testing.T) { 318 | mockT := new(MockT) 319 | mockRequire := New(mockT) 320 | 321 | mockRequire.JSONEq(`["foo", {"hello": "world", "nested": "hash"}]`, `["foo", {"nested": "hash", "hello": "world"}]`) 322 | if mockT.Failed { 323 | t.Error("Check should pass") 324 | } 325 | } 326 | 327 | func TestJSONEqWrapper_HashAndArrayNotEquivalent(t *testing.T) { 328 | mockT := new(MockT) 329 | mockRequire := New(mockT) 330 | 331 | mockRequire.JSONEq(`["foo", {"hello": "world", "nested": "hash"}]`, `{"foo": "bar", {"nested": "hash", "hello": "world"}}`) 332 | if !mockT.Failed { 333 | t.Error("Check should fail") 334 | } 335 | } 336 | 337 | func TestJSONEqWrapper_HashesNotEquivalent(t *testing.T) { 338 | mockT := new(MockT) 339 | mockRequire := New(mockT) 340 | 341 | mockRequire.JSONEq(`{"foo": "bar"}`, `{"foo": "bar", "hello": "world"}`) 342 | if !mockT.Failed { 343 | t.Error("Check should fail") 344 | } 345 | } 346 | 347 | func TestJSONEqWrapper_ActualIsNotJSON(t *testing.T) { 348 | mockT := new(MockT) 349 | mockRequire := New(mockT) 350 | 351 | mockRequire.JSONEq(`{"foo": "bar"}`, "Not JSON") 352 | if !mockT.Failed { 353 | t.Error("Check should fail") 354 | } 355 | } 356 | 357 | func TestJSONEqWrapper_ExpectedIsNotJSON(t *testing.T) { 358 | mockT := new(MockT) 359 | mockRequire := New(mockT) 360 | 361 | mockRequire.JSONEq("Not JSON", `{"foo": "bar", "hello": "world"}`) 362 | if !mockT.Failed { 363 | t.Error("Check should fail") 364 | } 365 | } 366 | 367 | func TestJSONEqWrapper_ExpectedAndActualNotJSON(t *testing.T) { 368 | mockT := new(MockT) 369 | mockRequire := New(mockT) 370 | 371 | mockRequire.JSONEq("Not JSON", "Not JSON") 372 | if !mockT.Failed { 373 | t.Error("Check should fail") 374 | } 375 | } 376 | 377 | func TestJSONEqWrapper_ArraysOfDifferentOrder(t *testing.T) { 378 | mockT := new(MockT) 379 | mockRequire := New(mockT) 380 | 381 | mockRequire.JSONEq(`["foo", {"hello": "world", "nested": "hash"}]`, `[{ "hello": "world", "nested": "hash"}, "foo"]`) 382 | if !mockT.Failed { 383 | t.Error("Check should fail") 384 | } 385 | } 386 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/require/require.go.tmpl: -------------------------------------------------------------------------------- 1 | {{.Comment}} 2 | func {{.DocInfo.Name}}(t TestingT, {{.Params}}) { 3 | if !assert.{{.DocInfo.Name}}(t, {{.ForwardedParams}}) { 4 | t.FailNow() 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/require/require_forward.go.tmpl: -------------------------------------------------------------------------------- 1 | {{.CommentWithoutT "a"}} 2 | func (a *Assertions) {{.DocInfo.Name}}({{.Params}}) { 3 | {{.DocInfo.Name}}(a.t, {{.ForwardedParams}}) 4 | } 5 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/require/requirements.go: -------------------------------------------------------------------------------- 1 | package require 2 | 3 | // TestingT is an interface wrapper around *testing.T 4 | type TestingT interface { 5 | Errorf(format string, args ...interface{}) 6 | FailNow() 7 | } 8 | 9 | //go:generate go run ../_codegen/main.go -output-package=require -template=require.go.tmpl -include-format-funcs 10 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/require/requirements_test.go: -------------------------------------------------------------------------------- 1 | package require 2 | 3 | import ( 4 | "errors" 5 | "testing" 6 | "time" 7 | ) 8 | 9 | // AssertionTesterInterface defines an interface to be used for testing assertion methods 10 | type AssertionTesterInterface interface { 11 | TestMethod() 12 | } 13 | 14 | // AssertionTesterConformingObject is an object that conforms to the AssertionTesterInterface interface 15 | type AssertionTesterConformingObject struct { 16 | } 17 | 18 | func (a *AssertionTesterConformingObject) TestMethod() { 19 | } 20 | 21 | // AssertionTesterNonConformingObject is an object that does not conform to the AssertionTesterInterface interface 22 | type AssertionTesterNonConformingObject struct { 23 | } 24 | 25 | type MockT struct { 26 | Failed bool 27 | } 28 | 29 | func (t *MockT) FailNow() { 30 | t.Failed = true 31 | } 32 | 33 | func (t *MockT) Errorf(format string, args ...interface{}) { 34 | _, _ = format, args 35 | } 36 | 37 | func TestImplements(t *testing.T) { 38 | 39 | Implements(t, (*AssertionTesterInterface)(nil), new(AssertionTesterConformingObject)) 40 | 41 | mockT := new(MockT) 42 | Implements(mockT, (*AssertionTesterInterface)(nil), new(AssertionTesterNonConformingObject)) 43 | if !mockT.Failed { 44 | t.Error("Check should fail") 45 | } 46 | } 47 | 48 | func TestIsType(t *testing.T) { 49 | 50 | IsType(t, new(AssertionTesterConformingObject), new(AssertionTesterConformingObject)) 51 | 52 | mockT := new(MockT) 53 | IsType(mockT, new(AssertionTesterConformingObject), new(AssertionTesterNonConformingObject)) 54 | if !mockT.Failed { 55 | t.Error("Check should fail") 56 | } 57 | } 58 | 59 | func TestEqual(t *testing.T) { 60 | 61 | Equal(t, 1, 1) 62 | 63 | mockT := new(MockT) 64 | Equal(mockT, 1, 2) 65 | if !mockT.Failed { 66 | t.Error("Check should fail") 67 | } 68 | 69 | } 70 | 71 | func TestNotEqual(t *testing.T) { 72 | 73 | NotEqual(t, 1, 2) 74 | mockT := new(MockT) 75 | NotEqual(mockT, 2, 2) 76 | if !mockT.Failed { 77 | t.Error("Check should fail") 78 | } 79 | } 80 | 81 | func TestExactly(t *testing.T) { 82 | 83 | a := float32(1) 84 | b := float32(1) 85 | c := float64(1) 86 | 87 | Exactly(t, a, b) 88 | 89 | mockT := new(MockT) 90 | Exactly(mockT, a, c) 91 | if !mockT.Failed { 92 | t.Error("Check should fail") 93 | } 94 | } 95 | 96 | func TestNotNil(t *testing.T) { 97 | 98 | NotNil(t, new(AssertionTesterConformingObject)) 99 | 100 | mockT := new(MockT) 101 | NotNil(mockT, nil) 102 | if !mockT.Failed { 103 | t.Error("Check should fail") 104 | } 105 | } 106 | 107 | func TestNil(t *testing.T) { 108 | 109 | Nil(t, nil) 110 | 111 | mockT := new(MockT) 112 | Nil(mockT, new(AssertionTesterConformingObject)) 113 | if !mockT.Failed { 114 | t.Error("Check should fail") 115 | } 116 | } 117 | 118 | func TestTrue(t *testing.T) { 119 | 120 | True(t, true) 121 | 122 | mockT := new(MockT) 123 | True(mockT, false) 124 | if !mockT.Failed { 125 | t.Error("Check should fail") 126 | } 127 | } 128 | 129 | func TestFalse(t *testing.T) { 130 | 131 | False(t, false) 132 | 133 | mockT := new(MockT) 134 | False(mockT, true) 135 | if !mockT.Failed { 136 | t.Error("Check should fail") 137 | } 138 | } 139 | 140 | func TestContains(t *testing.T) { 141 | 142 | Contains(t, "Hello World", "Hello") 143 | 144 | mockT := new(MockT) 145 | Contains(mockT, "Hello World", "Salut") 146 | if !mockT.Failed { 147 | t.Error("Check should fail") 148 | } 149 | } 150 | 151 | func TestNotContains(t *testing.T) { 152 | 153 | NotContains(t, "Hello World", "Hello!") 154 | 155 | mockT := new(MockT) 156 | NotContains(mockT, "Hello World", "Hello") 157 | if !mockT.Failed { 158 | t.Error("Check should fail") 159 | } 160 | } 161 | 162 | func TestPanics(t *testing.T) { 163 | 164 | Panics(t, func() { 165 | panic("Panic!") 166 | }) 167 | 168 | mockT := new(MockT) 169 | Panics(mockT, func() {}) 170 | if !mockT.Failed { 171 | t.Error("Check should fail") 172 | } 173 | } 174 | 175 | func TestNotPanics(t *testing.T) { 176 | 177 | NotPanics(t, func() {}) 178 | 179 | mockT := new(MockT) 180 | NotPanics(mockT, func() { 181 | panic("Panic!") 182 | }) 183 | if !mockT.Failed { 184 | t.Error("Check should fail") 185 | } 186 | } 187 | 188 | func TestNoError(t *testing.T) { 189 | 190 | NoError(t, nil) 191 | 192 | mockT := new(MockT) 193 | NoError(mockT, errors.New("some error")) 194 | if !mockT.Failed { 195 | t.Error("Check should fail") 196 | } 197 | } 198 | 199 | func TestError(t *testing.T) { 200 | 201 | Error(t, errors.New("some error")) 202 | 203 | mockT := new(MockT) 204 | Error(mockT, nil) 205 | if !mockT.Failed { 206 | t.Error("Check should fail") 207 | } 208 | } 209 | 210 | func TestEqualError(t *testing.T) { 211 | 212 | EqualError(t, errors.New("some error"), "some error") 213 | 214 | mockT := new(MockT) 215 | EqualError(mockT, errors.New("some error"), "Not some error") 216 | if !mockT.Failed { 217 | t.Error("Check should fail") 218 | } 219 | } 220 | 221 | func TestEmpty(t *testing.T) { 222 | 223 | Empty(t, "") 224 | 225 | mockT := new(MockT) 226 | Empty(mockT, "x") 227 | if !mockT.Failed { 228 | t.Error("Check should fail") 229 | } 230 | } 231 | 232 | func TestNotEmpty(t *testing.T) { 233 | 234 | NotEmpty(t, "x") 235 | 236 | mockT := new(MockT) 237 | NotEmpty(mockT, "") 238 | if !mockT.Failed { 239 | t.Error("Check should fail") 240 | } 241 | } 242 | 243 | func TestWithinDuration(t *testing.T) { 244 | 245 | a := time.Now() 246 | b := a.Add(10 * time.Second) 247 | 248 | WithinDuration(t, a, b, 15*time.Second) 249 | 250 | mockT := new(MockT) 251 | WithinDuration(mockT, a, b, 5*time.Second) 252 | if !mockT.Failed { 253 | t.Error("Check should fail") 254 | } 255 | } 256 | 257 | func TestInDelta(t *testing.T) { 258 | 259 | InDelta(t, 1.001, 1, 0.01) 260 | 261 | mockT := new(MockT) 262 | InDelta(mockT, 1, 2, 0.5) 263 | if !mockT.Failed { 264 | t.Error("Check should fail") 265 | } 266 | } 267 | 268 | func TestZero(t *testing.T) { 269 | 270 | Zero(t, "") 271 | 272 | mockT := new(MockT) 273 | Zero(mockT, "x") 274 | if !mockT.Failed { 275 | t.Error("Check should fail") 276 | } 277 | } 278 | 279 | func TestNotZero(t *testing.T) { 280 | 281 | NotZero(t, "x") 282 | 283 | mockT := new(MockT) 284 | NotZero(mockT, "") 285 | if !mockT.Failed { 286 | t.Error("Check should fail") 287 | } 288 | } 289 | 290 | func TestJSONEq_EqualSONString(t *testing.T) { 291 | mockT := new(MockT) 292 | JSONEq(mockT, `{"hello": "world", "foo": "bar"}`, `{"hello": "world", "foo": "bar"}`) 293 | if mockT.Failed { 294 | t.Error("Check should pass") 295 | } 296 | } 297 | 298 | func TestJSONEq_EquivalentButNotEqual(t *testing.T) { 299 | mockT := new(MockT) 300 | JSONEq(mockT, `{"hello": "world", "foo": "bar"}`, `{"foo": "bar", "hello": "world"}`) 301 | if mockT.Failed { 302 | t.Error("Check should pass") 303 | } 304 | } 305 | 306 | func TestJSONEq_HashOfArraysAndHashes(t *testing.T) { 307 | mockT := new(MockT) 308 | JSONEq(mockT, "{\r\n\t\"numeric\": 1.5,\r\n\t\"array\": [{\"foo\": \"bar\"}, 1, \"string\", [\"nested\", \"array\", 5.5]],\r\n\t\"hash\": {\"nested\": \"hash\", \"nested_slice\": [\"this\", \"is\", \"nested\"]},\r\n\t\"string\": \"foo\"\r\n}", 309 | "{\r\n\t\"numeric\": 1.5,\r\n\t\"hash\": {\"nested\": \"hash\", \"nested_slice\": [\"this\", \"is\", \"nested\"]},\r\n\t\"string\": \"foo\",\r\n\t\"array\": [{\"foo\": \"bar\"}, 1, \"string\", [\"nested\", \"array\", 5.5]]\r\n}") 310 | if mockT.Failed { 311 | t.Error("Check should pass") 312 | } 313 | } 314 | 315 | func TestJSONEq_Array(t *testing.T) { 316 | mockT := new(MockT) 317 | JSONEq(mockT, `["foo", {"hello": "world", "nested": "hash"}]`, `["foo", {"nested": "hash", "hello": "world"}]`) 318 | if mockT.Failed { 319 | t.Error("Check should pass") 320 | } 321 | } 322 | 323 | func TestJSONEq_HashAndArrayNotEquivalent(t *testing.T) { 324 | mockT := new(MockT) 325 | JSONEq(mockT, `["foo", {"hello": "world", "nested": "hash"}]`, `{"foo": "bar", {"nested": "hash", "hello": "world"}}`) 326 | if !mockT.Failed { 327 | t.Error("Check should fail") 328 | } 329 | } 330 | 331 | func TestJSONEq_HashesNotEquivalent(t *testing.T) { 332 | mockT := new(MockT) 333 | JSONEq(mockT, `{"foo": "bar"}`, `{"foo": "bar", "hello": "world"}`) 334 | if !mockT.Failed { 335 | t.Error("Check should fail") 336 | } 337 | } 338 | 339 | func TestJSONEq_ActualIsNotJSON(t *testing.T) { 340 | mockT := new(MockT) 341 | JSONEq(mockT, `{"foo": "bar"}`, "Not JSON") 342 | if !mockT.Failed { 343 | t.Error("Check should fail") 344 | } 345 | } 346 | 347 | func TestJSONEq_ExpectedIsNotJSON(t *testing.T) { 348 | mockT := new(MockT) 349 | JSONEq(mockT, "Not JSON", `{"foo": "bar", "hello": "world"}`) 350 | if !mockT.Failed { 351 | t.Error("Check should fail") 352 | } 353 | } 354 | 355 | func TestJSONEq_ExpectedAndActualNotJSON(t *testing.T) { 356 | mockT := new(MockT) 357 | JSONEq(mockT, "Not JSON", "Not JSON") 358 | if !mockT.Failed { 359 | t.Error("Check should fail") 360 | } 361 | } 362 | 363 | func TestJSONEq_ArraysOfDifferentOrder(t *testing.T) { 364 | mockT := new(MockT) 365 | JSONEq(mockT, `["foo", {"hello": "world", "nested": "hash"}]`, `[{ "hello": "world", "nested": "hash"}, "foo"]`) 366 | if !mockT.Failed { 367 | t.Error("Check should fail") 368 | } 369 | } 370 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/vendor/github.com/davecgh/go-spew/LICENSE: -------------------------------------------------------------------------------- 1 | ISC License 2 | 3 | Copyright (c) 2012-2013 Dave Collins 4 | 5 | Permission to use, copy, modify, and distribute this software for any 6 | purpose with or without fee is hereby granted, provided that the above 7 | copyright notice and this permission notice appear in all copies. 8 | 9 | THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 10 | WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 11 | MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 12 | ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 13 | WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 14 | ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 15 | OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 16 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/vendor/github.com/davecgh/go-spew/spew/bypass.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2015 Dave Collins 2 | // 3 | // Permission to use, copy, modify, and distribute this software for any 4 | // purpose with or without fee is hereby granted, provided that the above 5 | // copyright notice and this permission notice appear in all copies. 6 | // 7 | // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | // NOTE: Due to the following build constraints, this file will only be compiled 16 | // when the code is not running on Google App Engine, compiled by GopherJS, and 17 | // "-tags safe" is not added to the go build command line. The "disableunsafe" 18 | // tag is deprecated and thus should not be used. 19 | // +build !js,!appengine,!safe,!disableunsafe 20 | 21 | package spew 22 | 23 | import ( 24 | "reflect" 25 | "unsafe" 26 | ) 27 | 28 | const ( 29 | // UnsafeDisabled is a build-time constant which specifies whether or 30 | // not access to the unsafe package is available. 31 | UnsafeDisabled = false 32 | 33 | // ptrSize is the size of a pointer on the current arch. 34 | ptrSize = unsafe.Sizeof((*byte)(nil)) 35 | ) 36 | 37 | var ( 38 | // offsetPtr, offsetScalar, and offsetFlag are the offsets for the 39 | // internal reflect.Value fields. These values are valid before golang 40 | // commit ecccf07e7f9d which changed the format. The are also valid 41 | // after commit 82f48826c6c7 which changed the format again to mirror 42 | // the original format. Code in the init function updates these offsets 43 | // as necessary. 44 | offsetPtr = uintptr(ptrSize) 45 | offsetScalar = uintptr(0) 46 | offsetFlag = uintptr(ptrSize * 2) 47 | 48 | // flagKindWidth and flagKindShift indicate various bits that the 49 | // reflect package uses internally to track kind information. 50 | // 51 | // flagRO indicates whether or not the value field of a reflect.Value is 52 | // read-only. 53 | // 54 | // flagIndir indicates whether the value field of a reflect.Value is 55 | // the actual data or a pointer to the data. 56 | // 57 | // These values are valid before golang commit 90a7c3c86944 which 58 | // changed their positions. Code in the init function updates these 59 | // flags as necessary. 60 | flagKindWidth = uintptr(5) 61 | flagKindShift = uintptr(flagKindWidth - 1) 62 | flagRO = uintptr(1 << 0) 63 | flagIndir = uintptr(1 << 1) 64 | ) 65 | 66 | func init() { 67 | // Older versions of reflect.Value stored small integers directly in the 68 | // ptr field (which is named val in the older versions). Versions 69 | // between commits ecccf07e7f9d and 82f48826c6c7 added a new field named 70 | // scalar for this purpose which unfortunately came before the flag 71 | // field, so the offset of the flag field is different for those 72 | // versions. 73 | // 74 | // This code constructs a new reflect.Value from a known small integer 75 | // and checks if the size of the reflect.Value struct indicates it has 76 | // the scalar field. When it does, the offsets are updated accordingly. 77 | vv := reflect.ValueOf(0xf00) 78 | if unsafe.Sizeof(vv) == (ptrSize * 4) { 79 | offsetScalar = ptrSize * 2 80 | offsetFlag = ptrSize * 3 81 | } 82 | 83 | // Commit 90a7c3c86944 changed the flag positions such that the low 84 | // order bits are the kind. This code extracts the kind from the flags 85 | // field and ensures it's the correct type. When it's not, the flag 86 | // order has been changed to the newer format, so the flags are updated 87 | // accordingly. 88 | upf := unsafe.Pointer(uintptr(unsafe.Pointer(&vv)) + offsetFlag) 89 | upfv := *(*uintptr)(upf) 90 | flagKindMask := uintptr((1<>flagKindShift != uintptr(reflect.Int) { 92 | flagKindShift = 0 93 | flagRO = 1 << 5 94 | flagIndir = 1 << 6 95 | 96 | // Commit adf9b30e5594 modified the flags to separate the 97 | // flagRO flag into two bits which specifies whether or not the 98 | // field is embedded. This causes flagIndir to move over a bit 99 | // and means that flagRO is the combination of either of the 100 | // original flagRO bit and the new bit. 101 | // 102 | // This code detects the change by extracting what used to be 103 | // the indirect bit to ensure it's set. When it's not, the flag 104 | // order has been changed to the newer format, so the flags are 105 | // updated accordingly. 106 | if upfv&flagIndir == 0 { 107 | flagRO = 3 << 5 108 | flagIndir = 1 << 7 109 | } 110 | } 111 | } 112 | 113 | // unsafeReflectValue converts the passed reflect.Value into a one that bypasses 114 | // the typical safety restrictions preventing access to unaddressable and 115 | // unexported data. It works by digging the raw pointer to the underlying 116 | // value out of the protected value and generating a new unprotected (unsafe) 117 | // reflect.Value to it. 118 | // 119 | // This allows us to check for implementations of the Stringer and error 120 | // interfaces to be used for pretty printing ordinarily unaddressable and 121 | // inaccessible values such as unexported struct fields. 122 | func unsafeReflectValue(v reflect.Value) (rv reflect.Value) { 123 | indirects := 1 124 | vt := v.Type() 125 | upv := unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetPtr) 126 | rvf := *(*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetFlag)) 127 | if rvf&flagIndir != 0 { 128 | vt = reflect.PtrTo(v.Type()) 129 | indirects++ 130 | } else if offsetScalar != 0 { 131 | // The value is in the scalar field when it's not one of the 132 | // reference types. 133 | switch vt.Kind() { 134 | case reflect.Uintptr: 135 | case reflect.Chan: 136 | case reflect.Func: 137 | case reflect.Map: 138 | case reflect.Ptr: 139 | case reflect.UnsafePointer: 140 | default: 141 | upv = unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + 142 | offsetScalar) 143 | } 144 | } 145 | 146 | pv := reflect.NewAt(vt, upv) 147 | rv = pv 148 | for i := 0; i < indirects; i++ { 149 | rv = rv.Elem() 150 | } 151 | return rv 152 | } 153 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/vendor/github.com/davecgh/go-spew/spew/bypasssafe.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2015 Dave Collins 2 | // 3 | // Permission to use, copy, modify, and distribute this software for any 4 | // purpose with or without fee is hereby granted, provided that the above 5 | // copyright notice and this permission notice appear in all copies. 6 | // 7 | // THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | // WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | // MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | // ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | // WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | // ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | // OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | // NOTE: Due to the following build constraints, this file will only be compiled 16 | // when the code is running on Google App Engine, compiled by GopherJS, or 17 | // "-tags safe" is added to the go build command line. The "disableunsafe" 18 | // tag is deprecated and thus should not be used. 19 | // +build js appengine safe disableunsafe 20 | 21 | package spew 22 | 23 | import "reflect" 24 | 25 | const ( 26 | // UnsafeDisabled is a build-time constant which specifies whether or 27 | // not access to the unsafe package is available. 28 | UnsafeDisabled = true 29 | ) 30 | 31 | // unsafeReflectValue typically converts the passed reflect.Value into a one 32 | // that bypasses the typical safety restrictions preventing access to 33 | // unaddressable and unexported data. However, doing this relies on access to 34 | // the unsafe package. This is a stub version which simply returns the passed 35 | // reflect.Value when the unsafe package is not available. 36 | func unsafeReflectValue(v reflect.Value) reflect.Value { 37 | return v 38 | } 39 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/vendor/github.com/davecgh/go-spew/spew/doc.go: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2013 Dave Collins 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | /* 18 | Package spew implements a deep pretty printer for Go data structures to aid in 19 | debugging. 20 | 21 | A quick overview of the additional features spew provides over the built-in 22 | printing facilities for Go data types are as follows: 23 | 24 | * Pointers are dereferenced and followed 25 | * Circular data structures are detected and handled properly 26 | * Custom Stringer/error interfaces are optionally invoked, including 27 | on unexported types 28 | * Custom types which only implement the Stringer/error interfaces via 29 | a pointer receiver are optionally invoked when passing non-pointer 30 | variables 31 | * Byte arrays and slices are dumped like the hexdump -C command which 32 | includes offsets, byte values in hex, and ASCII output (only when using 33 | Dump style) 34 | 35 | There are two different approaches spew allows for dumping Go data structures: 36 | 37 | * Dump style which prints with newlines, customizable indentation, 38 | and additional debug information such as types and all pointer addresses 39 | used to indirect to the final value 40 | * A custom Formatter interface that integrates cleanly with the standard fmt 41 | package and replaces %v, %+v, %#v, and %#+v to provide inline printing 42 | similar to the default %v while providing the additional functionality 43 | outlined above and passing unsupported format verbs such as %x and %q 44 | along to fmt 45 | 46 | Quick Start 47 | 48 | This section demonstrates how to quickly get started with spew. See the 49 | sections below for further details on formatting and configuration options. 50 | 51 | To dump a variable with full newlines, indentation, type, and pointer 52 | information use Dump, Fdump, or Sdump: 53 | spew.Dump(myVar1, myVar2, ...) 54 | spew.Fdump(someWriter, myVar1, myVar2, ...) 55 | str := spew.Sdump(myVar1, myVar2, ...) 56 | 57 | Alternatively, if you would prefer to use format strings with a compacted inline 58 | printing style, use the convenience wrappers Printf, Fprintf, etc with 59 | %v (most compact), %+v (adds pointer addresses), %#v (adds types), or 60 | %#+v (adds types and pointer addresses): 61 | spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2) 62 | spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 63 | spew.Fprintf(someWriter, "myVar1: %v -- myVar2: %+v", myVar1, myVar2) 64 | spew.Fprintf(someWriter, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 65 | 66 | Configuration Options 67 | 68 | Configuration of spew is handled by fields in the ConfigState type. For 69 | convenience, all of the top-level functions use a global state available 70 | via the spew.Config global. 71 | 72 | It is also possible to create a ConfigState instance that provides methods 73 | equivalent to the top-level functions. This allows concurrent configuration 74 | options. See the ConfigState documentation for more details. 75 | 76 | The following configuration options are available: 77 | * Indent 78 | String to use for each indentation level for Dump functions. 79 | It is a single space by default. A popular alternative is "\t". 80 | 81 | * MaxDepth 82 | Maximum number of levels to descend into nested data structures. 83 | There is no limit by default. 84 | 85 | * DisableMethods 86 | Disables invocation of error and Stringer interface methods. 87 | Method invocation is enabled by default. 88 | 89 | * DisablePointerMethods 90 | Disables invocation of error and Stringer interface methods on types 91 | which only accept pointer receivers from non-pointer variables. 92 | Pointer method invocation is enabled by default. 93 | 94 | * ContinueOnMethod 95 | Enables recursion into types after invoking error and Stringer interface 96 | methods. Recursion after method invocation is disabled by default. 97 | 98 | * SortKeys 99 | Specifies map keys should be sorted before being printed. Use 100 | this to have a more deterministic, diffable output. Note that 101 | only native types (bool, int, uint, floats, uintptr and string) 102 | and types which implement error or Stringer interfaces are 103 | supported with other types sorted according to the 104 | reflect.Value.String() output which guarantees display 105 | stability. Natural map order is used by default. 106 | 107 | * SpewKeys 108 | Specifies that, as a last resort attempt, map keys should be 109 | spewed to strings and sorted by those strings. This is only 110 | considered if SortKeys is true. 111 | 112 | Dump Usage 113 | 114 | Simply call spew.Dump with a list of variables you want to dump: 115 | 116 | spew.Dump(myVar1, myVar2, ...) 117 | 118 | You may also call spew.Fdump if you would prefer to output to an arbitrary 119 | io.Writer. For example, to dump to standard error: 120 | 121 | spew.Fdump(os.Stderr, myVar1, myVar2, ...) 122 | 123 | A third option is to call spew.Sdump to get the formatted output as a string: 124 | 125 | str := spew.Sdump(myVar1, myVar2, ...) 126 | 127 | Sample Dump Output 128 | 129 | See the Dump example for details on the setup of the types and variables being 130 | shown here. 131 | 132 | (main.Foo) { 133 | unexportedField: (*main.Bar)(0xf84002e210)({ 134 | flag: (main.Flag) flagTwo, 135 | data: (uintptr) 136 | }), 137 | ExportedField: (map[interface {}]interface {}) (len=1) { 138 | (string) (len=3) "one": (bool) true 139 | } 140 | } 141 | 142 | Byte (and uint8) arrays and slices are displayed uniquely like the hexdump -C 143 | command as shown. 144 | ([]uint8) (len=32 cap=32) { 145 | 00000000 11 12 13 14 15 16 17 18 19 1a 1b 1c 1d 1e 1f 20 |............... | 146 | 00000010 21 22 23 24 25 26 27 28 29 2a 2b 2c 2d 2e 2f 30 |!"#$%&'()*+,-./0| 147 | 00000020 31 32 |12| 148 | } 149 | 150 | Custom Formatter 151 | 152 | Spew provides a custom formatter that implements the fmt.Formatter interface 153 | so that it integrates cleanly with standard fmt package printing functions. The 154 | formatter is useful for inline printing of smaller data types similar to the 155 | standard %v format specifier. 156 | 157 | The custom formatter only responds to the %v (most compact), %+v (adds pointer 158 | addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb 159 | combinations. Any other verbs such as %x and %q will be sent to the the 160 | standard fmt package for formatting. In addition, the custom formatter ignores 161 | the width and precision arguments (however they will still work on the format 162 | specifiers not handled by the custom formatter). 163 | 164 | Custom Formatter Usage 165 | 166 | The simplest way to make use of the spew custom formatter is to call one of the 167 | convenience functions such as spew.Printf, spew.Println, or spew.Printf. The 168 | functions have syntax you are most likely already familiar with: 169 | 170 | spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2) 171 | spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 172 | spew.Println(myVar, myVar2) 173 | spew.Fprintf(os.Stderr, "myVar1: %v -- myVar2: %+v", myVar1, myVar2) 174 | spew.Fprintf(os.Stderr, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) 175 | 176 | See the Index for the full list convenience functions. 177 | 178 | Sample Formatter Output 179 | 180 | Double pointer to a uint8: 181 | %v: <**>5 182 | %+v: <**>(0xf8400420d0->0xf8400420c8)5 183 | %#v: (**uint8)5 184 | %#+v: (**uint8)(0xf8400420d0->0xf8400420c8)5 185 | 186 | Pointer to circular struct with a uint8 field and a pointer to itself: 187 | %v: <*>{1 <*>} 188 | %+v: <*>(0xf84003e260){ui8:1 c:<*>(0xf84003e260)} 189 | %#v: (*main.circular){ui8:(uint8)1 c:(*main.circular)} 190 | %#+v: (*main.circular)(0xf84003e260){ui8:(uint8)1 c:(*main.circular)(0xf84003e260)} 191 | 192 | See the Printf example for details on the setup of variables being shown 193 | here. 194 | 195 | Errors 196 | 197 | Since it is possible for custom Stringer/error interfaces to panic, spew 198 | detects them and handles them internally by printing the panic information 199 | inline with the output. Since spew is intended to provide deep pretty printing 200 | capabilities on structures, it intentionally does not return any errors. 201 | */ 202 | package spew 203 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/vendor/github.com/davecgh/go-spew/spew/spew.go: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2013 Dave Collins 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | package spew 18 | 19 | import ( 20 | "fmt" 21 | "io" 22 | ) 23 | 24 | // Errorf is a wrapper for fmt.Errorf that treats each argument as if it were 25 | // passed with a default Formatter interface returned by NewFormatter. It 26 | // returns the formatted string as a value that satisfies error. See 27 | // NewFormatter for formatting details. 28 | // 29 | // This function is shorthand for the following syntax: 30 | // 31 | // fmt.Errorf(format, spew.NewFormatter(a), spew.NewFormatter(b)) 32 | func Errorf(format string, a ...interface{}) (err error) { 33 | return fmt.Errorf(format, convertArgs(a)...) 34 | } 35 | 36 | // Fprint is a wrapper for fmt.Fprint that treats each argument as if it were 37 | // passed with a default Formatter interface returned by NewFormatter. It 38 | // returns the number of bytes written and any write error encountered. See 39 | // NewFormatter for formatting details. 40 | // 41 | // This function is shorthand for the following syntax: 42 | // 43 | // fmt.Fprint(w, spew.NewFormatter(a), spew.NewFormatter(b)) 44 | func Fprint(w io.Writer, a ...interface{}) (n int, err error) { 45 | return fmt.Fprint(w, convertArgs(a)...) 46 | } 47 | 48 | // Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were 49 | // passed with a default Formatter interface returned by NewFormatter. It 50 | // returns the number of bytes written and any write error encountered. See 51 | // NewFormatter for formatting details. 52 | // 53 | // This function is shorthand for the following syntax: 54 | // 55 | // fmt.Fprintf(w, format, spew.NewFormatter(a), spew.NewFormatter(b)) 56 | func Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) { 57 | return fmt.Fprintf(w, format, convertArgs(a)...) 58 | } 59 | 60 | // Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it 61 | // passed with a default Formatter interface returned by NewFormatter. See 62 | // NewFormatter for formatting details. 63 | // 64 | // This function is shorthand for the following syntax: 65 | // 66 | // fmt.Fprintln(w, spew.NewFormatter(a), spew.NewFormatter(b)) 67 | func Fprintln(w io.Writer, a ...interface{}) (n int, err error) { 68 | return fmt.Fprintln(w, convertArgs(a)...) 69 | } 70 | 71 | // Print is a wrapper for fmt.Print that treats each argument as if it were 72 | // passed with a default Formatter interface returned by NewFormatter. It 73 | // returns the number of bytes written and any write error encountered. See 74 | // NewFormatter for formatting details. 75 | // 76 | // This function is shorthand for the following syntax: 77 | // 78 | // fmt.Print(spew.NewFormatter(a), spew.NewFormatter(b)) 79 | func Print(a ...interface{}) (n int, err error) { 80 | return fmt.Print(convertArgs(a)...) 81 | } 82 | 83 | // Printf is a wrapper for fmt.Printf that treats each argument as if it were 84 | // passed with a default Formatter interface returned by NewFormatter. It 85 | // returns the number of bytes written and any write error encountered. See 86 | // NewFormatter for formatting details. 87 | // 88 | // This function is shorthand for the following syntax: 89 | // 90 | // fmt.Printf(format, spew.NewFormatter(a), spew.NewFormatter(b)) 91 | func Printf(format string, a ...interface{}) (n int, err error) { 92 | return fmt.Printf(format, convertArgs(a)...) 93 | } 94 | 95 | // Println is a wrapper for fmt.Println that treats each argument as if it were 96 | // passed with a default Formatter interface returned by NewFormatter. It 97 | // returns the number of bytes written and any write error encountered. See 98 | // NewFormatter for formatting details. 99 | // 100 | // This function is shorthand for the following syntax: 101 | // 102 | // fmt.Println(spew.NewFormatter(a), spew.NewFormatter(b)) 103 | func Println(a ...interface{}) (n int, err error) { 104 | return fmt.Println(convertArgs(a)...) 105 | } 106 | 107 | // Sprint is a wrapper for fmt.Sprint that treats each argument as if it were 108 | // passed with a default Formatter interface returned by NewFormatter. It 109 | // returns the resulting string. See NewFormatter for formatting details. 110 | // 111 | // This function is shorthand for the following syntax: 112 | // 113 | // fmt.Sprint(spew.NewFormatter(a), spew.NewFormatter(b)) 114 | func Sprint(a ...interface{}) string { 115 | return fmt.Sprint(convertArgs(a)...) 116 | } 117 | 118 | // Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were 119 | // passed with a default Formatter interface returned by NewFormatter. It 120 | // returns the resulting string. See NewFormatter for formatting details. 121 | // 122 | // This function is shorthand for the following syntax: 123 | // 124 | // fmt.Sprintf(format, spew.NewFormatter(a), spew.NewFormatter(b)) 125 | func Sprintf(format string, a ...interface{}) string { 126 | return fmt.Sprintf(format, convertArgs(a)...) 127 | } 128 | 129 | // Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it 130 | // were passed with a default Formatter interface returned by NewFormatter. It 131 | // returns the resulting string. See NewFormatter for formatting details. 132 | // 133 | // This function is shorthand for the following syntax: 134 | // 135 | // fmt.Sprintln(spew.NewFormatter(a), spew.NewFormatter(b)) 136 | func Sprintln(a ...interface{}) string { 137 | return fmt.Sprintln(convertArgs(a)...) 138 | } 139 | 140 | // convertArgs accepts a slice of arguments and returns a slice of the same 141 | // length with each argument converted to a default spew Formatter interface. 142 | func convertArgs(args []interface{}) (formatters []interface{}) { 143 | formatters = make([]interface{}, len(args)) 144 | for index, arg := range args { 145 | formatters[index] = NewFormatter(arg) 146 | } 147 | return formatters 148 | } 149 | -------------------------------------------------------------------------------- /vendor/github.com/stretchr/testify/vendor/github.com/pmezard/go-difflib/LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2013, Patrick Mezard 2 | All rights reserved. 3 | 4 | Redistribution and use in source and binary forms, with or without 5 | modification, are permitted provided that the following conditions are 6 | met: 7 | 8 | Redistributions of source code must retain the above copyright 9 | notice, this list of conditions and the following disclaimer. 10 | Redistributions in binary form must reproduce the above copyright 11 | notice, this list of conditions and the following disclaimer in the 12 | documentation and/or other materials provided with the distribution. 13 | The names of its contributors may not be used to endorse or promote 14 | products derived from this software without specific prior written 15 | permission. 16 | 17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS 18 | IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 19 | TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A 20 | PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 21 | HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 22 | SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 23 | TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 24 | PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 25 | LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 26 | NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 27 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2009 The Go Authors. All rights reserved. 2 | 3 | Redistribution and use in source and binary forms, with or without 4 | modification, are permitted provided that the following conditions are 5 | met: 6 | 7 | * Redistributions of source code must retain the above copyright 8 | notice, this list of conditions and the following disclaimer. 9 | * Redistributions in binary form must reproduce the above 10 | copyright notice, this list of conditions and the following disclaimer 11 | in the documentation and/or other materials provided with the 12 | distribution. 13 | * Neither the name of Google Inc. nor the names of its 14 | contributors may be used to endorse or promote products derived from 15 | this software without specific prior written permission. 16 | 17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 18 | "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 19 | LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 20 | A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 21 | OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 22 | SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 23 | LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 24 | DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 25 | THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 26 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 27 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/PATENTS: -------------------------------------------------------------------------------- 1 | Additional IP Rights Grant (Patents) 2 | 3 | "This implementation" means the copyrightable works distributed by 4 | Google as part of the Go project. 5 | 6 | Google hereby grants to You a perpetual, worldwide, non-exclusive, 7 | no-charge, royalty-free, irrevocable (except as stated in this section) 8 | patent license to make, have made, use, offer to sell, sell, import, 9 | transfer and otherwise run, modify and propagate the contents of this 10 | implementation of Go, where such license applies only to those patent 11 | claims, both currently owned or controlled by Google and acquired in 12 | the future, licensable by Google that are necessarily infringed by this 13 | implementation of Go. This grant does not include claims that would be 14 | infringed only as a consequence of further modification of this 15 | implementation. If you or your agent or exclusive licensee institute or 16 | order or agree to the institution of patent litigation against any 17 | entity (including a cross-claim or counterclaim in a lawsuit) alleging 18 | that this implementation of Go or any code incorporated within this 19 | implementation of Go constitutes direct or contributory patent 20 | infringement, or inducement of patent infringement, then any patent 21 | rights granted to you under this License for this implementation of Go 22 | shall terminate as of the date such litigation is filed. 23 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/context/context.go: -------------------------------------------------------------------------------- 1 | // Copyright 2014 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // Package context defines the Context type, which carries deadlines, 6 | // cancelation signals, and other request-scoped values across API boundaries 7 | // and between processes. 8 | // 9 | // Incoming requests to a server should create a Context, and outgoing calls to 10 | // servers should accept a Context. The chain of function calls between must 11 | // propagate the Context, optionally replacing it with a modified copy created 12 | // using WithDeadline, WithTimeout, WithCancel, or WithValue. 13 | // 14 | // Programs that use Contexts should follow these rules to keep interfaces 15 | // consistent across packages and enable static analysis tools to check context 16 | // propagation: 17 | // 18 | // Do not store Contexts inside a struct type; instead, pass a Context 19 | // explicitly to each function that needs it. The Context should be the first 20 | // parameter, typically named ctx: 21 | // 22 | // func DoSomething(ctx context.Context, arg Arg) error { 23 | // // ... use ctx ... 24 | // } 25 | // 26 | // Do not pass a nil Context, even if a function permits it. Pass context.TODO 27 | // if you are unsure about which Context to use. 28 | // 29 | // Use context Values only for request-scoped data that transits processes and 30 | // APIs, not for passing optional parameters to functions. 31 | // 32 | // The same Context may be passed to functions running in different goroutines; 33 | // Contexts are safe for simultaneous use by multiple goroutines. 34 | // 35 | // See http://blog.golang.org/context for example code for a server that uses 36 | // Contexts. 37 | package context // import "golang.org/x/net/context" 38 | 39 | import "time" 40 | 41 | // A Context carries a deadline, a cancelation signal, and other values across 42 | // API boundaries. 43 | // 44 | // Context's methods may be called by multiple goroutines simultaneously. 45 | type Context interface { 46 | // Deadline returns the time when work done on behalf of this context 47 | // should be canceled. Deadline returns ok==false when no deadline is 48 | // set. Successive calls to Deadline return the same results. 49 | Deadline() (deadline time.Time, ok bool) 50 | 51 | // Done returns a channel that's closed when work done on behalf of this 52 | // context should be canceled. Done may return nil if this context can 53 | // never be canceled. Successive calls to Done return the same value. 54 | // 55 | // WithCancel arranges for Done to be closed when cancel is called; 56 | // WithDeadline arranges for Done to be closed when the deadline 57 | // expires; WithTimeout arranges for Done to be closed when the timeout 58 | // elapses. 59 | // 60 | // Done is provided for use in select statements: 61 | // 62 | // // Stream generates values with DoSomething and sends them to out 63 | // // until DoSomething returns an error or ctx.Done is closed. 64 | // func Stream(ctx context.Context, out chan<- Value) error { 65 | // for { 66 | // v, err := DoSomething(ctx) 67 | // if err != nil { 68 | // return err 69 | // } 70 | // select { 71 | // case <-ctx.Done(): 72 | // return ctx.Err() 73 | // case out <- v: 74 | // } 75 | // } 76 | // } 77 | // 78 | // See http://blog.golang.org/pipelines for more examples of how to use 79 | // a Done channel for cancelation. 80 | Done() <-chan struct{} 81 | 82 | // Err returns a non-nil error value after Done is closed. Err returns 83 | // Canceled if the context was canceled or DeadlineExceeded if the 84 | // context's deadline passed. No other values for Err are defined. 85 | // After Done is closed, successive calls to Err return the same value. 86 | Err() error 87 | 88 | // Value returns the value associated with this context for key, or nil 89 | // if no value is associated with key. Successive calls to Value with 90 | // the same key returns the same result. 91 | // 92 | // Use context values only for request-scoped data that transits 93 | // processes and API boundaries, not for passing optional parameters to 94 | // functions. 95 | // 96 | // A key identifies a specific value in a Context. Functions that wish 97 | // to store values in Context typically allocate a key in a global 98 | // variable then use that key as the argument to context.WithValue and 99 | // Context.Value. A key can be any type that supports equality; 100 | // packages should define keys as an unexported type to avoid 101 | // collisions. 102 | // 103 | // Packages that define a Context key should provide type-safe accessors 104 | // for the values stores using that key: 105 | // 106 | // // Package user defines a User type that's stored in Contexts. 107 | // package user 108 | // 109 | // import "golang.org/x/net/context" 110 | // 111 | // // User is the type of value stored in the Contexts. 112 | // type User struct {...} 113 | // 114 | // // key is an unexported type for keys defined in this package. 115 | // // This prevents collisions with keys defined in other packages. 116 | // type key int 117 | // 118 | // // userKey is the key for user.User values in Contexts. It is 119 | // // unexported; clients use user.NewContext and user.FromContext 120 | // // instead of using this key directly. 121 | // var userKey key = 0 122 | // 123 | // // NewContext returns a new Context that carries value u. 124 | // func NewContext(ctx context.Context, u *User) context.Context { 125 | // return context.WithValue(ctx, userKey, u) 126 | // } 127 | // 128 | // // FromContext returns the User value stored in ctx, if any. 129 | // func FromContext(ctx context.Context) (*User, bool) { 130 | // u, ok := ctx.Value(userKey).(*User) 131 | // return u, ok 132 | // } 133 | Value(key interface{}) interface{} 134 | } 135 | 136 | // Background returns a non-nil, empty Context. It is never canceled, has no 137 | // values, and has no deadline. It is typically used by the main function, 138 | // initialization, and tests, and as the top-level Context for incoming 139 | // requests. 140 | func Background() Context { 141 | return background 142 | } 143 | 144 | // TODO returns a non-nil, empty Context. Code should use context.TODO when 145 | // it's unclear which Context to use or it is not yet available (because the 146 | // surrounding function has not yet been extended to accept a Context 147 | // parameter). TODO is recognized by static analysis tools that determine 148 | // whether Contexts are propagated correctly in a program. 149 | func TODO() Context { 150 | return todo 151 | } 152 | 153 | // A CancelFunc tells an operation to abandon its work. 154 | // A CancelFunc does not wait for the work to stop. 155 | // After the first call, subsequent calls to a CancelFunc do nothing. 156 | type CancelFunc func() 157 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/context/go17.go: -------------------------------------------------------------------------------- 1 | // Copyright 2016 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // +build go1.7 6 | 7 | package context 8 | 9 | import ( 10 | "context" // standard library's context, as of Go 1.7 11 | "time" 12 | ) 13 | 14 | var ( 15 | todo = context.TODO() 16 | background = context.Background() 17 | ) 18 | 19 | // Canceled is the error returned by Context.Err when the context is canceled. 20 | var Canceled = context.Canceled 21 | 22 | // DeadlineExceeded is the error returned by Context.Err when the context's 23 | // deadline passes. 24 | var DeadlineExceeded = context.DeadlineExceeded 25 | 26 | // WithCancel returns a copy of parent with a new Done channel. The returned 27 | // context's Done channel is closed when the returned cancel function is called 28 | // or when the parent context's Done channel is closed, whichever happens first. 29 | // 30 | // Canceling this context releases resources associated with it, so code should 31 | // call cancel as soon as the operations running in this Context complete. 32 | func WithCancel(parent Context) (ctx Context, cancel CancelFunc) { 33 | ctx, f := context.WithCancel(parent) 34 | return ctx, CancelFunc(f) 35 | } 36 | 37 | // WithDeadline returns a copy of the parent context with the deadline adjusted 38 | // to be no later than d. If the parent's deadline is already earlier than d, 39 | // WithDeadline(parent, d) is semantically equivalent to parent. The returned 40 | // context's Done channel is closed when the deadline expires, when the returned 41 | // cancel function is called, or when the parent context's Done channel is 42 | // closed, whichever happens first. 43 | // 44 | // Canceling this context releases resources associated with it, so code should 45 | // call cancel as soon as the operations running in this Context complete. 46 | func WithDeadline(parent Context, deadline time.Time) (Context, CancelFunc) { 47 | ctx, f := context.WithDeadline(parent, deadline) 48 | return ctx, CancelFunc(f) 49 | } 50 | 51 | // WithTimeout returns WithDeadline(parent, time.Now().Add(timeout)). 52 | // 53 | // Canceling this context releases resources associated with it, so code should 54 | // call cancel as soon as the operations running in this Context complete: 55 | // 56 | // func slowOperationWithTimeout(ctx context.Context) (Result, error) { 57 | // ctx, cancel := context.WithTimeout(ctx, 100*time.Millisecond) 58 | // defer cancel() // releases resources if slowOperation completes before timeout elapses 59 | // return slowOperation(ctx) 60 | // } 61 | func WithTimeout(parent Context, timeout time.Duration) (Context, CancelFunc) { 62 | return WithDeadline(parent, time.Now().Add(timeout)) 63 | } 64 | 65 | // WithValue returns a copy of parent in which the value associated with key is 66 | // val. 67 | // 68 | // Use context Values only for request-scoped data that transits processes and 69 | // APIs, not for passing optional parameters to functions. 70 | func WithValue(parent Context, key interface{}, val interface{}) Context { 71 | return context.WithValue(parent, key, val) 72 | } 73 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/context/pre_go17.go: -------------------------------------------------------------------------------- 1 | // Copyright 2014 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // +build !go1.7 6 | 7 | package context 8 | 9 | import ( 10 | "errors" 11 | "fmt" 12 | "sync" 13 | "time" 14 | ) 15 | 16 | // An emptyCtx is never canceled, has no values, and has no deadline. It is not 17 | // struct{}, since vars of this type must have distinct addresses. 18 | type emptyCtx int 19 | 20 | func (*emptyCtx) Deadline() (deadline time.Time, ok bool) { 21 | return 22 | } 23 | 24 | func (*emptyCtx) Done() <-chan struct{} { 25 | return nil 26 | } 27 | 28 | func (*emptyCtx) Err() error { 29 | return nil 30 | } 31 | 32 | func (*emptyCtx) Value(key interface{}) interface{} { 33 | return nil 34 | } 35 | 36 | func (e *emptyCtx) String() string { 37 | switch e { 38 | case background: 39 | return "context.Background" 40 | case todo: 41 | return "context.TODO" 42 | } 43 | return "unknown empty Context" 44 | } 45 | 46 | var ( 47 | background = new(emptyCtx) 48 | todo = new(emptyCtx) 49 | ) 50 | 51 | // Canceled is the error returned by Context.Err when the context is canceled. 52 | var Canceled = errors.New("context canceled") 53 | 54 | // DeadlineExceeded is the error returned by Context.Err when the context's 55 | // deadline passes. 56 | var DeadlineExceeded = errors.New("context deadline exceeded") 57 | 58 | // WithCancel returns a copy of parent with a new Done channel. The returned 59 | // context's Done channel is closed when the returned cancel function is called 60 | // or when the parent context's Done channel is closed, whichever happens first. 61 | // 62 | // Canceling this context releases resources associated with it, so code should 63 | // call cancel as soon as the operations running in this Context complete. 64 | func WithCancel(parent Context) (ctx Context, cancel CancelFunc) { 65 | c := newCancelCtx(parent) 66 | propagateCancel(parent, c) 67 | return c, func() { c.cancel(true, Canceled) } 68 | } 69 | 70 | // newCancelCtx returns an initialized cancelCtx. 71 | func newCancelCtx(parent Context) *cancelCtx { 72 | return &cancelCtx{ 73 | Context: parent, 74 | done: make(chan struct{}), 75 | } 76 | } 77 | 78 | // propagateCancel arranges for child to be canceled when parent is. 79 | func propagateCancel(parent Context, child canceler) { 80 | if parent.Done() == nil { 81 | return // parent is never canceled 82 | } 83 | if p, ok := parentCancelCtx(parent); ok { 84 | p.mu.Lock() 85 | if p.err != nil { 86 | // parent has already been canceled 87 | child.cancel(false, p.err) 88 | } else { 89 | if p.children == nil { 90 | p.children = make(map[canceler]bool) 91 | } 92 | p.children[child] = true 93 | } 94 | p.mu.Unlock() 95 | } else { 96 | go func() { 97 | select { 98 | case <-parent.Done(): 99 | child.cancel(false, parent.Err()) 100 | case <-child.Done(): 101 | } 102 | }() 103 | } 104 | } 105 | 106 | // parentCancelCtx follows a chain of parent references until it finds a 107 | // *cancelCtx. This function understands how each of the concrete types in this 108 | // package represents its parent. 109 | func parentCancelCtx(parent Context) (*cancelCtx, bool) { 110 | for { 111 | switch c := parent.(type) { 112 | case *cancelCtx: 113 | return c, true 114 | case *timerCtx: 115 | return c.cancelCtx, true 116 | case *valueCtx: 117 | parent = c.Context 118 | default: 119 | return nil, false 120 | } 121 | } 122 | } 123 | 124 | // removeChild removes a context from its parent. 125 | func removeChild(parent Context, child canceler) { 126 | p, ok := parentCancelCtx(parent) 127 | if !ok { 128 | return 129 | } 130 | p.mu.Lock() 131 | if p.children != nil { 132 | delete(p.children, child) 133 | } 134 | p.mu.Unlock() 135 | } 136 | 137 | // A canceler is a context type that can be canceled directly. The 138 | // implementations are *cancelCtx and *timerCtx. 139 | type canceler interface { 140 | cancel(removeFromParent bool, err error) 141 | Done() <-chan struct{} 142 | } 143 | 144 | // A cancelCtx can be canceled. When canceled, it also cancels any children 145 | // that implement canceler. 146 | type cancelCtx struct { 147 | Context 148 | 149 | done chan struct{} // closed by the first cancel call. 150 | 151 | mu sync.Mutex 152 | children map[canceler]bool // set to nil by the first cancel call 153 | err error // set to non-nil by the first cancel call 154 | } 155 | 156 | func (c *cancelCtx) Done() <-chan struct{} { 157 | return c.done 158 | } 159 | 160 | func (c *cancelCtx) Err() error { 161 | c.mu.Lock() 162 | defer c.mu.Unlock() 163 | return c.err 164 | } 165 | 166 | func (c *cancelCtx) String() string { 167 | return fmt.Sprintf("%v.WithCancel", c.Context) 168 | } 169 | 170 | // cancel closes c.done, cancels each of c's children, and, if 171 | // removeFromParent is true, removes c from its parent's children. 172 | func (c *cancelCtx) cancel(removeFromParent bool, err error) { 173 | if err == nil { 174 | panic("context: internal error: missing cancel error") 175 | } 176 | c.mu.Lock() 177 | if c.err != nil { 178 | c.mu.Unlock() 179 | return // already canceled 180 | } 181 | c.err = err 182 | close(c.done) 183 | for child := range c.children { 184 | // NOTE: acquiring the child's lock while holding parent's lock. 185 | child.cancel(false, err) 186 | } 187 | c.children = nil 188 | c.mu.Unlock() 189 | 190 | if removeFromParent { 191 | removeChild(c.Context, c) 192 | } 193 | } 194 | 195 | // WithDeadline returns a copy of the parent context with the deadline adjusted 196 | // to be no later than d. If the parent's deadline is already earlier than d, 197 | // WithDeadline(parent, d) is semantically equivalent to parent. The returned 198 | // context's Done channel is closed when the deadline expires, when the returned 199 | // cancel function is called, or when the parent context's Done channel is 200 | // closed, whichever happens first. 201 | // 202 | // Canceling this context releases resources associated with it, so code should 203 | // call cancel as soon as the operations running in this Context complete. 204 | func WithDeadline(parent Context, deadline time.Time) (Context, CancelFunc) { 205 | if cur, ok := parent.Deadline(); ok && cur.Before(deadline) { 206 | // The current deadline is already sooner than the new one. 207 | return WithCancel(parent) 208 | } 209 | c := &timerCtx{ 210 | cancelCtx: newCancelCtx(parent), 211 | deadline: deadline, 212 | } 213 | propagateCancel(parent, c) 214 | d := deadline.Sub(time.Now()) 215 | if d <= 0 { 216 | c.cancel(true, DeadlineExceeded) // deadline has already passed 217 | return c, func() { c.cancel(true, Canceled) } 218 | } 219 | c.mu.Lock() 220 | defer c.mu.Unlock() 221 | if c.err == nil { 222 | c.timer = time.AfterFunc(d, func() { 223 | c.cancel(true, DeadlineExceeded) 224 | }) 225 | } 226 | return c, func() { c.cancel(true, Canceled) } 227 | } 228 | 229 | // A timerCtx carries a timer and a deadline. It embeds a cancelCtx to 230 | // implement Done and Err. It implements cancel by stopping its timer then 231 | // delegating to cancelCtx.cancel. 232 | type timerCtx struct { 233 | *cancelCtx 234 | timer *time.Timer // Under cancelCtx.mu. 235 | 236 | deadline time.Time 237 | } 238 | 239 | func (c *timerCtx) Deadline() (deadline time.Time, ok bool) { 240 | return c.deadline, true 241 | } 242 | 243 | func (c *timerCtx) String() string { 244 | return fmt.Sprintf("%v.WithDeadline(%s [%s])", c.cancelCtx.Context, c.deadline, c.deadline.Sub(time.Now())) 245 | } 246 | 247 | func (c *timerCtx) cancel(removeFromParent bool, err error) { 248 | c.cancelCtx.cancel(false, err) 249 | if removeFromParent { 250 | // Remove this timerCtx from its parent cancelCtx's children. 251 | removeChild(c.cancelCtx.Context, c) 252 | } 253 | c.mu.Lock() 254 | if c.timer != nil { 255 | c.timer.Stop() 256 | c.timer = nil 257 | } 258 | c.mu.Unlock() 259 | } 260 | 261 | // WithTimeout returns WithDeadline(parent, time.Now().Add(timeout)). 262 | // 263 | // Canceling this context releases resources associated with it, so code should 264 | // call cancel as soon as the operations running in this Context complete: 265 | // 266 | // func slowOperationWithTimeout(ctx context.Context) (Result, error) { 267 | // ctx, cancel := context.WithTimeout(ctx, 100*time.Millisecond) 268 | // defer cancel() // releases resources if slowOperation completes before timeout elapses 269 | // return slowOperation(ctx) 270 | // } 271 | func WithTimeout(parent Context, timeout time.Duration) (Context, CancelFunc) { 272 | return WithDeadline(parent, time.Now().Add(timeout)) 273 | } 274 | 275 | // WithValue returns a copy of parent in which the value associated with key is 276 | // val. 277 | // 278 | // Use context Values only for request-scoped data that transits processes and 279 | // APIs, not for passing optional parameters to functions. 280 | func WithValue(parent Context, key interface{}, val interface{}) Context { 281 | return &valueCtx{parent, key, val} 282 | } 283 | 284 | // A valueCtx carries a key-value pair. It implements Value for that key and 285 | // delegates all other calls to the embedded Context. 286 | type valueCtx struct { 287 | Context 288 | key, val interface{} 289 | } 290 | 291 | func (c *valueCtx) String() string { 292 | return fmt.Sprintf("%v.WithValue(%#v, %#v)", c.Context, c.key, c.val) 293 | } 294 | 295 | func (c *valueCtx) Value(key interface{}) interface{} { 296 | if c.key == key { 297 | return c.val 298 | } 299 | return c.Context.Value(key) 300 | } 301 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/context/withtimeout_test.go: -------------------------------------------------------------------------------- 1 | // Copyright 2014 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package context_test 6 | 7 | import ( 8 | "fmt" 9 | "time" 10 | 11 | "golang.org/x/net/context" 12 | ) 13 | 14 | func ExampleWithTimeout() { 15 | // Pass a context with a timeout to tell a blocking function that it 16 | // should abandon its work after the timeout elapses. 17 | ctx, _ := context.WithTimeout(context.Background(), 100*time.Millisecond) 18 | select { 19 | case <-time.After(200 * time.Millisecond): 20 | fmt.Println("overslept") 21 | case <-ctx.Done(): 22 | fmt.Println(ctx.Err()) // prints "context deadline exceeded" 23 | } 24 | // Output: 25 | // context deadline exceeded 26 | } 27 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/proxy/direct.go: -------------------------------------------------------------------------------- 1 | // Copyright 2011 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package proxy 6 | 7 | import ( 8 | "net" 9 | ) 10 | 11 | type direct struct{} 12 | 13 | // Direct is a direct proxy: one that makes network connections directly. 14 | var Direct = direct{} 15 | 16 | func (direct) Dial(network, addr string) (net.Conn, error) { 17 | return net.Dial(network, addr) 18 | } 19 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/proxy/per_host.go: -------------------------------------------------------------------------------- 1 | // Copyright 2011 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package proxy 6 | 7 | import ( 8 | "net" 9 | "strings" 10 | ) 11 | 12 | // A PerHost directs connections to a default Dialer unless the hostname 13 | // requested matches one of a number of exceptions. 14 | type PerHost struct { 15 | def, bypass Dialer 16 | 17 | bypassNetworks []*net.IPNet 18 | bypassIPs []net.IP 19 | bypassZones []string 20 | bypassHosts []string 21 | } 22 | 23 | // NewPerHost returns a PerHost Dialer that directs connections to either 24 | // defaultDialer or bypass, depending on whether the connection matches one of 25 | // the configured rules. 26 | func NewPerHost(defaultDialer, bypass Dialer) *PerHost { 27 | return &PerHost{ 28 | def: defaultDialer, 29 | bypass: bypass, 30 | } 31 | } 32 | 33 | // Dial connects to the address addr on the given network through either 34 | // defaultDialer or bypass. 35 | func (p *PerHost) Dial(network, addr string) (c net.Conn, err error) { 36 | host, _, err := net.SplitHostPort(addr) 37 | if err != nil { 38 | return nil, err 39 | } 40 | 41 | return p.dialerForRequest(host).Dial(network, addr) 42 | } 43 | 44 | func (p *PerHost) dialerForRequest(host string) Dialer { 45 | if ip := net.ParseIP(host); ip != nil { 46 | for _, net := range p.bypassNetworks { 47 | if net.Contains(ip) { 48 | return p.bypass 49 | } 50 | } 51 | for _, bypassIP := range p.bypassIPs { 52 | if bypassIP.Equal(ip) { 53 | return p.bypass 54 | } 55 | } 56 | return p.def 57 | } 58 | 59 | for _, zone := range p.bypassZones { 60 | if strings.HasSuffix(host, zone) { 61 | return p.bypass 62 | } 63 | if host == zone[1:] { 64 | // For a zone "example.com", we match "example.com" 65 | // too. 66 | return p.bypass 67 | } 68 | } 69 | for _, bypassHost := range p.bypassHosts { 70 | if bypassHost == host { 71 | return p.bypass 72 | } 73 | } 74 | return p.def 75 | } 76 | 77 | // AddFromString parses a string that contains comma-separated values 78 | // specifying hosts that should use the bypass proxy. Each value is either an 79 | // IP address, a CIDR range, a zone (*.example.com) or a hostname 80 | // (localhost). A best effort is made to parse the string and errors are 81 | // ignored. 82 | func (p *PerHost) AddFromString(s string) { 83 | hosts := strings.Split(s, ",") 84 | for _, host := range hosts { 85 | host = strings.TrimSpace(host) 86 | if len(host) == 0 { 87 | continue 88 | } 89 | if strings.Contains(host, "/") { 90 | // We assume that it's a CIDR address like 127.0.0.0/8 91 | if _, net, err := net.ParseCIDR(host); err == nil { 92 | p.AddNetwork(net) 93 | } 94 | continue 95 | } 96 | if ip := net.ParseIP(host); ip != nil { 97 | p.AddIP(ip) 98 | continue 99 | } 100 | if strings.HasPrefix(host, "*.") { 101 | p.AddZone(host[1:]) 102 | continue 103 | } 104 | p.AddHost(host) 105 | } 106 | } 107 | 108 | // AddIP specifies an IP address that will use the bypass proxy. Note that 109 | // this will only take effect if a literal IP address is dialed. A connection 110 | // to a named host will never match an IP. 111 | func (p *PerHost) AddIP(ip net.IP) { 112 | p.bypassIPs = append(p.bypassIPs, ip) 113 | } 114 | 115 | // AddNetwork specifies an IP range that will use the bypass proxy. Note that 116 | // this will only take effect if a literal IP address is dialed. A connection 117 | // to a named host will never match. 118 | func (p *PerHost) AddNetwork(net *net.IPNet) { 119 | p.bypassNetworks = append(p.bypassNetworks, net) 120 | } 121 | 122 | // AddZone specifies a DNS suffix that will use the bypass proxy. A zone of 123 | // "example.com" matches "example.com" and all of its subdomains. 124 | func (p *PerHost) AddZone(zone string) { 125 | if strings.HasSuffix(zone, ".") { 126 | zone = zone[:len(zone)-1] 127 | } 128 | if !strings.HasPrefix(zone, ".") { 129 | zone = "." + zone 130 | } 131 | p.bypassZones = append(p.bypassZones, zone) 132 | } 133 | 134 | // AddHost specifies a hostname that will use the bypass proxy. 135 | func (p *PerHost) AddHost(host string) { 136 | if strings.HasSuffix(host, ".") { 137 | host = host[:len(host)-1] 138 | } 139 | p.bypassHosts = append(p.bypassHosts, host) 140 | } 141 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/proxy/per_host_test.go: -------------------------------------------------------------------------------- 1 | // Copyright 2011 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package proxy 6 | 7 | import ( 8 | "errors" 9 | "net" 10 | "reflect" 11 | "testing" 12 | ) 13 | 14 | type recordingProxy struct { 15 | addrs []string 16 | } 17 | 18 | func (r *recordingProxy) Dial(network, addr string) (net.Conn, error) { 19 | r.addrs = append(r.addrs, addr) 20 | return nil, errors.New("recordingProxy") 21 | } 22 | 23 | func TestPerHost(t *testing.T) { 24 | var def, bypass recordingProxy 25 | perHost := NewPerHost(&def, &bypass) 26 | perHost.AddFromString("localhost,*.zone,127.0.0.1,10.0.0.1/8,1000::/16") 27 | 28 | expectedDef := []string{ 29 | "example.com:123", 30 | "1.2.3.4:123", 31 | "[1001::]:123", 32 | } 33 | expectedBypass := []string{ 34 | "localhost:123", 35 | "zone:123", 36 | "foo.zone:123", 37 | "127.0.0.1:123", 38 | "10.1.2.3:123", 39 | "[1000::]:123", 40 | } 41 | 42 | for _, addr := range expectedDef { 43 | perHost.Dial("tcp", addr) 44 | } 45 | for _, addr := range expectedBypass { 46 | perHost.Dial("tcp", addr) 47 | } 48 | 49 | if !reflect.DeepEqual(expectedDef, def.addrs) { 50 | t.Errorf("Hosts which went to the default proxy didn't match. Got %v, want %v", def.addrs, expectedDef) 51 | } 52 | if !reflect.DeepEqual(expectedBypass, bypass.addrs) { 53 | t.Errorf("Hosts which went to the bypass proxy didn't match. Got %v, want %v", bypass.addrs, expectedBypass) 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/proxy/proxy.go: -------------------------------------------------------------------------------- 1 | // Copyright 2011 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // Package proxy provides support for a variety of protocols to proxy network 6 | // data. 7 | package proxy // import "golang.org/x/net/proxy" 8 | 9 | import ( 10 | "errors" 11 | "net" 12 | "net/url" 13 | "os" 14 | ) 15 | 16 | // A Dialer is a means to establish a connection. 17 | type Dialer interface { 18 | // Dial connects to the given address via the proxy. 19 | Dial(network, addr string) (c net.Conn, err error) 20 | } 21 | 22 | // Auth contains authentication parameters that specific Dialers may require. 23 | type Auth struct { 24 | User, Password string 25 | } 26 | 27 | // FromEnvironment returns the dialer specified by the proxy related variables in 28 | // the environment. 29 | func FromEnvironment() Dialer { 30 | allProxy := os.Getenv("all_proxy") 31 | if len(allProxy) == 0 { 32 | return Direct 33 | } 34 | 35 | proxyURL, err := url.Parse(allProxy) 36 | if err != nil { 37 | return Direct 38 | } 39 | proxy, err := FromURL(proxyURL, Direct) 40 | if err != nil { 41 | return Direct 42 | } 43 | 44 | noProxy := os.Getenv("no_proxy") 45 | if len(noProxy) == 0 { 46 | return proxy 47 | } 48 | 49 | perHost := NewPerHost(proxy, Direct) 50 | perHost.AddFromString(noProxy) 51 | return perHost 52 | } 53 | 54 | // proxySchemes is a map from URL schemes to a function that creates a Dialer 55 | // from a URL with such a scheme. 56 | var proxySchemes map[string]func(*url.URL, Dialer) (Dialer, error) 57 | 58 | // RegisterDialerType takes a URL scheme and a function to generate Dialers from 59 | // a URL with that scheme and a forwarding Dialer. Registered schemes are used 60 | // by FromURL. 61 | func RegisterDialerType(scheme string, f func(*url.URL, Dialer) (Dialer, error)) { 62 | if proxySchemes == nil { 63 | proxySchemes = make(map[string]func(*url.URL, Dialer) (Dialer, error)) 64 | } 65 | proxySchemes[scheme] = f 66 | } 67 | 68 | // FromURL returns a Dialer given a URL specification and an underlying 69 | // Dialer for it to make network requests. 70 | func FromURL(u *url.URL, forward Dialer) (Dialer, error) { 71 | var auth *Auth 72 | if u.User != nil { 73 | auth = new(Auth) 74 | auth.User = u.User.Username() 75 | if p, ok := u.User.Password(); ok { 76 | auth.Password = p 77 | } 78 | } 79 | 80 | switch u.Scheme { 81 | case "socks5": 82 | return SOCKS5("tcp", u.Host, auth, forward) 83 | } 84 | 85 | // If the scheme doesn't match any of the built-in schemes, see if it 86 | // was registered by another package. 87 | if proxySchemes != nil { 88 | if f, ok := proxySchemes[u.Scheme]; ok { 89 | return f(u, forward) 90 | } 91 | } 92 | 93 | return nil, errors.New("proxy: unknown scheme: " + u.Scheme) 94 | } 95 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/proxy/proxy_test.go: -------------------------------------------------------------------------------- 1 | // Copyright 2011 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package proxy 6 | 7 | import ( 8 | "io" 9 | "net" 10 | "net/url" 11 | "strconv" 12 | "sync" 13 | "testing" 14 | ) 15 | 16 | func TestFromURL(t *testing.T) { 17 | endSystem, err := net.Listen("tcp", "127.0.0.1:0") 18 | if err != nil { 19 | t.Fatalf("net.Listen failed: %v", err) 20 | } 21 | defer endSystem.Close() 22 | gateway, err := net.Listen("tcp", "127.0.0.1:0") 23 | if err != nil { 24 | t.Fatalf("net.Listen failed: %v", err) 25 | } 26 | defer gateway.Close() 27 | 28 | var wg sync.WaitGroup 29 | wg.Add(1) 30 | go socks5Gateway(t, gateway, endSystem, socks5Domain, &wg) 31 | 32 | url, err := url.Parse("socks5://user:password@" + gateway.Addr().String()) 33 | if err != nil { 34 | t.Fatalf("url.Parse failed: %v", err) 35 | } 36 | proxy, err := FromURL(url, Direct) 37 | if err != nil { 38 | t.Fatalf("FromURL failed: %v", err) 39 | } 40 | _, port, err := net.SplitHostPort(endSystem.Addr().String()) 41 | if err != nil { 42 | t.Fatalf("net.SplitHostPort failed: %v", err) 43 | } 44 | if c, err := proxy.Dial("tcp", "localhost:"+port); err != nil { 45 | t.Fatalf("FromURL.Dial failed: %v", err) 46 | } else { 47 | c.Close() 48 | } 49 | 50 | wg.Wait() 51 | } 52 | 53 | func TestSOCKS5(t *testing.T) { 54 | endSystem, err := net.Listen("tcp", "127.0.0.1:0") 55 | if err != nil { 56 | t.Fatalf("net.Listen failed: %v", err) 57 | } 58 | defer endSystem.Close() 59 | gateway, err := net.Listen("tcp", "127.0.0.1:0") 60 | if err != nil { 61 | t.Fatalf("net.Listen failed: %v", err) 62 | } 63 | defer gateway.Close() 64 | 65 | var wg sync.WaitGroup 66 | wg.Add(1) 67 | go socks5Gateway(t, gateway, endSystem, socks5IP4, &wg) 68 | 69 | proxy, err := SOCKS5("tcp", gateway.Addr().String(), nil, Direct) 70 | if err != nil { 71 | t.Fatalf("SOCKS5 failed: %v", err) 72 | } 73 | if c, err := proxy.Dial("tcp", endSystem.Addr().String()); err != nil { 74 | t.Fatalf("SOCKS5.Dial failed: %v", err) 75 | } else { 76 | c.Close() 77 | } 78 | 79 | wg.Wait() 80 | } 81 | 82 | func socks5Gateway(t *testing.T, gateway, endSystem net.Listener, typ byte, wg *sync.WaitGroup) { 83 | defer wg.Done() 84 | 85 | c, err := gateway.Accept() 86 | if err != nil { 87 | t.Errorf("net.Listener.Accept failed: %v", err) 88 | return 89 | } 90 | defer c.Close() 91 | 92 | b := make([]byte, 32) 93 | var n int 94 | if typ == socks5Domain { 95 | n = 4 96 | } else { 97 | n = 3 98 | } 99 | if _, err := io.ReadFull(c, b[:n]); err != nil { 100 | t.Errorf("io.ReadFull failed: %v", err) 101 | return 102 | } 103 | if _, err := c.Write([]byte{socks5Version, socks5AuthNone}); err != nil { 104 | t.Errorf("net.Conn.Write failed: %v", err) 105 | return 106 | } 107 | if typ == socks5Domain { 108 | n = 16 109 | } else { 110 | n = 10 111 | } 112 | if _, err := io.ReadFull(c, b[:n]); err != nil { 113 | t.Errorf("io.ReadFull failed: %v", err) 114 | return 115 | } 116 | if b[0] != socks5Version || b[1] != socks5Connect || b[2] != 0x00 || b[3] != typ { 117 | t.Errorf("got an unexpected packet: %#02x %#02x %#02x %#02x", b[0], b[1], b[2], b[3]) 118 | return 119 | } 120 | if typ == socks5Domain { 121 | copy(b[:5], []byte{socks5Version, 0x00, 0x00, socks5Domain, 9}) 122 | b = append(b, []byte("localhost")...) 123 | } else { 124 | copy(b[:4], []byte{socks5Version, 0x00, 0x00, socks5IP4}) 125 | } 126 | host, port, err := net.SplitHostPort(endSystem.Addr().String()) 127 | if err != nil { 128 | t.Errorf("net.SplitHostPort failed: %v", err) 129 | return 130 | } 131 | b = append(b, []byte(net.ParseIP(host).To4())...) 132 | p, err := strconv.Atoi(port) 133 | if err != nil { 134 | t.Errorf("strconv.Atoi failed: %v", err) 135 | return 136 | } 137 | b = append(b, []byte{byte(p >> 8), byte(p)}...) 138 | if _, err := c.Write(b); err != nil { 139 | t.Errorf("net.Conn.Write failed: %v", err) 140 | return 141 | } 142 | } 143 | -------------------------------------------------------------------------------- /vendor/golang.org/x/net/proxy/socks5.go: -------------------------------------------------------------------------------- 1 | // Copyright 2011 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package proxy 6 | 7 | import ( 8 | "errors" 9 | "io" 10 | "net" 11 | "strconv" 12 | ) 13 | 14 | // SOCKS5 returns a Dialer that makes SOCKSv5 connections to the given address 15 | // with an optional username and password. See RFC 1928. 16 | func SOCKS5(network, addr string, auth *Auth, forward Dialer) (Dialer, error) { 17 | s := &socks5{ 18 | network: network, 19 | addr: addr, 20 | forward: forward, 21 | } 22 | if auth != nil { 23 | s.user = auth.User 24 | s.password = auth.Password 25 | } 26 | 27 | return s, nil 28 | } 29 | 30 | type socks5 struct { 31 | user, password string 32 | network, addr string 33 | forward Dialer 34 | } 35 | 36 | const socks5Version = 5 37 | 38 | const ( 39 | socks5AuthNone = 0 40 | socks5AuthPassword = 2 41 | ) 42 | 43 | const socks5Connect = 1 44 | 45 | const ( 46 | socks5IP4 = 1 47 | socks5Domain = 3 48 | socks5IP6 = 4 49 | ) 50 | 51 | var socks5Errors = []string{ 52 | "", 53 | "general failure", 54 | "connection forbidden", 55 | "network unreachable", 56 | "host unreachable", 57 | "connection refused", 58 | "TTL expired", 59 | "command not supported", 60 | "address type not supported", 61 | } 62 | 63 | // Dial connects to the address addr on the network net via the SOCKS5 proxy. 64 | func (s *socks5) Dial(network, addr string) (net.Conn, error) { 65 | switch network { 66 | case "tcp", "tcp6", "tcp4": 67 | default: 68 | return nil, errors.New("proxy: no support for SOCKS5 proxy connections of type " + network) 69 | } 70 | 71 | conn, err := s.forward.Dial(s.network, s.addr) 72 | if err != nil { 73 | return nil, err 74 | } 75 | if err := s.connect(conn, addr); err != nil { 76 | conn.Close() 77 | return nil, err 78 | } 79 | return conn, nil 80 | } 81 | 82 | // connect takes an existing connection to a socks5 proxy server, 83 | // and commands the server to extend that connection to target, 84 | // which must be a canonical address with a host and port. 85 | func (s *socks5) connect(conn net.Conn, target string) error { 86 | host, portStr, err := net.SplitHostPort(target) 87 | if err != nil { 88 | return err 89 | } 90 | 91 | port, err := strconv.Atoi(portStr) 92 | if err != nil { 93 | return errors.New("proxy: failed to parse port number: " + portStr) 94 | } 95 | if port < 1 || port > 0xffff { 96 | return errors.New("proxy: port number out of range: " + portStr) 97 | } 98 | 99 | // the size here is just an estimate 100 | buf := make([]byte, 0, 6+len(host)) 101 | 102 | buf = append(buf, socks5Version) 103 | if len(s.user) > 0 && len(s.user) < 256 && len(s.password) < 256 { 104 | buf = append(buf, 2 /* num auth methods */, socks5AuthNone, socks5AuthPassword) 105 | } else { 106 | buf = append(buf, 1 /* num auth methods */, socks5AuthNone) 107 | } 108 | 109 | if _, err := conn.Write(buf); err != nil { 110 | return errors.New("proxy: failed to write greeting to SOCKS5 proxy at " + s.addr + ": " + err.Error()) 111 | } 112 | 113 | if _, err := io.ReadFull(conn, buf[:2]); err != nil { 114 | return errors.New("proxy: failed to read greeting from SOCKS5 proxy at " + s.addr + ": " + err.Error()) 115 | } 116 | if buf[0] != 5 { 117 | return errors.New("proxy: SOCKS5 proxy at " + s.addr + " has unexpected version " + strconv.Itoa(int(buf[0]))) 118 | } 119 | if buf[1] == 0xff { 120 | return errors.New("proxy: SOCKS5 proxy at " + s.addr + " requires authentication") 121 | } 122 | 123 | if buf[1] == socks5AuthPassword { 124 | buf = buf[:0] 125 | buf = append(buf, 1 /* password protocol version */) 126 | buf = append(buf, uint8(len(s.user))) 127 | buf = append(buf, s.user...) 128 | buf = append(buf, uint8(len(s.password))) 129 | buf = append(buf, s.password...) 130 | 131 | if _, err := conn.Write(buf); err != nil { 132 | return errors.New("proxy: failed to write authentication request to SOCKS5 proxy at " + s.addr + ": " + err.Error()) 133 | } 134 | 135 | if _, err := io.ReadFull(conn, buf[:2]); err != nil { 136 | return errors.New("proxy: failed to read authentication reply from SOCKS5 proxy at " + s.addr + ": " + err.Error()) 137 | } 138 | 139 | if buf[1] != 0 { 140 | return errors.New("proxy: SOCKS5 proxy at " + s.addr + " rejected username/password") 141 | } 142 | } 143 | 144 | buf = buf[:0] 145 | buf = append(buf, socks5Version, socks5Connect, 0 /* reserved */) 146 | 147 | if ip := net.ParseIP(host); ip != nil { 148 | if ip4 := ip.To4(); ip4 != nil { 149 | buf = append(buf, socks5IP4) 150 | ip = ip4 151 | } else { 152 | buf = append(buf, socks5IP6) 153 | } 154 | buf = append(buf, ip...) 155 | } else { 156 | if len(host) > 255 { 157 | return errors.New("proxy: destination hostname too long: " + host) 158 | } 159 | buf = append(buf, socks5Domain) 160 | buf = append(buf, byte(len(host))) 161 | buf = append(buf, host...) 162 | } 163 | buf = append(buf, byte(port>>8), byte(port)) 164 | 165 | if _, err := conn.Write(buf); err != nil { 166 | return errors.New("proxy: failed to write connect request to SOCKS5 proxy at " + s.addr + ": " + err.Error()) 167 | } 168 | 169 | if _, err := io.ReadFull(conn, buf[:4]); err != nil { 170 | return errors.New("proxy: failed to read connect reply from SOCKS5 proxy at " + s.addr + ": " + err.Error()) 171 | } 172 | 173 | failure := "unknown error" 174 | if int(buf[1]) < len(socks5Errors) { 175 | failure = socks5Errors[buf[1]] 176 | } 177 | 178 | if len(failure) > 0 { 179 | return errors.New("proxy: SOCKS5 proxy at " + s.addr + " failed to connect: " + failure) 180 | } 181 | 182 | bytesToDiscard := 0 183 | switch buf[3] { 184 | case socks5IP4: 185 | bytesToDiscard = net.IPv4len 186 | case socks5IP6: 187 | bytesToDiscard = net.IPv6len 188 | case socks5Domain: 189 | _, err := io.ReadFull(conn, buf[:1]) 190 | if err != nil { 191 | return errors.New("proxy: failed to read domain length from SOCKS5 proxy at " + s.addr + ": " + err.Error()) 192 | } 193 | bytesToDiscard = int(buf[0]) 194 | default: 195 | return errors.New("proxy: got unknown address type " + strconv.Itoa(int(buf[3])) + " from SOCKS5 proxy at " + s.addr) 196 | } 197 | 198 | if cap(buf) < bytesToDiscard { 199 | buf = make([]byte, bytesToDiscard) 200 | } else { 201 | buf = buf[:bytesToDiscard] 202 | } 203 | if _, err := io.ReadFull(conn, buf); err != nil { 204 | return errors.New("proxy: failed to read address from SOCKS5 proxy at " + s.addr + ": " + err.Error()) 205 | } 206 | 207 | // Also need to discard the port number 208 | if _, err := io.ReadFull(conn, buf[:2]); err != nil { 209 | return errors.New("proxy: failed to read port from SOCKS5 proxy at " + s.addr + ": " + err.Error()) 210 | } 211 | 212 | return nil 213 | } 214 | --------------------------------------------------------------------------------