ASG
IBM
Zystems
Cressida
Icon
Netflexity
 
  MQSeries.net
Search  Search       Tech Exchange      Education      Certifications      Library      Info Center      SupportPacs      LinkedIn  Search  Search                                                                   FAQ  FAQ   Usergroups  Usergroups
 
Register  ::  Log in Log in to check your private messages
 
RSS Feed - WebSphere MQ Support RSS Feed - Message Broker Support

MQSeries.net Forum Index » IBM MQ API Support » Message under cursor

Post new topic  Reply to topic Goto page 1, 2  Next
 Message under cursor « View previous topic :: View next topic » 
Author Message
RogerLacroix
PostPosted: Fri Jul 30, 2004 8:39 am    Post subject: Message under cursor Reply with quote

Jedi Knight

Joined: 15 May 2001
Posts: 3264
Location: London, ON Canada

All,

I was doing some testing of MQ code and have a question.

First the testing:

Test #1: I created a program to browse messages until a particular message then do a destructive get of it. I put 10 messages in the queue and had the program destructively get message number 6. This worked fine and the queue had 9 messages left the original message # 6 was removed.

I cleared the queue before the next test.

Test #2: I created a program to browse to message a particular message then do a destructive get of it and all remaining messages. I put 10 messages in the queue and had the program destructively get message number 6 and the remaining messages (7,8,9&10). This worked and but I did not get the results I was expecting. It should have removed the 5 messages starting at messages # 6 (i.e. 6,7,8,9&10). It removed 5 messages but they were message # 6,1,2,3&4. The message # 5,7,8,9&10 were left on the queue.

I did several tests and concluded the following: When the program does a destructive get for a 'message under cursor', it does not actually move the destructive get cursor.

For those who do not know, when an application reads a message there are 2 cursors that keep track of where you are while getting messages. There is a Browse Cursor and a Destructive Read Cursor. They are independent of each other.

I thought that when an application does a 'destructive get under cursor' (MQGMO_MSG_UNDER_CURSOR) that the destructive get cursor was moved to the current message position but that does not appear to be true. It remains at its previous position.

I.e. In my example, even though my app. did a 'destructive get under cursor' for message number 6, the destructive get cursor was still pointing to the first message in the queue.

So, to the question: How do you move the destructive get cursor without deleting messages? I have gone through the GetMessageOptions and I don't see anything.

It appears that once you starting browsing beyond the first message, you are stuck with doing the 'destructive get under cursor' for removing messages. (Because the 'destructive get under cursor' is still pointing at the first message. )

So, if this is not the solution, then what is a better one?

Regards,
Roger Lacroix
_________________
Capitalware: Transforming tomorrow into today.
Connected to MQ!
Twitter
Back to top
View user's profile Send private message Visit poster's website
PeterPotkay
PostPosted: Fri Jul 30, 2004 1:28 pm    Post subject: Reply with quote

Poobah

Joined: 15 May 2001
Posts: 7722

Messages are 1 2 3 4 5 6 7 8 9 10.
You browse to message 6.
You get message 6 destructivly.
What do you get now if you do another browse? 7? Or 1?





Quote:

For those who do not know, when an application reads a message there are 2 cursors that keep track of where you are while getting messages. There is a Browse Cursor and a Destructive Read Cursor. They are independent of each other.

Is this documented somewhere?



Quote:

I thought that when an application does a 'destructive get under cursor' (MQGMO_MSG_UNDER_CURSOR) that the destructive get cursor was moved to the current message position but that does not appear to be true. It remains at its previous position.

The APR manual says:
Quote:

Note that the browse cursor is not moved by nonbrowse MQGET calls using the same Hobj handle.


What does that mean???? I think it means: If you browse to #5, get #5, the cursor still points at #5? If yes, I would think you would then need to issue anothe MQGMO_BROWSE_NEXT, which would get you to #6, right? Or are you saying you get thrown to #1 no matter what?

