github.com/l3x/learn-fp-go@v0.0.0-20171228022418-7639825d0b71/3-functional-techniques/ch08-pipelining/04_buffered_cpus/main.go (about) 1 package main 2 3 import ( 4 "fmt" 5 gc "github.com/go-goodies/go_currency" 6 "runtime" 7 ) 8 9 func main() { 10 orders := GetOrders() 11 numberOfOrders := len(orders) 12 cpus := runtime.NumCPU() 13 runtime.GOMAXPROCS(cpus) 14 input := make(chan Order, cpus) 15 output := make(chan Order, cpus) 16 for i := 0; i < numberOfOrders; i++ { 17 go func() { 18 for order := range input { 19 output <- Pipeline(order) 20 } 21 }() 22 } 23 for _, order := range orders { 24 input <- *order 25 } 26 close(input) 27 for i := 0; i < numberOfOrders; i++ { 28 fmt.Println("The result is:", <-output) 29 } 30 } 31 32 func Pipeline(o Order) Order { 33 o = Authenticate(o) 34 o = Decrypt(o) 35 o = Charge(o) 36 return o 37 } 38 39 40 func Authenticate(o Order) Order { 41 fmt.Printf("Order %d is Authenticated\n", o.OrderNumber) 42 return o 43 } 44 45 func Decrypt(o Order) Order { 46 fmt.Printf("Order %d is Decrypted\n", o.OrderNumber) 47 return o 48 } 49 50 func Charge(o Order) Order { 51 fmt.Printf("Order %d is Charged\n", o.OrderNumber) 52 return o 53 } 54 55 type Order struct { 56 OrderNumber int 57 IsValid bool 58 Credentials string 59 CCardNumber string 60 CCardExpDate string 61 LineItems []LineItem 62 } 63 64 type LineItem struct { 65 Description string 66 Count int 67 PriceUSD gc.USD 68 } 69 func GetOrders() []*Order { 70 71 order1 := &Order{ 72 10001, 73 true, 74 "alice,secret", 75 "7b/HWvtIB9a16AYk+Yv6WWwer3GFbxpjoR+GO9iHIYY=", 76 "0922", 77 []LineItem{ 78 {"Apples", 1, gc.USD{4, 50}}, 79 {"Oranges", 4, gc.USD{12, 00}}, 80 }, 81 } 82 83 order2 := &Order{ 84 10002, 85 true, 86 "bob,secret", 87 "EOc3kF/OmxY+dRCaYRrey8h24QoGzVU0/T2QKVCHb1Q=", 88 "0123", 89 []LineItem{ 90 {"Milk", 2, gc.USD{8, 00}}, 91 {"Sugar", 1, gc.USD{2, 25}}, 92 {"Salt", 3, gc.USD{3, 75}}, 93 }, 94 } 95 orders := []*Order{order1, order2} 96 return orders 97 }