FTP refresher part III - iSeries file transfer error checking

The FTP refresher course would not be complete without a discussion of error checking. It is time to introduce a second CL procedure. Refer to the actual ftp procedure as the "first" or calling procedure and the error checking routine as the "second" or called procedure.

In the previous discussion (refresher course part II) the results of the transmission from the file OUTPUT were copied from qgpl/qoutput to a physical file qgpl/ftpout.

The first procedure, the calling procedure, needs a few variables declared. Two are defined as alphanumeric and one is numeric.

DCL       var(&FTPERR)  type(*char) len(1)
DCL       var(&FTPDAT)  type(*char) len(60)
DCL       var(&RECS)      type(*dec) len(10 0)

When the FTP is run and control is passed back the calling procedure should immediately check for an empty file.  If the &RECS is zero then a message is sent and the FTP procedure is terminated.

RTVMBRD       file(qgpl/qoutput) mbr(output) nbrcurrcd(&RECS)
      SNDMSG   MSG('''File not transferred!   No FTP records found in the output file.  +
          See qgpl/qoutput(output) for details''') tousr(*SYSOPR)
      GOTO   cmdlbl(END)

Before calling the error checking procedure we need override to the OUTPUT results file prior to calling the error checking procedure.

OVRDBF   file(OUTPUT) tofile(qgpl/ftpout)

Add a call statement for calling the second procedure.  The first CL will compile, but not run, even if the second procedure does not yet exist. 

CALL     pgm(qgpl/CHKFTP) parm(&ftperr &ftpdat)

Now create/compile the second procedure.

Example of the called procedure CHKFTP:

/* Name: CHKFTP                                                                                                                     */
/* Description:   CHECK FTP FOR ERRORS                                                                            */
              PGM       parm(&ftperr &ftpdat)

/* also define variables in the called error checker  */

               DCL       var(&FTPERR)  type(*char) len(1)
               DCL       var(&FTPDAT)  type(*char) len(60)
               DCL       var(&RECS)      type(*dec) len(10 0)

 /* declare the results file and initialize variables */
             DCLF     file(qgpl/ftpout) rcdfmt(*all)

            CHGVAR   var(&ftpdat) value(*blanks)
            CHGVAR   var(&ftperr) value('N')

/* read through the results and look for error messages*/
            monmsg(CPF0864) exec(RETURN)
            IF cond(%sst(&DATA 1 1) *EQ '4' THEN(DO)
            CHGVAR   var(&ftpdat) value(&DATA)
            CHGVAR   var(&ftperr) value('Y')
            IF cond(%sst(&DATA 1 2) *EQ '53' *OR %sst(&DATA 1 2) *EQ '55') THEN(DO)
            CHGVAR   var(&ftpdat) value(&DATA)
            CHGVAR   var(&ftperr) value('Y')

            GOTO      cmdlbl(RCVF)

The copy of qoutput file is checked for status messages that start with a '4' or '53' or '55' but only legitimate errors should be trapped.  The FTP error codes starting with '4', '53', and '55' denote the transmission has failed.  While extremely rare beware of the possibility that some superfluous messages could start with these characters.  If so the error checker will need to trap at a more detailed level.

If errors are detected the procedure should send a message and end without clearing the work files.  If the transmission is mission critical then further corrective action might be required to ensure completion of the transmission (e.g. manual FTP).

Most problems are noted in the setting up and testing phase.  Automated FTP in production can be very stable but the procedures must always be coordinated with certain changes on the remote system.

Next, the error flag and data parameters are passed back to the calling procedure and checked.

      IF   cond(&FTPERR = 'Y') THEN(DO)
         SNDMSG     MSG('''File not transferred!  Problem with FTP.  +
         Error code ''*CAT &FTPDAT *CAT''. See QGPL/QOUTPUT/OUTPUT for details''') +
         goto  cmdlbl(END)

Finally make sure the main FTP procedure includes the ENDPGM tag.

The intent here is to provide a refresher for your understanding of FTP as opposed to providing cut and paste code.  A basic understanding of FTP is a prerequisite to implementing any of this code.