What is your browse option on the next MQGET call after you succesfully pull #5?
_________________
Peter Potkay
Keep Calm and MQ On
Back to top
View user's profile Send private message
RogerLacroix
PostPosted: Fri Jul 30, 2004 2:01 pm    Post subject: Reply with quote

Jedi Knight

Joined: 15 May 2001
Posts: 3264
Location: London, ON Canada

Quote:
Messages are 1 2 3 4 5 6 7 8 9 10.
You browse to message 6.
You get message 6 destructivly.
What do you get now if you do another browse? 7? Or 1?

Browse will be # 7.

Quote:
Quote:
For those who do not know, when an application reads a message there are 2 cursors that keep track of where you are while getting messages. There is a Browse Cursor and a Destructive Read Cursor. They are independent of each other.

Is this documented somewhere?

Yes, I don't remember where it is.

Quote:
The APR manual says:
Quote:
Note that the browse cursor is not moved by nonbrowse MQGET calls using the same Hobj handle.

Ah ha, per your previous item, this infers 2 cursors. (Otherwise, they want not have said 'browse' cursor.)

Quote:
If you browse to #5, get #5, the cursor still points at #5? If yes, I would think you would then need to issue anothe MQGMO_BROWSE_NEXT, which would get you to #6, right?

Yes. (Browsing).

But if I do a destructive get then I would get # 1.

Code:
if (browse)
   getOptions.options=MQC.MQGMO_BROWSE_NEXT+MQC.MQGMO_NO_WAIT+MQC.MQGMO_FAIL_IF_QUIESCING+MQC.MQGMO_ACCEPT_TRUNCATED_MSG;
else
   getOptions.options=MQC.MQGMO_NO_WAIT+MQC.MQGMO_FAIL_IF_QUIESCING+MQC.MQGMO_ACCEPT_TRUNCATED_MSG;


Now going back to your question, after I pull message #5 (get message under cursor), if the browse flag is true then message # 6 will be returned. But if the browse flag is false then message # 1 is returned.

Regards,
Roger Lacroix
_________________
Capitalware: Transforming tomorrow into today.
Connected to MQ!
Twitter
Back to top
View user's profile Send private message Visit poster's website
PeterPotkay
PostPosted: Fri Jul 30, 2004 2:08 pm    Post subject: Reply with quote

Poobah

Joined: 15 May 2001
Posts: 7722

Browse to 5
GET 5
Browse next (will get you to 6?) <<<add this step to your process
GET 6
Browse next
GET 7


Will this work?
_________________
Peter Potkay
Keep Calm and MQ On
Back to top
View user's profile Send private message
RogerLacroix
PostPosted: Fri Jul 30, 2004 2:23 pm    Post subject: Reply with quote

Jedi Knight

Joined: 15 May 2001
Posts: 3264
Location: London, ON Canada

Hi,

I assume by 'Browse' you mean: do a non-destructive get and by 'GET' you mean a destructive get? True?

Let me lay it out without a loop structure. Assume 10 messages in the queue.

Scenario #1:

Open Queue
Browse First - returns #1
Browse Next - returns #2
Browse Next - returns #3
Browse Next - returns #4
Browse Next - returns #5
Browse Next - returns #6
Destructive Get message under cursor - - returns #6
Browse Next - returns #7
Browse Next - returns #8
Browse Next - returns #9
Browse Next - returns #10
Browse Next - returns 2033 - no more messages
Close Queue

Scenario #2:

Open Queue
Browse First - returns #1
Browse Next - returns #2
Browse Next - returns #3
Browse Next - returns #4
Browse Next - returns #5
Browse Next - returns #6
Destructive Get message under cursor - - returns #6
Destructive Get - returns #1
Destructive Get - returns #2
Destructive Get - returns #3
Destructive Get - returns #4
Destructive Get - returns #5
Destructive Get - returns 6th message in queue originally #7
Destructive Get - returns 7th message in queue originally #8
Destructive Get - returns 8th message in queue originally #9
Destructive Get - returns 9th message in queue originally #10
Destructive Get - returns 2033 - no more messages
Close Queue

