github.com/graybobo/golang.org-package-offline-cache@v0.0.0-20200626051047-6608995c132f/x/talks/2013/distsys/addr4.go (about) 1 // +build OMIT 2 3 package main 4 5 import ( 6 "fmt" 7 "math/rand" 8 "time" 9 ) 10 11 func lookup() { 12 const max = 2 13 14 done := make(chan bool, len(worklist)) 15 limit := make(chan bool, max) 16 17 for _, w := range worklist { 18 go func(w *Work) { 19 limit <- true 20 w.addrs, w.err = LookupHost(w.host) 21 <-limit 22 done <- true 23 }(w) 24 } 25 26 for i := 0; i < len(worklist); i++ { 27 <-done 28 } 29 } 30 31 func main() { 32 rand.Seed(time.Now().UnixNano()) 33 34 t0 := time.Now() 35 lookup() 36 37 fmt.Printf("\n") 38 for _, w := range worklist { 39 if w.err != nil { 40 fmt.Printf("%s: error: %v\n", w.host, w.err) 41 continue 42 } 43 fmt.Printf("%s: %v\n", w.host, w.addrs) 44 } 45 fmt.Printf("total lookup time: %.3f seconds\n", time.Since(t0).Seconds()) 46 } 47 48 var worklist = []*Work{ 49 {host: "fast.com"}, 50 {host: "slow.com"}, 51 {host: "fast.missing.com"}, 52 {host: "slow.missing.com"}, 53 } 54 55 type Work struct { 56 host string 57 addrs []string 58 err error 59 } 60 61 func LookupHost(name string) (addrs []string, err error) { 62 t0 := time.Now() 63 defer func() { 64 fmt.Printf("lookup %s: %.3f seconds\n", name, time.Since(t0).Seconds()) 65 }() 66 h := hosts[name] 67 if h == nil { 68 h = failure 69 } 70 return h(name) 71 } 72 73 type resolver func(string) ([]string, error) 74 75 var hosts = map[string]resolver{ 76 "fast.com": delay(10*time.Millisecond, fixedAddrs("10.0.0.1")), 77 "slow.com": delay(2*time.Second, fixedAddrs("10.0.0.4")), 78 "fast.missing.com": delay(10*time.Millisecond, failure), 79 "slow.missing.com": delay(2*time.Second, failure), 80 } 81 82 func fixedAddrs(addrs ...string) resolver { 83 return func(string) ([]string, error) { 84 return addrs, nil 85 } 86 } 87 88 func delay(d time.Duration, f resolver) resolver { 89 return func(name string) ([]string, error) { 90 time.Sleep(d/2 + time.Duration(rand.Int63n(int64(d/2)))) 91 return f(name) 92 } 93 } 94 95 func failure(name string) ([]string, error) { 96 return nil, fmt.Errorf("unknown host %v", name) 97 }