Author |
Message
|
fishlips |
Posted: Thu Mar 01, 2012 4:14 am Post subject: Receiving IBytesMessages via .NET interface - error 2010 |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
I've written an application that connects to queues and receives messages using the .NET Interface.
I’m hoping you can help me with an MQ error that I’m getting. I’ve tested my VB.NET code using IBytesMessage type and found that this enabled me to download ZIPs that I had uploaded via RFHUtil.
Unfortunately, there are now messages on our queue TAS.TEIM.ESSDATA that my code doesn’t seem to be able to read. The code fails on these messages with error 2010 (07DA) (RC2010): MQRC_DATA_LENGTH_ERROR
Do you have any idea as to why the code fails? It manages to successfully connect to the queue, but the Consumer object throws the exception when it calls the ReceiveNoWait method to receive the message into a IMessage object.
Here's the Code:
Code: |
Dim blnErrorOccurred As Boolean = False
Dim Consumer As IMessageConsumer = Nothing
Dim session As ISession = Nothing
Dim destination As IDestination = Nothing
Dim connection As IConnection = Nothing
Dim cfConnectionFactory As IConnectionFactory = Nothing
Try
'Create an XMS Factory Object
Dim FactoryFactory As XMSFactoryFactory = XMSFactoryFactory.GetInstance(XMSC.CT_WMQ)
'Create a ConnectionFactory Object
cfConnectionFactory = FactoryFactory.CreateConnectionFactory()
'this variable will contain the full path of any file downloaded from MQ
Dim strMQMessageOutputFileDestinationFilePath As String = ""
'This variable will be used to evaluate whether the MQ Message Output file exists
Dim fiMQMessageOutputFile As FileInfo = Nothing
'Set various Connection Factory properties
cfConnectionFactory.SetStringProperty(XMSC.WMQ_HOST_NAME, Me.HostName)
cfConnectionFactory.SetIntProperty(XMSC.WMQ_PORT, 1414)
cfConnectionFactory.SetStringProperty(XMSC.WMQ_CHANNEL, "SYSTEM.DEF.SVRCONN")
cfConnectionFactory.SetIntProperty(XMSC.WMQ_CONNECTION_MODE, XMSC.WMQ_CM_CLIENT)
cfConnectionFactory.SetStringProperty(XMSC.WMQ_QUEUE_MANAGER, Me.QueueManager)
cfConnectionFactory.SetIntProperty(XMSC.WMQ_BROKER_VERSION, 0)
'Create a new Iconnection object via the Connection Factory
connection = cfConnectionFactory.CreateConnection()
'Create a sesion via the Connection Object, using ClientAcknowledge mode
'ClientAcknowledge is being used because it allows us to control precisely
'when a message should be removed from the queue
session = connection.CreateSession(False, AcknowledgeMode.ClientAcknowledge)
'Create a destination using the Session Object
destination = session.CreateQueue(Me.mstrDestinationURI)
destination.SetIntProperty(XMSC.DELIVERY_MODE, 1)
'Create a consumer using the Session & Destination Objects
Consumer = session.CreateConsumer(destination)
connection.Start()
'IMessage is the base class that is returned from the Consumer's Receive method
Dim recvMsg As IMessage = Nothing
Do
' Retrieve message from Queue, using the XML file's specified time out
'ReceiveNoWait will run until
recvMsg = Consumer.ReceiveNoWait
If not recvMsg Is Nothing Then
If TypeOf (recvMsg) Is IBytesMessage Then
'Binary Message
Dim msg As IBytesMessage = CType(recvMsg, IBytesMessage)
Dim buffer(msg.BodyLength) As Byte
msg.ReadBytes(buffer)
Dim content As String = Text.Encoding.UTF8.GetString(buffer)
'The PrepareDestinationFile Function will generate a unique file name for the new file
'and ensure that the file does not already exist on the drive
strMQMessageOutputFileDestinationFilePath = PrepareDestinationFile()
'A FileStream object is needed to write a binary array to a file
Dim fsZipFile As FileStream = New FileStream(strMQMessageOutputFileDestinationFilePath, FileMode.Create)
'Write the contents of the Byte Array to the File via the FileStream object
fsZipFile.Write(buffer, 0, buffer.Length)
fsZipFile.Close()
End If
End If
Loop
'Close connection to MQ
connection.Close()
Catch ex As Exception
blnErrorOccurred = True
Finally
'destroy all objects
If Not Consumer Is Nothing Then
Consumer = Nothing
End If
If Not destination Is Nothing Then
destination = Nothing
End If
If Not session Is Nothing Then
session = Nothing
End If
If Not connection Is Nothing Then
connection = Nothing
End If
If Not cfConnectionFactory Is Nothing Then
cfConnectionFactory = Nothing
End If
End Try
|
Any help you can provide would be much appreciated |
|
Back to top |
|
 |