If I don't stop it after a paricular number of messages then the above happens (i.e. only destructively get 5 messages).

Regards,
Roger Lacroix
_________________
Capitalware: Transforming tomorrow into today.
Connected to MQ!
Twitter
Back to top
View user's profile Send private message Visit poster's website
PeterPotkay
PostPosted: Fri Jul 30, 2004 2:27 pm    Post subject: Reply with quote

Poobah

Joined: 15 May 2001
Posts: 7722

Try Scenario #3:

Open Queue
Browse First - returns #1
Browse Next - returns #2
Browse Next - returns #3
Browse Next - returns #4
Browse Next - returns #5
Browse Next - returns #6
Destructive Get message under cursor - - returns #6
Browse Next - returns #7
Destructive Get - returns #7
Browse Next - returns #8
Destructive Get - returns #8
Browse Next - returns #9
Destructive Get - returns #9
Browse Next - returns #10
Destructive Get - returns #10
Browse Next - returns 2033 - no more messages
_________________
Peter Potkay
Keep Calm and MQ On
Back to top
View user's profile Send private message
RogerLacroix
PostPosted: Fri Jul 30, 2004 2:43 pm    Post subject: Reply with quote

Jedi Knight

Joined: 15 May 2001
Posts: 3264
Location: London, ON Canada

Be right back ..........................

I'm Back.

For a minute, you had me wondering but here are the results:

Try Scenario #3:

Open Queue
Browse First - returns #1
Browse Next - returns #2
Browse Next - returns #3
Browse Next - returns #4
Browse Next - returns #5
Browse Next - returns #6
Destructive Get message under cursor - - returns #6
Browse Next - returns #7
Destructive Get - returns #1
Browse Next - returns #8
Destructive Get - returns #2
Browse Next - returns #9
Destructive Get - returns #3
Browse Next - returns #10
Destructive Get - returns #4
Browse Next - returns 2033 - no more messages

It's kinda cool that the cursors are truly independent of one another but it lends me back to my original question: How do you move the destructive get cursor?

Regards,
Roger Lacroix
_________________
Capitalware: Transforming tomorrow into today.
Connected to MQ!
Twitter
Back to top
View user's profile Send private message Visit poster's website
PeterPotkay
PostPosted: Fri Jul 30, 2004 4:25 pm    Post subject: Reply with quote

Poobah

Joined: 15 May 2001
Posts: 7722

Quote:

Browse Next - returns #6
Destructive Get message under cursor - - returns #6


but

Quote:

Browse Next - returns #7

then
Quote:

Destructive Get - returns #1



You got me Roger. The behaviour you are seeing is not what I would have expected.
_________________
Peter Potkay
Keep Calm and MQ On
Back to top
View user's profile Send private message
RogerLacroix
PostPosted: Fri Jul 30, 2004 5:59 pm    Post subject: Reply with quote

Jedi Knight

Joined: 15 May 2001
Posts: 3264
Location: London, ON Canada

Hi,

Actually, now that I have had a chance to think about it, it makes perfect sense. I would have expected it to work that way.

I was just re-reading sections in the APR manual and I can't seem to find anything about moving the destructive get cursor, other than doing a destructive get.

So to 'cherry pick' messages, I guess I'll have to browse and only use 'get under cursor' method.

Regards,
Roger Lacroix
_________________
Capitalware: Transforming tomorrow into today.
Connected to MQ!
Twitter
Back to top
View user's profile Send private message Visit poster's website
PeterPotkay
PostPosted: Sat Jul 31, 2004 3:36 am    Post subject: Reply with quote

Poobah

Joined: 15 May 2001
Posts: 7722

Are you trying to allow a user of a GUI tool to CTRL + SHIFT and select multiple messages from a view, and then select DELETE, so that they can pick and choose messages from a queue to delete?

