@SASJedi you helped me out last time and I'm integrating in my tool kit the source statement for proc cas code.
https://communities.sas.com/t5/SAS-Programming/datastep-runcode-loading-from-oracle/m-p/799609
I wonder why the source / endource block apparently does not accept 2 data steps or cas actions (I've tried both combinations, neither one worked).
The code only executes the first data step in the block.
proc cas;
function doesTableExist(casLib,casTable);
table.tableExists result=r status=rc / caslib=casLib table=casTable;
tableExists = dictionary(r, "exists");
return tableExists;
end func;
/*
It's easier to write DATA steps in a source block than to write
the code within a string parameter. Use caslib.table_name format
to reference CAS tables when running in CAS.
*/
source myDataStep;
data MKT.DIR_CLIENTES_BI1;
set MKT.DIR_CLIENTES_BI;
format _fec_explotacion ddmmyy10.;
_fec_explotacion=input(put(fec_explotacion, 8.), yymmdd10.);
date_order=-_fec_explotacion;
array temp (*) CIF_NIF COD_PAIS COD_POSTAL COD_PROVINCIA DOMICILIO TIPDOMI TIPOVIA;
array temp1 (*) _numeric_;
missy=(cmiss(of temp[*]) + cmiss(of temp1[*]));
run;
proc cas;
session mysession;
simple.groupByInfo result=r / /* 1 */
includeDuplicates=false,
minFrequency=1,
groupByLimit=1000M,
noVars=false,
casOut={name="DIR_CLIENTES_BI2", replace=true, CASLIB="mkt"},
table={vars={"cif_nif", "date_order", "missy"}, name="DIR_CLIENTES_BI1", CASLIB="mkt",
computedVars={{name='flag'}},
computedVarsProgram='flag =1' };
run;
endsource;
tableExists = doesTableExist("MKT", "DIR_CLIENTES_BI");
if tableExists ^=0 then do;
/* Execute the DATA step code from the source block named myDataStep */
dataStep.runCode result=r status=rc /
code=myDataStep;
end;
run;
Digging deeper, I found this:
https://documentation.sas.com/doc/de/pgmsascdc/9.4_3.5/caspg/n0vsh1uy8gxjodn1p4zg9iw3jwfa.htm
containing this:
- When using CASL, DATA step statements specified after the DATA step RUN statement are ignored by SAS.
and this:
proc cas;
runCode / code =
"
data myData;
put 'inside DATA step';
run;
put 'This statement is ignored' ;
";
run;
quit;
Which means that the runcode action will run a single data step, and nothing more.
Please post the log resulting from running this code.
If I replace the cas action from the second block by an additional data step the result stays the same.
The code does not reveal anything to me.
It doesn't even throw out an error.
I does not create the second table executing only the first data step.
I've tried without success duplicating the source ("myDataStep2") and put the second data step in it. I suppose that this approach is promising but I cannot manage to execute it afterwards.
...then do;
dataStep.runCode result=r status=rc /
code=myDataStep;
dataStep.runCode result=r status=rc /
code=myDataStep2;
end;
proc cas;
function doesTableExist(casLib,casTable);
table.tableExists result=r status=rc / caslib=casLib table=casTable;
tableExists = dictionary(r, "exists");
return tableExists;
end func;
/*
It's easier to write DATA steps in a source block than to write
the code within a string parameter. Use caslib.table_name format
to reference CAS tables when running in CAS.
*/
source myDataStep;
data MKT.DIR_CLIENTES_BI1;
set MKT.DIR_CLIENTES_BI;
format _fec_explotacion ddmmyy10.;
_fec_explotacion=input(put(fec_explotacion, 8.), yymmdd10.);
date_order=-_fec_explotacion;
array temp (*) CIF_NIF COD_PAIS COD_POSTAL COD_PROVINCIA DOMICILIO TIPDOMI TIPOVIA;
array temp1 (*) _numeric_;
missy=(cmiss(of temp[*]) + cmiss(of temp1[*]));
run;
data MKT.DIR_CLIENTES_BI2;
set MKT.DIR_CLIENTES_BI1;
by cif_nif _fec_explotacion missy;
if first.cif_nif;
run;
endsource;
tableExists = doesTableExist("MKT", "DIR_CLIENTES_BI");
if tableExists ^=0 then do;
/* Execute the DATA step code from the source block named myDataStep */
dataStep.runCode result=r status=rc /
code=myDataStep;
end;
run;
1 %studio_hide_wrapper;
82 proc cas;
83
84 function doesTableExist(casLib,casTable);
85 table.tableExists result=r status=rc / caslib=casLib table=casTable;
86 tableExists = dictionary(r, "exists");
87 return tableExists;
88 end func;
89
90 /*
91 It's easier to write DATA steps in a source block than to write
92 the code within a string parameter. Use caslib.table_name format
93 to reference CAS tables when running in CAS.
94 */
95 source myDataStep;
96 data MKT.DIR_CLIENTES_BI1;
97 set MKT.DIR_CLIENTES_BI;
98 format _fec_explotacion ddmmyy10.;
99 _fec_explotacion=input(put(fec_explotacion, 8.), yymmdd10.);
100 date_order=-_fec_explotacion;
101 array temp (*) CIF_NIF COD_PAIS COD_POSTAL COD_PROVINCIA DOMICILIO TIPDOMI TIPOVIA;
102 array temp1 (*) _numeric_;
103 missy=(cmiss(of temp[*]) + cmiss(of temp1[*]));
104 run;
105
106 data MKT.DIR_CLIENTES_BI2;
107 set MKT.DIR_CLIENTES_BI1;
108 by cif_nif _fec_explotacion missy;
109 if first.cif_nif;
110 run;
111
112 endsource;
113
114
115 tableExists = doesTableExist("MKT", "DIR_CLIENTES_BI");
116 if tableExists ^=0 then do;
117 /* Execute the DATA step code from the source block named myDataStep */
118 dataStep.runCode result=r status=rc /
119 code=myDataStep;
120 end;
121 run;
NOTE: Active Session now MYSESSION.
122
123 %studio_hide_wrapper;
134
135
Digging deeper, I found this:
https://documentation.sas.com/doc/de/pgmsascdc/9.4_3.5/caspg/n0vsh1uy8gxjodn1p4zg9iw3jwfa.htm
containing this:
- When using CASL, DATA step statements specified after the DATA step RUN statement are ignored by SAS.
and this:
proc cas;
runCode / code =
"
data myData;
put 'inside DATA step';
run;
put 'This statement is ignored' ;
";
run;
quit;
Which means that the runcode action will run a single data step, and nothing more.
The runcode action is explicitly described as "Runs data step code"; I suspect that your PROC CAS step in the SOURCE/ENDSOURCE block is therefore ignored.
PROC CAS is only valid on the Compute Server for submitting CASL code to CAS for execution. You can't run PROC CAS on the CAS server, so any calls to PROC CAS within a CASL SOURCE block will not be executed.
I know that this has been answered, but I just wanted to mention this from the documentation for PROC CAS:
PROC CAS does not have any required or optional arguments. Once PROC CAS is executed, it will continue running until it reaches one of the following:
At that point, you will have to execute PROC CAS again using the syntax above.
SAS Innovate 2025 is scheduled for May 6-9 in Orlando, FL. Sign up to be first to learn about the agenda and registration!
Learn how use the CAT functions in SAS to join values from multiple variables into a single value.
Find more tutorials on the SAS Users YouTube channel.
Ready to level-up your skills? Choose your own adventure.