@@ -62,9 +62,20 @@ func TestLargeTextMessage(t *testing.T) {
6262
6363 // The message is still left on the queue since it failed to be received successfully.
6464
65- // Since the buffer size is configured using the ConnectionFactoy we will
66- // create a second connection in order to successfully retrieve the message.
67- cf .ReceiveBufferSize = len (txtOver32kb ) + 50
65+ // Use a special attribute of the returned exception to look up what the actual length of the
66+ // message is, so that we can correctly increase the buffer size in order to receive the message.
67+ switch jmsExc := errRcv .(type ) {
68+ case jms20subset.JMSExceptionImpl :
69+ realMessageLength := jmsExc .GetMessageLength ()
70+ assert .Equal (t , len (txtOver32kb ), realMessageLength ) // check it matches the original (long) length
71+
72+ // Since the buffer size is configured using the ConnectionFactory we will
73+ // create a second connection in order to successfully retrieve the message.
74+ cf .ReceiveBufferSize = realMessageLength
75+
76+ default :
77+ assert .Fail (t , "Got something other than a JMSExceptionImpl" )
78+ }
6879
6980 context2 , ctxErr2 := cf .CreateContext ()
7081 assert .Nil (t , ctxErr2 )
@@ -78,7 +89,7 @@ func TestLargeTextMessage(t *testing.T) {
7889 defer consumer2 .Close ()
7990 }
8091
81- rcvMsg2 , errRcv2 := consumer2 .ReceiveNoWait ()
92+ rcvMsg2 , errRcv2 := consumer2 .ReceiveNoWait () // receive the message using the correct (larger) buffer size
8293 assert .Nil (t , errRcv2 )
8394 assert .NotNil (t , rcvMsg2 )
8495
@@ -134,9 +145,20 @@ func TestLargeReceiveStringBodyTextMessage(t *testing.T) {
134145
135146 // The message is still left on the queue since it failed to be received successfully.
136147
137- // Since the buffer size is configured using the ConnectionFactoy we will
138- // create a second connection in order to successfully retrieve the message.
139- cf .ReceiveBufferSize = len (txtOver32kb ) + 50
148+ // Use a special attribute of the returned exception to look up what the actual length of the
149+ // message is, so that we can correctly increase the buffer size in order to receive the message.
150+ switch jmsExc := errRcv .(type ) {
151+ case jms20subset.JMSExceptionImpl :
152+ realMessageLength := jmsExc .GetMessageLength ()
153+ assert .Equal (t , len (txtOver32kb ), realMessageLength ) // check it matches the original (long) length
154+
155+ // Since the buffer size is configured using the ConnectionFactory we will
156+ // create a second connection in order to successfully retrieve the message.
157+ cf .ReceiveBufferSize = realMessageLength
158+
159+ default :
160+ assert .Fail (t , "Got something other than a JMSExceptionImpl" )
161+ }
140162
141163 context2 , ctxErr2 := cf .CreateContext ()
142164 assert .Nil (t , ctxErr2 )
@@ -200,9 +222,20 @@ func TestLargeBytesMessage(t *testing.T) {
200222
201223 // The message is still left on the queue since it failed to be received successfully.
202224
203- // Since the buffer size is configured using the ConnectionFactoy we will
204- // create a second connection in order to successfully retrieve the message.
205- cf .ReceiveBufferSize = len (bytesOver32kb ) + 50
225+ // Use a special attribute of the returned exception to look up what the actual length of the
226+ // message is, so that we can correctly increase the buffer size in order to receive the message.
227+ switch jmsExc := errRcv .(type ) {
228+ case jms20subset.JMSExceptionImpl :
229+ realMessageLength := jmsExc .GetMessageLength ()
230+ assert .Equal (t , len (txtOver32kb ), realMessageLength ) // check it matches the original (long) length
231+
232+ // Since the buffer size is configured using the ConnectionFactory we will
233+ // create a second connection in order to successfully retrieve the message.
234+ cf .ReceiveBufferSize = realMessageLength
235+
236+ default :
237+ assert .Fail (t , "Got something other than a JMSExceptionImpl" )
238+ }
206239
207240 context2 , ctxErr2 := cf .CreateContext ()
208241 assert .Nil (t , ctxErr2 )
@@ -273,9 +306,20 @@ func TestLargeReceiveBytesBodyBytesMessage(t *testing.T) {
273306
274307 // The message is still left on the queue since it failed to be received successfully.
275308
276- // Since the buffer size is configured using the ConnectionFactoy we will
277- // create a second connection in order to successfully retrieve the message.
278- cf .ReceiveBufferSize = len (bytesOver32kb ) + 50
309+ // Use a special attribute of the returned exception to look up what the actual length of the
310+ // message is, so that we can correctly increase the buffer size in order to receive the message.
311+ switch jmsExc := errRcv .(type ) {
312+ case jms20subset.JMSExceptionImpl :
313+ realMessageLength := jmsExc .GetMessageLength ()
314+ assert .Equal (t , len (txtOver32kb ), realMessageLength ) // check it matches the original (long) length
315+
316+ // Since the buffer size is configured using the ConnectionFactory we will
317+ // create a second connection in order to successfully retrieve the message.
318+ cf .ReceiveBufferSize = realMessageLength
319+
320+ default :
321+ assert .Fail (t , "Got something other than a JMSExceptionImpl" )
322+ }
279323
280324 context2 , ctxErr2 := cf .CreateContext ()
281325 assert .Nil (t , ctxErr2 )
@@ -295,6 +339,168 @@ func TestLargeReceiveBytesBodyBytesMessage(t *testing.T) {
295339
296340}
297341
342+ /*
343+ * Test receiving a truncated text message, where the body of the message is larger than the receive buffer.
344+ */
345+ func TestTruncatedTextMessage (t * testing.T ) {
346+
347+ // Loads CF parameters from connection_info.json and applicationApiKey.json in the Downloads directory
348+ cf , cfErr := mqjms .CreateConnectionFactoryFromDefaultJSONFiles ()
349+ cf .ReceiveBufferSize = 1024
350+ cf .AcceptTruncatedMessage = true
351+ assert .Nil (t , cfErr )
352+
353+ // Creates a connection to the queue manager, using defer to close it automatically
354+ // at the end of the function (if it was created successfully)
355+ context , ctxErr := cf .CreateContext ()
356+ assert .Nil (t , ctxErr )
357+ if context != nil {
358+ defer context .Close ()
359+ }
360+
361+ // Get a long text string over 32kb in length
362+ txtOver32kb := getStringOver32kb ()
363+
364+ // Create a TextMessage with it
365+ msg := context .CreateTextMessageWithString (txtOver32kb )
366+
367+ // Now send the message and get it back again.
368+ queue := context .CreateQueue ("DEV.QUEUE.1" )
369+ errSend := context .CreateProducer ().SetTimeToLive (5000 ).Send (queue , msg )
370+ assert .Nil (t , errSend )
371+
372+ consumer , errCons := context .CreateConsumer (queue ) // with 1kb buffer size as applied at the beginning of this test
373+ assert .Nil (t , errCons )
374+ if consumer != nil {
375+ defer consumer .Close ()
376+ }
377+
378+ // Since we have set the flag to allow a truncated message to be returned, this will pass
379+ // but will only return the first 1024 bytes (cf.ReceiveBufferSize) of the message.
380+ truncMsg , errRcv := consumer .ReceiveNoWait ()
381+ assert .NotNil (t , errRcv )
382+ assert .Equal (t , "MQRC_TRUNCATED_MSG_ACCEPTED" , errRcv .GetReason ())
383+ assert .Equal (t , "2079" , errRcv .GetErrorCode ())
384+
385+ assert .NotNil (t , truncMsg ) // We have received the message, but it is truncated.
386+
387+ switch txtTruncMsg := truncMsg .(type ) {
388+ case jms20subset.TextMessage :
389+ receivedTxt := txtTruncMsg .GetText ()
390+ assert .Equal (t , cf .ReceiveBufferSize , len (* receivedTxt ))
391+ default :
392+ assert .Fail (t , "Got something other than a text message" )
393+ }
394+
395+ // Use a special attribute of the returned exception to look up what the actual length of the
396+ // message is, so that we can tidy up the message (read successfully) in the event the previous
397+ // step failed.
398+ switch jmsExc := errRcv .(type ) {
399+ case jms20subset.JMSExceptionImpl :
400+ realMessageLength := jmsExc .GetMessageLength ()
401+ assert .Equal (t , len (txtOver32kb ), realMessageLength ) // check it matches the original (long) length
402+
403+ // Since the buffer size is configured using the ConnectionFactory we will
404+ // create a second connection in order to successfully retrieve the message.
405+ cf .ReceiveBufferSize = realMessageLength
406+
407+ default :
408+ assert .Fail (t , "Got something other than a JMSExceptionImpl" )
409+ }
410+
411+ context2 , ctxErr2 := cf .CreateContext ()
412+ assert .Nil (t , ctxErr2 )
413+ if context2 != nil {
414+ defer context2 .Close ()
415+ }
416+
417+ consumer2 , errCons2 := context2 .CreateConsumer (queue )
418+ assert .Nil (t , errCons2 )
419+ if consumer2 != nil {
420+ defer consumer2 .Close ()
421+ }
422+
423+ // If the first part of this text was successful then there should be no message to receive.
424+ tidyMsg , tidyErr := consumer2 .ReceiveNoWait ()
425+ assert .Nil (t , tidyErr )
426+ assert .Nil (t , tidyMsg )
427+
428+ }
429+
430+ /*
431+ * Test receiving a truncated bytes message, where the body of the message is larger than the receive buffer.
432+ */
433+ func TestTruncatedBytesMessage (t * testing.T ) {
434+
435+ // Loads CF parameters from connection_info.json and applicationApiKey.json in the Downloads directory
436+ cf , cfErr := mqjms .CreateConnectionFactoryFromDefaultJSONFiles ()
437+ cf .ReceiveBufferSize = 1024
438+ cf .AcceptTruncatedMessage = true
439+ assert .Nil (t , cfErr )
440+
441+ // Creates a connection to the queue manager, using defer to close it automatically
442+ // at the end of the function (if it was created successfully)
443+ context , ctxErr := cf .CreateContext ()
444+ assert .Nil (t , ctxErr )
445+ if context != nil {
446+ defer context .Close ()
447+ }
448+
449+ // Get a long text string over 32kb in length
450+ txtOver32kb := getStringOver32kb ()
451+ bytesOver32kb := []byte (txtOver32kb )
452+
453+ // Create a TextMessage with it
454+ msg := context .CreateBytesMessageWithBytes (bytesOver32kb )
455+
456+ // Now send the message and get it back again.
457+ queue := context .CreateQueue ("DEV.QUEUE.1" )
458+ errSend := context .CreateProducer ().SetTimeToLive (5000 ).Send (queue , msg )
459+ assert .Nil (t , errSend )
460+
461+ consumer , errCons := context .CreateConsumer (queue ) // with 1kb buffer size as applied at the beginning of this test
462+ assert .Nil (t , errCons )
463+ if consumer != nil {
464+ defer consumer .Close ()
465+ }
466+
467+ // Since we have set the flag to allow a truncated message to be returned, this will pass
468+ // but will only return the first 1024 bytes (cf.ReceiveBufferSize) of the message.
469+ truncMsg , errRcv := consumer .ReceiveNoWait ()
470+ assert .NotNil (t , errRcv )
471+ assert .Equal (t , "MQRC_TRUNCATED_MSG_ACCEPTED" , errRcv .GetReason ())
472+ assert .Equal (t , "2079" , errRcv .GetErrorCode ())
473+
474+ assert .NotNil (t , truncMsg ) // We have received the message, but it is truncated.
475+
476+ switch bytesTruncMsg := truncMsg .(type ) {
477+ case jms20subset.BytesMessage :
478+ receivedBytes := bytesTruncMsg .ReadBytes ()
479+ assert .Equal (t , cf .ReceiveBufferSize , len (* receivedBytes ))
480+ default :
481+ assert .Fail (t , "Got something other than a bytes message" )
482+ }
483+
484+ // Make sure we tidy up in case the previous part of the test failed.
485+ cf .ReceiveBufferSize = len (txtOver32kb ) + 50
486+
487+ context2 , ctxErr2 := cf .CreateContext ()
488+ assert .Nil (t , ctxErr2 )
489+ if context2 != nil {
490+ defer context2 .Close ()
491+ }
492+
493+ consumer2 , errCons2 := context2 .CreateConsumer (queue )
494+ assert .Nil (t , errCons2 )
495+ if consumer2 != nil {
496+ defer consumer2 .Close ()
497+ }
498+
499+ // Attempt to receive a message, and don't worry whether it does or not.
500+ consumer2 .ReceiveNoWait ()
501+
502+ }
503+
298504func getStringOver32kb () string {
299505
300506 // Build a text string which is over 32KB (in a not very efficient way!)
0 commit comments