如何在CL程序中运行SQL(AS400)

时间:2017-01-11 19:15:45

标签: sql ibm-midrange rpgle

让我先说一下我对AS400和RPGLE以及CL编程非常陌生。我非常了解SQL,但在使用AS400 时却没有。)

这看起来应该很简单。

在年终,我们必须将仓库表更新为新的当年。这是一个手动过程,转到STRSQL并运行

 update rco set ccfscy = '2017' where crsts = 'A'

这是过去40年来同一个人所做的,他们现在正在退休。我的老板希望这个成为一个CL程序,在没有人手动运行STRSQL命令的情况下完成它,并且它可以集成到年终过程中。

所有CL程序所要做的就是提示您想要更改仓库文件的年份,并在屏幕上输入日期后,它将运行SQL程序并根据SQL命令更新记录。

有人可以指出我可以了解更多关于使用CL程序完成此过程的方向吗?

谢谢。

Thomas J Cusick,系统程序员

3 个答案:

答案 0 :(得分:5)

假设您使用的是当前支持的IBM i ..

版本

IBM在几个版本之前添加了一个RUNSQL CL命令......

完整的CL程序看起来如此:

pgm
  runsql sql('update rco set ccfscy = ''2017'' where crsts = ''A''')
endpgm

但如果你把这一年作为一个参数来传播会更好......

pgm parm(&year)
  dcl &year *char 4
  dcl &stmt *char 50
  /* using &quote makes life easier than doubling quote literals */
  dcl &quote *char 1 value('''')

  chgvar &stmt value('update rco set ccfscy =' *cat &quote *cat &year *cat +
     &quote *cat 'where crsts = ' *cat &quote *cat 'A' *cat &quote)

  runsql sql(&stmt)

endpgm

答案 1 :(得分:1)

使用RPGLE和DDS代替CL或QMQRY的一个非常简单的例子如下所示:

显示文件:

 A                                      INDARA
 A          R DSPLY                     WINDOW(*DFT 7 35)
 A                                      WDWTITLE((*TEXT 'Year End Process')-
 A                                       *TOP *CENTER)
 A                                      CF03(03)
 A                                  2  2'Type values, press Enter.'
 A                                      COLOR(BLU)
 A                                  4  5'Current Year :'
 A                                      COLOR(WHT)
 A            CURYR          4Y 0B  4 22EDTCDE(4)
 A  30                                  ERRMSG('Invalid Year')
 A                                  6  2'F3=Exit'

RPGLE

   ctl-opt Option(*SrcStmt : *NoDebugIo: *NoUnref)
           DftActGrp(*No) ActGrp(*New)
           Main(main);

   // display file and indicators
   dcl-f prompt Workstn Indds(Indicators);
   dcl-ds Indicators Len(99);
     F3Pressed      Ind Pos(3);
     InvalidYear    Ind Pos(30);
     Errors         Ind Pos(30) Dim(10);
   end-ds;

   dcl-proc main;

     dcl-s ContinueTransaction   Ind Inz(*On);
     dcl-s CurrentYear           Int(5) Inz(0);

     CurrentYear = %subdt(%date(): *YEARS);
     curyr = CurrentYear;
     dow ContinueTransaction;
       exfmt dsply;
       ContinueTransaction = *Off;
       Errors = *Off;
       select;
         when F3Pressed;
         when curyr >= CurrentYear - 1 and
              curyr <= CurrentYear + 1;
           exec sql
             update rco
               set ccfscdy = :curyr
               where crsts = 'A';
         other;
           InvalidYear = *On;
           ContinueTransaction = *On;
       endsl;
     enddo;

     close prompt;
     return;
   end-proc;

这会将当前年份默认为提示,并在输入的年份与当前年份相差太远时提供消息。不像QMQRY解决方案那么快速和肮脏,但实际上并非如此复杂,并且一旦拥有它,您就可以复制并更改提示,验证和SQL到您的内容。

答案 2 :(得分:0)

谢谢查尔斯,这有助于...... 同时,我的老板带着他实际上正在寻找的一个例子来找我,以下是我最终做的事情。

首先我创建了一个Type * QMQRY的File CLD @ 91Q1,这个文件保存了实际的SQL语句......

UPDATE &GWHRE.RCO SET CCFSCY = &SELYEAR WHERE CRSTS = 'A'

其次,我创建了一个调用CLD @ 91Q1查询的XCLP

...

/*********************************************************************/  
/* CALL SQL TO UPDATE THE COMPANY RECORDS WITH THE CURRENT YEAR      */  
/*********************************************************************/  

         CHGVAR     VAR(&SELYEAR)   VALUE(&GYEAR)                    
         STRQMQRY   QMQRY(*LIBL/CLD@91Q1) NAMING(*SYS) +             
                      SETVAR((SELYEAR &SELYEAR) (GWHRE &GWHRE))      
...

最后我创建了XDSPF文件,为用户提供了输入所需信息的位置。

看着这看起来有点令人费解,但这就是Boss想要的,所以这就是老板所得到的。

我认为这是一个很好的练习,我可以看到在更复杂的SQL语句中使用这种过程。