Problem with retrieving Program Messages
  (31-replies, RPG IV)
Post your reply | Return to Forum  Refresh | ascending | descending
Author: sha_sha Return to Forum  Refresh 2010-02-10 08.16.54
You can: 
1) before retrieve list objects by API
3) Sndpgmmsg and save msgkey as msgkey_start
3) Use copy with generic
4) Sndpgmmsg and save msgkey as msgkey_end
5) Retrieve program messages between msgkey_start and msgkey_end
6) Seek exceptions or errors and you can find objects which are not copied.
   // so you have all objects which are copied
Author: GEFISWN Return to Forum  Refresh 2010-02-02 08.27.05
The CPP is identical but we are still on V5R4 (and QSYS2929 = German :))
Nevertheless very strange.
Author: GEFISWN Return to Forum  Refresh 2010-02-02 08.14.22
The CPP is identical but we are still on V5R4 (and QSYS2929 = German :))
Nevertheless very strange.
Author: TFisher Return to Forum  Refresh 2010-02-02 08.09.47
I don't think you are going to be able to get it to work without doing a COPY 
for each file.  That is, retrieving a list of the files and doing the wildcard 
search yourself inside your program...then doing a COPY for each file 
separatly.
Author: GEFISWN Return to Forum  Refresh 2010-02-02 07.58.30
The CPP is identical but we are still on V5R4 (and QSYS2929 = German :))
Nevertheless very strange.
Author: TFisher Return to Forum  Refresh 2010-02-02 07.45.03
I didn't suggest that the select panel was a "customized feature", only that 
something must be configured differently here because it never appears on our 
systems when there are more than one file matching with the generic file name 
(wildcard).  

It's because of this program being called that I beleive the messages might be 
in a different call stack.

But, since you brought up the idea that perhaps this is a "customized" 
feature...let's check.  The CPP for COPY is 'QSYS/QP0LCCPY' on our system.  
What is yours?  Also, I am on V6.
Author: Bob Cozzi Return to Forum  Refresh 2010-02-02 07.30.35
If you are getting a list of files (were you getting this before as I don't
recall reading that issue) then it disrupts (i.e., receives) the request message
and therefore it is no longer there. You may have to get the message by msgkey.


Author: GEFISWN Return to Forum  Refresh 2010-02-02 07.20.43
I'm sure this automatic select panel is not a customized feature. I tested it 
on 2 different systems with the same result. But it appears only, when there 
is more than one file matching with the generic specification.

Refering to QMHRCVPM:
I tried different message types - but in vain.
Author: DaleB Return to Forum  Refresh 2010-02-02 07.12.00
Not sure sure about the *PRV; may work, may not. The code sample I gave you was
lifted from production code. It will iterate all program messages, unless you
Leave the loop early.
Author: TFisher Return to Forum  Refresh 2010-02-02 05.41.17
I don't know why you are getting a panel to select the files, I don't get that 
here.

When I copy one file the CPCA087 is a Completion message (*COMP).  When I copy 
multiple files the CPCA087 messages are Information messages (*INFO).

I am thinking that something on your system is configured differently which is 
why you are going into an application to select the files.  And perhaps this is 
causing the messages to be logged with a different call stack....just a guess 
since I cannot get the same results with COPY using a generic file (or 
wildcard).
Author: GEFISWN Return to Forum  Refresh 2010-02-02 03.12.14
I tried all your suggestions but it didn't work.
As it is rather inexplicable I would like to show you details of my test:

Test program with full pathname:
-----------------------------------
 #SrcPath = '/tmp/slptrace.log';                                    
 #TgtPath = '/gefis/tmp/slptrace.cpy';                              
 pCmdStg = 'COPY OBJ(''' + %trimr(#SrcPath) + ''') TOOBJ(''' +     
            %trimr(#TgtPath) + ''') REPLACE(*YES)';                 
 CallP(E) QCMDEXC(pCmdStg:%len(pCmdStg));                         
                                                                    
Now the joblog shows:
> call noll/rcvprvmsg2 parm('0') <- my testprogram 
  Object copied.                 <- CPCA087

Let's receive the program msgq
 #StackCnt = %int(pStack);  <- was passed as *zero
 #MsgType =  '*PRV';                                                
 #MsgKey  = *ALLx'00';                                              
 DoU dsAPIErrDS.ByteRtn > *zeros;                                    
     QMHRCVPM(dsRCVM0100:%size(dsRCVM0100):'RCVM0100':'*':#StackCnt:  
              #MsgType:#MsgKey:0:'*SAME':dsAPIErrDS);                
     #MsgKey  = dsRCVM0100.MsgKey;                                   
     If dsRCVM0100.MsgID = 'CPCA087'; 
    Now the debugger shows:
    dsRCVM0100.MSGID = 'CPCA087'                                              
    dsRCVM0100.MSGDTA =                                                       
    '   ¬/tmp/slptrace.log   ¬/gefis/tmp/slptrace.cpy
     EndIf;                          
EndDo;                              

Test program with generic pathname:
-----------------------------------
 #SrcPath = '/tmp/*.log';                                    
 #TgtPath = '/gefis/tmp/slptrace.cpy';                              
 pCmdStg = 'COPY OBJ(''' + %trimr(#SrcPath) + ''') TOOBJ(''' +     
            %trimr(#TgtPath) + ''') REPLACE(*YES)';                 
 CallP(E) QCMDEXC(pCmdStg:%len(pCmdStg));                         
                                                                    
Now the following panel is displayed:
         Select Object
Directory  . . . . :   /tmp                  
Type option, press Enter.                    
  1=Select                                   
Opt  Object link                             
 _   dlfm_QZDFMSVR_33d.log                   
 _   slptrace.log                            
More than one name matches pattern.          

After selecting file slptrace.log and pressing Enter, the file is copied.

The joblog shows:
> call noll/rcvprvmsg3 parm('0')     <- my test program
  More than one name matches pattern.
  Object copied.                     <- CPCA087
       
Let's receive the program msgq
 #StackCnt = %int(pStack);  <- was passed as parameter (I tried with 0-4)
 #MsgType =  '*PRV';                                                
 #MsgKey  = *ALLx'00';                                              
 DoU dsAPIErrDS.ByteRtn > *zeros;                                    
     QMHRCVPM(dsRCVM0100:%size(dsRCVM0100):'RCVM0100':'*':#StackCnt:  
              #MsgType:#MsgKey:0:'*SAME':dsAPIErrDS);                
     #MsgKey  = dsRCVM0100.MsgKey;                                   
     If dsRCVM0100.MsgID = 'CPCA087'; <- Was never found!!
        //                 
     EndIf;                          
EndDo;                              
Author: Bob Cozzi Return to Forum  Refresh 2010-02-01 11.39.34
CPCA087 is a *INFO message. Thought the "CPC" indicated *COMP.

I would set the message type to *ANY and blank out the msgkey variable. 
Then cycle through each one returned until (A) You hit the CPCA087 or (B) you
retrieve a *RQS message. 

As for the msgkey, your situation may be a simple matter of changing it to
*BLANKS vs *ZEROS.
Author: DaleB Return to Forum  Refresh 2010-02-01 11.32.41
I have programs that process the program message queue in a loop for different
reasons, but the basics should be similar. I've changed my field names to match
your sample, but you'll have to adjust subfield names of $RCVM0100 to match
your definitions:

       #MsgKey = '*TOP';
       DoU $RCVM0100.BytesReturned=8 AND $RCVM0100.BytesAvailable=*ZERO;
         QMHRCVPM($RCVM0100:%size($RCVM0100):'RCVM0100':'*':*ZERO:
              '*NEXT':#MsgKey:*ZERO:'*SAME':$APIErrDS);
         If $RCVM0100.MsgID='CPCA087';
           // Get details from $RCVM0100.ReplacementData
         EndIf;
         #MsgKey = $RCVM0100.MessageKey;
       EndDo;
Author: GEFISWN Return to Forum  Refresh 2010-02-01 11.31.14
It's a little bit strange with that COPY command.
If you execute it interactively from a command line, you surely can enter a 
generic file name and all the matching files are copied by one step.
But when the same command is executed within the RPG program with QCMDEXC, it 
is promted automatically and all matching files are shown for selection.
I didn't know that before.
Author: TFisher Return to Forum  Refresh 2010-02-01 11.04.55
First, QCMDCHK will indeed return the changed command string.  Second, even the 
COPY command requires the '?' in order to prompt it correctly.

  Command = '?COPY ';                  
  LenCommand = %Len(Command);           
  Callp(e) QcmdChk(Command:LenCommand);
  // now Command equals the parms the user enters

But I agree that QCMDCHK will not provide you with all the files when the user 
enters something like '/tmp/*.csv'.  You need to stick with trying to read the 
joblog to find the actual files, or do a DIR to pull them before doing a 
COPY...but even DIR may not be correct since it could list 4 files then the 
COPY could copy 5 files if a new file was created between DIR and COPY.

The message type will be *INFO:

 COPY OBJ('/fisherto/*.rtf')           
 Object copied.                        <- CPCA087 *INFO       
 1 objects copied.  0 objects failed.  <- CPFA0BB *COMP
Author: GEFISWN Return to Forum  Refresh 2010-02-01 11.00.07
Hello Bob,

I just have read your reply. Well my API call looks like:

 #StackCnt = %int(p$Stack); <-- passed by parameter. I tried all stacks 
from 0 up to 4.                                      
 #MsgType =  '*PRV';                                              
 #MsgKey  = *ALLx'00';                                            
 *in66    = *off;                                                 
                                                                  
 DoU $APIErrDS.ByteRtn > *zeros;                                  
      QMHRCVPM($RCVM0100:%size($RCVM0100):'RCVM0100':'*':#StackCnt:
              #MsgType:#MsgKey:0:'*SAME':$APIErrDS);              
     #MsgKey  = $RCVM0100.MsgKey;                                 
     If $RCVM0100.MsgID = 'CPCA087';                              
        *in66 = *on;                                              
     EndIf;                                                       
 EndDo; 

You suggested message type *COMP. I'll try it.
Author: GEFISWN Return to Forum  Refresh 2010-02-01 10.54.40
Hello Bob,

I just have read your reply. Well my API call looks like:

 #StackCnt = %int(p$Stack); <-- passed by parameter. I tried all stacks 
from 0 up to 4.                                      
 #MsgType =  '*PRV';                                              
 #MsgKey  = *ALLx'00';                                            
 *in66    = *off;                                                 
                                                                  
 DoU $APIErrDS.ByteRtn > *zeros;                                  
      QMHRCVPM($RCVM0100:%size($RCVM0100):'RCVM0100':'*':#StackCnt:
              #MsgType:#MsgKey:0:'*SAME':$APIErrDS);              
     #MsgKey  = $RCVM0100.MsgKey;                                 
     If $RCVM0100.MsgID = 'CPCA087';                              
        *in66 = *on;                                              
     EndIf;                                                       
 EndDo; 

You suggested message type *COMP. I'll try it.
Author: GEFISWN Return to Forum  Refresh 2010-02-01 10.45.59
Hello All,

I tried both QCMDCHK and QCAPCMD. QCMDCHK cannot return changed command string.
QCAPCMD does it in general, but in my case it returns the command string with 
the generic file name. This is the return value in parameter 6 (=Changed 
command string)diplayed by the debugger:
> EVAL ChgCmdStr                                                          
  CHGCMDSTR =                                                             
            ....5...10...15...20...25...30...35...40...45...50...55...60  
       1   '? COPY OBJ('/tmp/*.csv') TOOBJ('/gefis/artikelcopy.csv') REP' 
      61   'LACE(*YES)                                                  ' 

The '?' before the command to force prompting is not necessary. Prompting is 
done by the COPY command itself when a generic file name is supplied.

I'm sure QCMDCHK and QCAPCMD will not solve my issue.
I'll continue to struggle with the QMHRCVPM API.

Author: GEFISWN Return to Forum  Refresh 2010-02-01 10.36.13
QCMDCHK would still return the command string with the generic file name!
Author: Bob Cozzi Return to Forum  Refresh 2010-02-01 10.20.49
So did  your call to the API look anything like this?

qmhrcvpm(rtnMsgInfo: %size(rtnMsgInfo): 'RCVM0100':'*':0:'*COMP':
                     rtnMsgKey: 0 :'*SAME':apiError);
Author: Bob Cozzi Return to Forum  Refresh 2010-02-01 09.55.21
I think fish meant QCMDCHK which returns a command string and not QCMDEXC which
doesn't return a command string.

Anyway, the issue is with your QMHRCVPM API call. it is tricky to use this.
If you have RPGLIB (formerly RPG xTools) you can call the wrappers for that and
it'll just work. If you don't, then I'll have to go look at the options, but I
do know that simply specifying 0 for the call-stack-entry is not enough.
Author: TFisher Return to Forum  Refresh 2010-02-01 09.53.07
Okay, are you saying that the user actually enters a wildcard and multiple 
files are being copied?  If so, then you may have been on the right 
track...reading the joblog.  I was thinking you were talking about CPYF...then 
I read your original post again and saw that you are doing a 'COPY' which 
allows generic file names (COPY A*).
Author: TFisher Return to Forum  Refresh 2010-02-01 09.43.33
Is there a reason you can't use QCAPCMD?  I like this API over the QCMDCHK and 
QCMDEXC APIs.

However, QCMDCHK will return the new command to your application...but you will 
need to check for F12 or F3.  If the user presses F12 on the command panel then 
you would not want to issue the command returned.

If you are entering a file name and pressing Enter then you "should" be getting 
the new command string back into your program.  If you aren't then you are 
doing something wrong.
Author: DaleB Return to Forum  Refresh 2010-02-01 09.36.06
Maybe we need to take a step back here. What happens with your command? It
sounds like maybe your command shows a list of objects, then the user selects
from the list and you copy or whatever it is you're doing with the selected
item. If that's true, then you are not prompting the command (i.e., '?' in the
command string), you're just running the command. Is this closer to the mark?
Author: GEFISWN Return to Forum  Refresh 2010-02-01 09.33.22
QCMDCHK would still return the command string with the generic file name!
Author: TFisher Return to Forum  Refresh 2010-02-01 09.10.37
USE QCAPCMD TO PROMPT THE COMMAND AND LATER EXECUTE THE COMMAND AFTER YOU HAVE 
EXTRACTED THE FILE NAME.
Author: neilrh Return to Forum  Refresh 2010-02-01 08.40.12
"The Check Command Syntax (QCMDCHK) API performs syntax checking for a single 
command, and optionally prompts for the command. The command is not run. If 
prompting is requested, the command string is returned to the calling program 
with the updated values as entered through prompting. The QCMDCHK API can be 
called from an HLL program."

From the V5R3 manual - it would appear that the command is supposed to return 
promted values.  Does this mean that actual does not meet intent in this case.
Author: GEFISWN Return to Forum  Refresh 2010-02-01 08.34.19
QCMDCHK would still return the command string with the generic file name!
Author: TFisher Return to Forum  Refresh 2010-02-01 08.07.55
Use QCAPCMD to prompt and then to execute the command.
Author: GEFISWN Return to Forum  Refresh 2010-02-01 07.10.12
QCMDCHK would still return the command string with the generic file name!
Author: TFisher Return to Forum  Refresh 2010-02-01 06.52.21
Why not use QCMDCHK (or QCAPCMD) to prompt the user.  The command string will 
be returned to you and then you may easily extract the file name entered by the 
user before you execute the copy using QCMDEXC (or QCAPCMD).
Author: GEFISWN Return to Forum  Refresh 2010-02-01 04.24.35
Hello All,

I’m despairing on a problem with the QMHRCVPM API.

I prepare a COPY command in a RPG program with a generic file name
In the OBJ parameter and perform it by using QCMDEXC.
It works fine: The command does a prompting and the user may select a certain
file name which is then copied.

But now I want to know in my program, which file was actually selected by the 
user.
I tried to get the message ID CPCA087 which is shown in the log and which 
contains the full pathnames of the copy command in the message data.
I used the QMCRCVPM API in a loop and I tried all stack counts from 0 up to x –
 but in vain.

The interesting fact is:
When I do exactly the same with a non-generic file name in the OBJ parameter, 
I get the CPCA087 by QMHRCVPM by the very first time (with stack count 0).

What I’m doing wrong?
Thanks in advance for every idea or hint.
Regards,
Werner Noll
Your reply | top | Return to Forum | ascending | descending
      Name:
    
By pressing you agree to the
forum guidelines
      Note: Your message is limited to 3500 characters.