JasonE |
Posted: Thu Mar 01, 2012 7:55 am Post subject: |
|
|
Grand Master
Joined: 03 Nov 2003 Posts: 1220 Location: Hursley
|
What's the size of the messages causing you problems? |
|
Back to top |
|
 |
fishlips |
Posted: Thu Mar 01, 2012 8:18 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
The messages are between 5MB and 72MB. |
|
Back to top |
|
 |
mqjeff |
Posted: Thu Mar 01, 2012 8:20 am Post subject: |
|
|
Grand Master
Joined: 25 Jun 2008 Posts: 17447
|
Are all of the needed MQ objects that are involved configured to support a MAXMSGLN bigger than 72MB?
This includes the channel that is in use between the receiving application and the queue manager. |
|
Back to top |
|
 |
fishlips |
Posted: Thu Mar 01, 2012 8:31 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
The queue's max message length is 5,248,800, and the channel's max message length is 104,857,600.
WRT to the various MQ objects involved, I'm not so sure. As you can see, the main objects in use are:
- XMSfactoryFactory
- IConnectionFactory
- IConnection
- ISession
- IDestination
- IMessageConsumer
Which of these objects have a MAXMSGLN property that I can set? |
|
Back to top |
|
 |
mqjeff |
Posted: Thu Mar 01, 2012 8:42 am Post subject: |
|
|
Grand Master
Joined: 25 Jun 2008 Posts: 17447
|
I meant "objects as defined in MQ" not ".NET instances of MQ Classes", sorry.
You need to ensure that the queue manager, queue, SVRCONN and CLNTCONN in use all have MAXMSGLN of 104857600. |
|
Back to top |
|
 |
fishlips |
Posted: Thu Mar 01, 2012 8:50 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
mqjeff wrote: |
I meant "objects as defined in MQ" not ".NET instances of MQ Classes", sorry.
You need to ensure that the queue manager, queue, SVRCONN and CLNTCONN in use all have MAXMSGLN of 104857600. |
Ok, well the queue manager's MAXMSGLN = 104,857,600
The queue's MAXMSGLN is 52,428,800
The AMC.SVRCONN channel's MAXMSGLN is 104,857,600
I'm not sure if we have a CLNTCONN. Do you think it could be because the queue's MAXMSGLN is 52,428,800? If I change the queue's MAXMSGLN to 104,857,600, and it doesn't fix the fault, is it ok to change it back? |
|
Back to top |
|
 |
mqjeff |
Posted: Thu Mar 01, 2012 9:14 am Post subject: |
|
|
Grand Master
Joined: 25 Jun 2008 Posts: 17447
|
Every time you use a SVRCONN you also use a CLNTCONN.
notice
Quote: |
This reason can also be returned to an MQ client program on the MQGET, MQPUT, or MQPUT1 call, if the BufferLength parameter exceeds the maximum message size that was negotiated for the client channel. |
|
|
Back to top |
|
 |
fishlips |
Posted: Thu Mar 01, 2012 9:21 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
I can see a CLIENT.[QUEUE MANAGER NAME] in our Channels, is that what you mean by Client Connection?
Or do you actually mean Advanced --> Client Connections? |
|
Back to top |
|
 |
