github.com/alwitt/goutils@v0.6.4/bus_test.go (about) 1 package goutils 2 3 import ( 4 "context" 5 "testing" 6 "time" 7 8 "github.com/apex/log" 9 "github.com/google/uuid" 10 "github.com/stretchr/testify/assert" 11 ) 12 13 func TestMessageTopicOnePubOneSub(t *testing.T) { 14 assert := assert.New(t) 15 log.SetLevel(log.DebugLevel) 16 17 ctxt, cancel := context.WithCancel(context.Background()) 18 defer cancel() 19 20 testTopic, err := getNewMessageTopicInstance( 21 ctxt, uuid.NewString(), log.Fields{"unit-testiung": "testing"}, 22 ) 23 assert.Nil(err) 24 25 type testMsg struct { 26 msg string 27 } 28 29 // Case 0: create subscription 30 subscriber := uuid.NewString() 31 subChan, err := testTopic.CreateSubscription(ctxt, subscriber, 0) 32 assert.Nil(err) 33 34 // Case 1: blocking publish 35 { 36 test := testMsg{msg: uuid.NewString()} 37 complete := make(chan bool, 1) 38 39 lclCtxt, lclCancel := context.WithTimeout(ctxt, time.Millisecond*100) 40 41 go func() { 42 assert.Nil(testTopic.Publish(lclCtxt, &test, 0)) 43 complete <- true 44 }() 45 46 select { 47 case <-lclCtxt.Done(): 48 assert.False(true, "msg timed out") 49 case msg, ok := <-subChan: 50 assert.True(ok) 51 asString, ok := msg.(*testMsg) 52 assert.True(ok) 53 assert.Equal(test.msg, asString.msg) 54 } 55 56 select { 57 case <-lclCtxt.Done(): 58 assert.False(true, "test timed out") 59 case <-complete: 60 break 61 } 62 63 lclCancel() 64 } 65 66 // Case 2: non-blocking publish, but not receiving 67 { 68 test := testMsg{msg: uuid.NewString()} 69 70 lclCtxt, lclCancel := context.WithTimeout(ctxt, time.Millisecond*100) 71 72 assert.Nil(testTopic.Publish(lclCtxt, &test, time.Millisecond*10)) 73 74 lclCancel() 75 } 76 77 // Case 3: non-blocking publish, prepared to receive 78 { 79 test := testMsg{msg: uuid.NewString()} 80 complete := make(chan bool, 1) 81 82 lclCtxt, lclCancel := context.WithTimeout(ctxt, time.Millisecond*100) 83 84 go func() { 85 assert.Nil(testTopic.Publish(lclCtxt, &test, time.Millisecond*10)) 86 complete <- true 87 }() 88 89 select { 90 case <-lclCtxt.Done(): 91 assert.False(true, "msg timed out") 92 case msg, ok := <-subChan: 93 assert.True(ok) 94 asString, ok := msg.(*testMsg) 95 assert.True(ok) 96 assert.Equal(test.msg, asString.msg) 97 } 98 99 select { 100 case <-lclCtxt.Done(): 101 assert.False(true, "test timed out") 102 case <-complete: 103 break 104 } 105 106 lclCancel() 107 } 108 109 // Delete subscription 110 assert.Nil(testTopic.DeleteSubscription(ctxt, subscriber)) 111 } 112 113 func TestMessageTopicOnePubMultiSub(t *testing.T) { 114 assert := assert.New(t) 115 log.SetLevel(log.DebugLevel) 116 117 ctxt, cancel := context.WithCancel(context.Background()) 118 defer cancel() 119 120 testTopic, err := getNewMessageTopicInstance( 121 ctxt, uuid.NewString(), log.Fields{"unit-testiung": "testing"}, 122 ) 123 assert.Nil(err) 124 125 type testMsg struct { 126 msg string 127 } 128 129 // Case 0: create subscriptions 130 subNames := []string{} 131 subs := map[string]chan interface{}{} 132 for itr := 0; itr < 2; itr++ { 133 subscriber := uuid.NewString() 134 subChan, err := testTopic.CreateSubscription(ctxt, subscriber, 0) 135 assert.Nil(err) 136 subs[subscriber] = subChan 137 subNames = append(subNames, subscriber) 138 } 139 140 // Case 1: blocking publish 141 { 142 test := testMsg{msg: uuid.NewString()} 143 complete := make(chan bool, 3) 144 145 lclCtxt, lclCancel := context.WithTimeout(ctxt, time.Millisecond*100) 146 147 go func() { 148 assert.Nil(testTopic.Publish(lclCtxt, &test, 0)) 149 complete <- true 150 }() 151 152 h := func(channel chan interface{}) { 153 select { 154 case <-lclCtxt.Done(): 155 assert.False(true, "msg timed out") 156 case msg, ok := <-channel: 157 assert.True(ok) 158 asString, ok := msg.(*testMsg) 159 assert.True(ok) 160 assert.Equal(test.msg, asString.msg) 161 complete <- true 162 } 163 } 164 165 for _, channel := range subs { 166 go h(channel) 167 } 168 169 for itr := 0; itr < 3; itr++ { 170 select { 171 case <-lclCtxt.Done(): 172 assert.False(true, "test timed out") 173 case <-complete: 174 } 175 } 176 177 lclCancel() 178 } 179 180 // Case 2: non-blocking publish, but one not receiving 181 { 182 test := testMsg{msg: uuid.NewString()} 183 complete := make(chan bool, 1) 184 185 lclCtxt, lclCancel := context.WithTimeout(ctxt, time.Millisecond*100) 186 187 go func() { 188 assert.Nil(testTopic.Publish(lclCtxt, &test, time.Millisecond*10)) 189 complete <- true 190 }() 191 192 select { 193 case <-lclCtxt.Done(): 194 assert.False(true, "msg timed out") 195 case msg, ok := <-subs[subNames[0]]: 196 assert.True(ok) 197 asString, ok := msg.(*testMsg) 198 assert.True(ok) 199 assert.Equal(test.msg, asString.msg) 200 } 201 202 select { 203 case <-lclCtxt.Done(): 204 assert.False(true, "test timed out") 205 case <-complete: 206 } 207 208 select { 209 case <-lclCtxt.Done(): 210 break 211 case <-subs[subNames[1]]: 212 assert.False(true, "should not have received a message") 213 } 214 215 lclCancel() 216 } 217 218 // Case 3: non-blocking publish, prepared to receive 219 { 220 test := testMsg{msg: uuid.NewString()} 221 complete := make(chan bool, 3) 222 223 lclCtxt, lclCancel := context.WithTimeout(ctxt, time.Millisecond*100) 224 225 go func() { 226 assert.Nil(testTopic.Publish(lclCtxt, &test, time.Millisecond*10)) 227 complete <- true 228 }() 229 230 h := func(channel chan interface{}) { 231 select { 232 case <-lclCtxt.Done(): 233 assert.False(true, "msg timed out") 234 case msg, ok := <-channel: 235 assert.True(ok) 236 asString, ok := msg.(*testMsg) 237 assert.True(ok) 238 assert.Equal(test.msg, asString.msg) 239 complete <- true 240 } 241 } 242 243 for _, channel := range subs { 244 go h(channel) 245 } 246 247 for itr := 0; itr < 3; itr++ { 248 select { 249 case <-lclCtxt.Done(): 250 assert.False(true, "test timed out") 251 case <-complete: 252 } 253 } 254 255 lclCancel() 256 } 257 258 // Delete subscription 259 for subName := range subs { 260 assert.Nil(testTopic.DeleteSubscription(ctxt, subName)) 261 } 262 } 263 264 func TestMessageBus(t *testing.T) { 265 assert := assert.New(t) 266 log.SetLevel(log.DebugLevel) 267 268 ctxt, cancel := context.WithCancel(context.Background()) 269 defer cancel() 270 271 testBus, err := GetNewMessageBusInstance(ctxt, log.Fields{"unit-testing": "testing"}) 272 assert.Nil(err) 273 274 // Case 0: create topic 275 topic := uuid.NewString() 276 { 277 _, err := testBus.CreateTopic(ctxt, topic, log.Fields{}) 278 assert.Nil(err) 279 } 280 // Create same topic again 281 { 282 _, err := testBus.CreateTopic(ctxt, topic, log.Fields{}) 283 assert.Nil(err) 284 } 285 286 // Case 1: get topic 287 { 288 _, err := testBus.GetTopic(ctxt, topic) 289 assert.Nil(err) 290 } 291 // Get unknown topic 292 { 293 _, err := testBus.GetTopic(ctxt, uuid.NewString()) 294 assert.NotNil(err) 295 } 296 297 // Case 2: delete topic 298 assert.Nil(testBus.DeleteTopic(ctxt, topic)) 299 // Delete unknown topic 300 assert.NotNil(testBus.DeleteTopic(ctxt, uuid.NewString())) 301 }