I think the only way to pull this off is that your program will have to generate its own index, record which messages the user selects, and then do an individual browse then destructive get of each one, all the while keeping the internal index in order. (The user selects Message #2 and #4 and #9 to delete:You have to browse 2 deep and destructive GET, then browse 2 deep again, and destructive GET, and finally browse 7 deep and destructive MQGET.)

If messages are deleted from the queue via Expiry or because another app read some, it will make the whole process much trickier and might cause the wrong message to be deleted if you're not careful in the design/testing.
_________________
Peter Potkay
Keep Calm and MQ On
Back to top
View user's profile Send private message
RogerLacroix
PostPosted: Sat Jul 31, 2004 7:53 am    Post subject: Reply with quote

Jedi Knight

Joined: 15 May 2001
Posts: 3264
Location: London, ON Canada

Hi,

Actually, for MQ Visual Edit, it uses 'Get by MsgId & CorrelId' for messages that the user wants to delete. Far more efficient.

What you described won't work unless you meant 'Destructive Get under Cursor' rather than just 'Destructive Get'. Because of my answer with scenario # 3.

I am building a non-GUI tool like MQ Visual Edit. I want to provide the ablility to delete messages 101-105 of a queue with 200 messages. I totally agree that expired messages may skew the numbering of messages in a queue. But it is up to the user to understand the messages in their queues. (That may be a pipe dream - but almost every tool can be dangerous if you don't understand it or the data.)


Regards,
Roger Lacroix
_________________
Capitalware: Transforming tomorrow into today.
Connected to MQ!
Twitter
Back to top
View user's profile Send private message Visit poster's website
PeterPotkay
PostPosted: Sat Jul 31, 2004 11:25 am    Post subject: Reply with quote

Poobah

Joined: 15 May 2001
Posts: 7722

Quote:

Actually, for MQ Visual Edit, it uses 'Get by MsgId & CorrelId' for messages that the user wants to delete. Far more efficient.


But technically it is vulnerable to the scenario where developers dumps messages to the queue with all the same Message-ID and maybe no Correl-ID, or the same Correl-ID. Yeah, I seen it happen and it foiled a GUI tool that relied on MessageID+CorrelID+PutTime for the selection of deleting a specific message off of a queue. The developers were dumping the messages with the same IDs to the queue so fast that some of the messages had the same PutTime.

Then the users were trying to copy a specific message to put to another q or to delete it, and invariably getting the wrong one.

You and I both know they shouldn't have put the messages to the queue with the same IDs. But man did we waste a lot of time trying to figure out the confusion when they thought they were getting a particular message with particular data and they weren't getting the results they were supposed to. (They did fix their code to allow unique MessageIDs.)

If by MessageID / CorrelID is how your tool grabs the messages, I would put a warning in the documenttion (if its not already there) saying results will not be as expected if the messages are sitting on the queues with identical IDs.
_________________
Peter Potkay
Keep Calm and MQ On
Back to top
View user's profile Send private message
jefflowrey
PostPosted: Sat Jul 31, 2004 1:27 pm    Post subject: Reply with quote

Grand Poobah

Joined: 16 Oct 2002
Posts: 19981

Yeah - I seem to remember warning Roger, a while ago, about a similar problem encountered with QPasa.

Message ID + Correlation ID = not guaranteed unique. Sorry Roger!
_________________
I am *not* the model of the modern major general.
Back to top
View user's profile Send private message
RogerLacroix
PostPosted: Sat Jul 31, 2004 6:08 pm    Post subject: Reply with quote

Jedi Knight

Joined: 15 May 2001
Posts: 3264
Location: London, ON Canada

Oops, I shouldn't have brought up MQ Visual Edit cause now we have changed subjects. Peter, yes, I agree with you and MQ Visual Edit's docs states that things like deletion, forwarding, etc... are done by MsgID + CorrelID. It is a restriction and every once in a while I get an email about it.

Jeff, I kind of remember a discussion (But I've never used QPasa).

Please let me refocus this thread back to the question: How do you move the destructive get cursor?

Regards,
Roger Lacroix
_________________
Capitalware: Transforming tomorrow into today.
Connected to MQ!
Twitter
Back to top
View user's profile Send private message Visit poster's website
gunter
PostPosted: Sun Aug 01, 2004 4:56 am    Post subject: Reply with quote

Partisan

Joined: 21 Jan 2004
Posts: 307
Location: Germany, Frankfurt

Roger,

I made a quick test on this by changing the code in amqsget. I couldn't find any unexpected behavior.

The result is:
$ ./brouwse_under_cursor TT QM1
Sample AMQSGET0 start
Browse Next <#1> // it's first
Browse Next <#2>
Browse Next <#3>
Browse Next <#4>
Browse Next <#5>
Browse Next <#6>
Destructive Get <#6>
Browse Next <#7>
Destructive Get <#7>
Browse Next <#8>
Destructive Get <#8>
Browse Next <#9>
Browse Next <#10>

After this the content of the queue is:

$ ./amqsget TT QM1
Sample AMQSGET0 start
message <#1>
message <#2>
message <#3>
message <#4>
message <#5>
message <#9>
message <#10>
no more messages

Here the code I changed:

Code:
   gmo.Options = MQGMO_WAIT       /* wait for new messages           */
               + MQGMO_BROWSE_FIRST
               + MQGMO_CONVERT;   /* convert if necessary            */
   gmo.WaitInterval = 15000;      /* 15 second limit for waiting     */

   
   while (CompCode != MQCC_FAILED)
   {
       buflen = sizeof(buffer) - 1; /* buffer size available for GET   */

       memcpy(md.MsgId, MQMI_NONE, sizeof(md.MsgId));
       memcpy(md.CorrelId, MQCI_NONE, sizeof(md.CorrelId));

       md.Encoding       = MQENC_NATIVE;
       md.CodedCharSetId = MQCCSI_Q_MGR;

       MQGET(Hcon,                /* connection handle                 */
             Hobj,                /* object handle                     */
             &md,                 /* message descriptor                */
             &gmo,                /* get message options               */
             buflen,              /* buffer length                     */
             buffer,              /* message buffer                    */
             &messlen,            /* message length                    */
             &CompCode,           /* completion code                   */
             &Reason);            /* reason code                       */

       if (CompCode != MQCC_FAILED)
       {
           buffer[messlen] = '\0';            /* add terminator          */
           printf("Browse Next <%s>\n", buffer);
           i++;
           if( i > 5 && i < 9 )
           {
               memcpy(md.MsgId, MQMI_NONE, sizeof(md.MsgId));
               memcpy(md.CorrelId, MQCI_NONE, sizeof(md.CorrelId));
               md.Encoding       = MQENC_NATIVE;
               md.CodedCharSetId = MQCCSI_Q_MGR;

               gmo.Options = MQGMO_WAIT       /* wait for new messages           */
                           + MQGMO_MSG_UNDER_CURSOR
                           + MQGMO_CONVERT;   /* convert if necessary            */

               MQGET(Hcon,                /* connection handle                 */
                     Hobj,                /* object handle                     */
                     &md,                 /* message descriptor                */
                     &gmo,                /* get message options               */
                     buflen,              /* buffer length                     */
                     buffer,              /* message buffer                    */
                     &messlen,            /* message length                    */
                     &CompCode,           /* completion code                   */
                     &Reason);            /* reason code                       */
             
               printf("Destructive Get <%s>\n", buffer);
           }
       }
       gmo.Options = MQGMO_WAIT       /* wait for new messages           */
                   + MQGMO_BROWSE_NEXT
                   + MQGMO_CONVERT;   /* convert if necessary            */
   }



_________________
Gunter Jeschawitz
IBM Certified System Administrator - Websphere MQ, 5.3
Back to top
View user's profile Send private message
Display posts from previous:   
Post new topic  Reply to topic Goto page 1, 2  Next Page 1 of 2

MQSeries.net Forum Index » IBM MQ API Support » Message under cursor
Jump to:  



You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
Protected by Anti-Spam ACP
 
 


Theme by Dustin Baccetti
Powered by phpBB © 2001, 2002 phpBB Group

Copyright © MQSeries.net. All rights reserved.