fishlips |
Posted: Thu Mar 01, 2012 9:29 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
Just to clarify, I have a test queue that I created. I just put a test message on there and can confirm that my development PC is still able to connect and download the text message successfully.
(I haven't posted the code
It's obviously something to do with the make up of the messages that have been posted to our queue which is causing the problem. |
|
Back to top |
|
 |
mqjeff |
Posted: Thu Mar 01, 2012 9:29 am Post subject: |
|
|
Grand Master
Joined: 25 Jun 2008 Posts: 17447
|
fishlips wrote: |
I can see a CLIENT.[QUEUE MANAGER NAME] in our Channels, is that what you mean by Client Connection?
Or do you actually mean Advanced --> Client Connections? |
I mean specifically an MQ object of type 'CLNTCONN'.
Which will indeed be listed under the Client Connections folder in MQExplorer.
But remember that the relevant CLNTCONN is the one that has the same name as the SVRCONN. Like all MQ channels, SVRCONN/CLNTCONNs are paired and associated by name. So where you have a SENDER that needs to talk to a remote qmgr, that remote qmgr needs a RECEIVER of the SAME NAME.
All of this is a round about way of telling you to investigate the method you are using to build the ConnectionFactory. And, for example, examine if the ConnectionFactory allows you to specify something like the maxmsgln of the client side. Or if you need to instead tell the ConnectionFactory to use a channel table instead. |
|
Back to top |
|
 |
fishlips |
Posted: Fri Mar 02, 2012 2:23 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
Ok, well here's a bit more info about the messages.
Messages that I uploaded during development have a blank value in the "MQ Message Format" field, and have the msgType of "8 Datagram".
The messages received from the customer have MQHRF2 in the "MQ Message Format", and have the msgType of "8 Datagram".
Are there changes I need to make to the code, in order to read messages with the "MQHRF2" format? |
|
Back to top |
|
 |
Vitor |
Posted: Fri Mar 02, 2012 4:45 am Post subject: |
|
|
 Grand High Poobah
Joined: 11 Nov 2005 Posts: 26093 Location: Texas, USA
|
fishlips wrote: |
Are there changes I need to make to the code, in order to read messages with the "MQHRF2" format? |
Yes, or if you're using WMQv7 you need to cater for them; v7 introduced message properties which replaced the MQRFH2 header. Much discussion on this in the forum.
It's not what's causing your 2010 code. That's an object too small to handle the message you're getting as previously indicated. _________________ Honesty is the best policy.
Insanity is the best defence. |
|
Back to top |
|
 |
fishlips |
Posted: Fri Mar 02, 2012 5:08 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
Ok, well with a bit more jiggery pokery in RFHUtil I've managed to create a message with an MQHRF2 header:
Code: |
Data tab:
Set Packed dec = HOST (390)
MQMD Tab:
Code page = 819
Int Fmt: Unix
PD Fmt: Host
ID Display: Hex
Persistent Msg: Yes
RFH Tab:
RFH V2 Fixed Data
Set Integer Encoding = Unix
Set Pack Dec = Host
Tick Include RFH V2 Header, and tick the V2 Folder "usr"
In usr tab, set the text box to read as:
fileName=MyFileName908209384024.txt
|
If I then press write Q, the message appears to be exactly the same as the messages I've received from the customer, apart from these subtle differences:
1. My application type is "32-but windows", the customers' is "Queue Manager Publish"
2. My Put Allocation Name is "rfhutil.exe", theirs is "LIT_BKR1"
I ran my code against my newly created message (with the MQHRF2 header) and it worked, so I'm now at a loss as to why the same code doesn't download DATAGRAM messages on the actual live queue. The live queue's messages & test queue's message have exactly the same Message Type, Persistence, Coded character set identifier, and encoding values.
RFHUtil confirms that the message format is also an exact match (MQHRF2), so why can't I read messages from the live queue? I'm still getting the error 2010 (07DA) (RC2010): MQRC_DATA_LENGTH_ERROR on this line:
Code: |
recvMsg = Consumer.ReceiveNoWait |
I guess it has to be an error in the way that the queue has been configured, would you agree?
Last edited by fishlips on Fri Mar 02, 2012 5:24 am; edited 1 time in total |
|
Back to top |
|
 |
fishlips |
Posted: Fri Mar 02, 2012 5:20 am Post subject: |
|
|
 Apprentice
Joined: 21 Dec 2011 Posts: 36
|
Vitor wrote: |
It's not what's causing your 2010 code. That's an object too small to handle the message you're getting as previously indicated. |
If this is the case, than fair enough; Of course, the next question I'm going to ask is what property in the connection facory properties is the one that increases the maximum msg size?
I'm looking through the definition of XMSC so far and there's loads, with fairly unhelpful descriptions. Just from a quick browse, could it be perhaps:
Code: |
- WMQ_MSG_BATCH_SIZE
- WMQ_MAX_BUFFER_SIZE
|
Any ideas? Maybe I'll just try setting them to 52,428,800 ?
Last edited by fishlips on Fri Mar 02, 2012 5:25 am; edited 1 time in total |
|
Back to top |
|
 |
|