github.com/angenalZZZ/gofunc@v0.0.0-20210507121333-48ff1be3917b/rpc/nats/subscribers.go (about) 1 package nats 2 3 import ( 4 "log" 5 "syscall" 6 "time" 7 8 "github.com/angenalZZZ/gofunc/f" 9 "github.com/nats-io/nats.go" 10 ) 11 12 // Subscribers subscriber list for a Client Connect. 13 type Subscribers struct { 14 *nats.Conn 15 sub []*nats.Subscription 16 Subj []string 17 Hand []nats.MsgHandler 18 Since *f.TimeStamp 19 MsgLimit int // sets the limits for pending messages for this subscription. 20 BytesLimit int // sets the limits for a message's bytes for this subscription. 21 } 22 23 // NewSubscribers Create subscriber list for a Client Connect. 24 func NewSubscribers(nc *nats.Conn, subject []string, msgHandler []nats.MsgHandler) *Subscribers { 25 sub := &Subscribers{ 26 Conn: nc, 27 Subj: subject, 28 Hand: msgHandler, 29 Since: f.TimeFrom(time.Now(), true), 30 MsgLimit: 100000000, // pending messages: 100 million 31 BytesLimit: 1048576, // a message's size: 1MB 32 } 33 return sub 34 } 35 36 // Run runtime to end your application. 37 func (sub *Subscribers) Run(waitFunc ...func()) { 38 var err error 39 40 // Handle panic. 41 defer func() { 42 err := recover() 43 if err != nil { 44 Log.Error().Msgf("[nats] run error > %v", err) 45 } else { 46 Log.Warn().Msg("[nats] stop receive new data") 47 } 48 49 // Unsubscribe will remove interest in the given subject. 50 for _, s := range sub.sub { 51 _ = s.Unsubscribe() 52 } 53 // Drain connection (Preferred for responders), Close() not needed if this is called. 54 _ = sub.Conn.Drain() 55 56 // os.Exit(1) 57 if err != nil { 58 log.Fatal(err) 59 } 60 }() 61 62 // Async Subscriber. 63 sub.sub = make([]*nats.Subscription, len(sub.Subj)) 64 for i, subj := range sub.Subj { 65 sub.sub[i], err = sub.Conn.Subscribe(subj, sub.Hand[i]) 66 67 // Set listening. 68 SubscribeErrorHandle(sub.sub[i], true, err) 69 if err != nil { 70 log.Fatal(err) 71 } 72 73 // Set pending limits. 74 SubscribeLimitHandle(sub.sub[i], sub.MsgLimit, sub.BytesLimit) 75 76 // Flush connection to server, returns when all messages have been processed. 77 FlushAndCheckLastError(sub.Conn) 78 } 79 80 if len(waitFunc) > 0 { 81 waitFunc[0]() 82 return 83 } 84 85 // Pass the signals you want to end your application. 86 death := f.NewDeath(syscall.SIGINT, syscall.SIGTERM) 87 // When you want to block for shutdown signals. 88 death.WaitForDeathWithFunc(func() { 89 Log.Error().Msg("[nats] forced to shutdown.") 90 }) 91 }