0
votes

I'm trying to call a MACRO on SAS CI (using a Node Process) but I'm receiving a error message (1012 or 3000) when I tried to execute. This code is working perfect on SAS Enterprise Guide.

I tried remove the "call execute" syntax, but I did not success.

DATA _NULL_ ;
SET SMS_TEMP END = EOF ;
  IF _N_ = 1 THEN DO UNTIL (EOF);
    %build_JSON;
  END ;
     PUT 'Complete';
  STOP ;
RUN ;

Code full:

DATA _NULL_ ;
SET SMS_TEMP END = EOF ;
  IF _N_ = 1 THEN DO UNTIL (EOF);

    CALL EXECUTE('%build_JSON');
  END ;
     PUT 'FINAL';
  STOP ;
RUN ;

%macro build_JSON;
FILENAME CODE TEMP;
    DATA _NULL_;
    SET SMS_TEMP;
    FILE CODE ;
      PUT 
          'WRITE VALUES "TP_SMS" ' CODSMS :$QUOTE. ';' 
        / 'WRITE VALUES "NM_REMETENTESMS" ' REMETENTE :$QUOTE. ';'
        / 'WRITE VALUES "NR_TELEFONECELULARSMS" ' MOBILE :$QUOTE. ';'
        / 'WRITE VALUES "TX_MENSAGEMSMS" ' MSGTEXT :$QUOTE. ';'
        / 'WRITE VALUES "DT_PARAENVIOSMS" ' DATAPARA  :$QUOTE. ';'
        / 'WRITE VALUES "DT_LIMITEENVIOSMS" ' DATALIMI  :$QUOTE. ';'
        / 'WRITE VALUES "DS_CHAVEORIGEMSMS" ' RESP :$QUOTE. ';'
        ;
    RUN;

    PROC JSON OUT="%SYSFUNC(GETOPTION(WORK))/TEST.JSON" PRETTY KEYS NOSASTAGS;
      WRITE OPEN OBJECT; 
      %INCLUDE CODE;
      WRITE CLOSE;   
    RUN;

FILENAME CODE CLEAR;
%MEND build_JSON;

I expect to working with macros on SAS CI (using SAS Code on Node Process).

How can I do it?

I'll try to explain exactly what I needed: I have a dataset that I need create a JSON file for each line from my dataset. After I'll call another macro with a API process. My loop should be: Read (1), Create out JSON File (2), execute the API Macro (3). Exclude the file out (json), and find for the next register;

3
You need to define the macro before you call it. - Tom
You have only showed partial code for the second step, creating a JSON file from a dataset. What are you going to do with the JSON file? Does what you do with it produce any outputs that you need to agregate? - Tom

3 Answers

0
votes

First make sure you define the macro before you call it.

Second your macro is just doing the same thing every time so there is no sense it calling multiple times.

So why have a macro at all? Why not just call the code that the macro is generating?

Or perhaps you want to define your macro to take an input parameter? Such as the name of the dataset to convert to JSON? If so where is the list of dataset going to come from?

Note that your first step cannot work since your macro generates multiple steps. The first PROC or DATA statement generated will end your data step in the middle of definition of the DO/END block so it will fail since SAS will never see a closing END for the opening DO.

0
votes

I did some adjusts in my code:

DATA _NULL_ ;
IF _N_ = 1 THEN DO UNTIL (EOF);
  SET SMS_TEMP END = EOF ;
   PUT 'Number line:' NumbLINE;
   CALL SYMPUTX('NRL',NumbLINE);
   CALL SYMPUTX('RESPTRACKING',RESP);
   CALL EXECUTE('%BUILD_JSON');
   /*CALL EXECUTE('%CALLAPI');        --- In dev*/
   /*CALL EXECUTE('%DELETEFILE');     --- In dev*/
  END ; 
  ELSE DO;
     PUT 'FINISH';
  END;
RUN ;

This code above is responsible to call all my MACROS one by one until end of file.

%MACRO BUILD_JSON;
FILENAME CODE TEMP;
    DATA _NULL_;
    SET SMS_TEMP;
    WHERE NROLINHA EQ &NRL.;
    FILE CODE ;
      PUT 
          'WRITE VALUES "PITP_SMS" ' CODSMS :$QUOTE. ';' 
        / 'WRITE VALUES "PINM_REMETENTESMS" ' REMETENTE :$QUOTE. ';'
        / 'WRITE VALUES "PINR_TELEFONECELULARSMS" ' MOBILE :$QUOTE. ';'
        / 'WRITE VALUES "PITX_MENSAGEMSMS" ' MSGTEXT :$QUOTE. ';'
        / 'WRITE VALUES "PIDT_PARAENVIOSMS" ' DATAPARA  :$QUOTE. ';'
        / 'WRITE VALUES "PIDT_LIMITEENVIOSMS" ' DATALIMI  :$QUOTE. ';'
        / 'WRITE VALUES "PIDS_CHAVEORIGEMSMS" ' RESP :$QUOTE. ';'
        ;
    RUN;


    PROC JSON OUT="%SYSFUNC(GETOPTION(WORK))/TEST.JSON" PRETTY KEYS NOSASTAGS;
      WRITE OPEN OBJECT; 
      %INCLUDE CODE;
      WRITE CLOSE;   
    RUN;
FILENAME CODE CLEAR;
%MEND BUILD_JSON;

I expect create a routine to Create a JSON file ->then-> Call API Macro to send this JSON ->then-> Exclude this File ->then-> Repeat. For each line of my dataset I'll call this looping process and it seems working as well at least on SAS Enterprise Guide.

This problem occurs just when I tried execute this code on SAS Customer Intelligence (CI) trought a process node.

0
votes

When calling a macro from CALL EXECUTE it will immediately execute up to a point where code gen will occur. This can be confusing to novice users of the feature and has side effects discussed in documentation and conference papers.

To explicitly stack macro invocation statements so they only occur after the step completes, the EXECUTE should use an argument that %NRSTR wraps the macro invocation.

call execute ('%NRSTR(the source code that invokes the macro)');