62 %macro mv_createwebservice(path=
64 ,desc=Created by the mv_createwebservice.sas macro
67 ,access_token_var=ACCESS_TOKEN
68 ,grant_type=sas_services
75 %
if &grant_type=detect %then %
do;
76 %
if %symexist(&access_token_var) %then %let grant_type=authorization_code;
77 %
else %let grant_type=sas_services;
79 %
if &grant_type=sas_services %then %
do;
80 %let oauth_bearer=oauth_bearer=sas_services;
81 %let &access_token_var=;
83 %put &sysmacroname: grant_type=&grant_type;
86 %mp_abort(iftrue=(&grant_type ne authorization_code and &grant_type ne password
87 and &grant_type ne sas_services
90 ,msg=%str(Invalid value
for grant_type: &grant_type)
92 %mp_abort(iftrue=(%mf_isblank(&path)=1)
94 ,msg=%str(path value must be provided)
96 %mp_abort(iftrue=(%length(&path)=1)
98 ,msg=%str(path value must be provided)
100 %mp_abort(iftrue=(%mf_isblank(&name)=1)
102 ,msg=%str(name value must be provided)
105 options noquotelenmax;
107 *
remove any trailing slash ;
108 %
if "%substr(&path,%length(&path),1)" =
"/" %then
109 %let path=%substr(&path,1,%length(&path)-1);
112 %put &sysmacroname: Path &path being checked / created;
113 %mv_createfolder(path=&path)
116 %let base_uri=%mf_getplatform(VIYARESTAPI);
120 %let fname1=%mf_getuniquefileref();
121 proc http method=
'GET' out=&fname1 &oauth_bearer
122 url=
"&base_uri/folders/folders/@item?path=&path";
123 %
if &grant_type=authorization_code %then %
do;
124 headers
"Authorization"=
"Bearer &&&access_token_var";
127 %
if &debug %then %
do;
134 %mp_abort(iftrue=(&SYS_PROCHTTP_STATUS_CODE ne 200)
136 ,msg=%str(&SYS_PROCHTTP_STATUS_CODE &SYS_PROCHTTP_STATUS_PHRASE)
141 %let libref1=%mf_getuniquelibref();
142 libname &libref1 JSON fileref=&fname1;
146 if rel=
'members' then call symputx(
'membercheck',quote(
"&base_uri"!!trim(href)),
'l');
147 else if rel=
'self' then call symputx(
'parentFolderUri',href,
'l');
151 call symputx(
'folderid',
id,
'l');
154 %let fname2=%mf_getuniquefileref();
155 proc http method=
'GET'
158 url=%unquote(%superq(membercheck));
160 %
if &grant_type=authorization_code %then %
do;
161 "Authorization"=
"Bearer &&&access_token_var"
163 'Accept'=
'application/vnd.sas.collection+json'
164 'Accept-Language'=
'string';
165 %
if &debug=1 %then %
do;
170 %mp_abort(iftrue=(&SYS_PROCHTTP_STATUS_CODE ne 200)
172 ,msg=%str(&SYS_PROCHTTP_STATUS_CODE &SYS_PROCHTTP_STATUS_PHRASE)
175 %
if %upcase(&replace)=YES %then %
do;
176 %mv_deletejes(path=&path, name=&name)
181 %let libref2=%mf_getuniquelibref();
182 libname &libref2 JSON fileref=&fname2;
183 %local exists; %let exists=0;
186 if contenttype=
'jobDefinition' and upcase(name)=
"%upcase(&name)" then
187 call symputx(
'exists',1,
'l');
189 %mp_abort(iftrue=(&exists=1)
191 ,msg=%str(Job &name already exists in &path)
193 libname &libref2 clear;
198 %let fname3=%mf_getuniquefileref();
200 file &fname3 TERMSTR=
' ';
201 length
string $32767;
202 string=cats(
'{"version": 0,"name":"'
204 ,
'","type":"Compute","parameters":[{"name":"_addjesbeginendmacros"'
205 ,
',"type":"CHARACTER","defaultValue":"false"}');
206 context=quote(cats(symget(
'contextname')));
207 if context ne
'""' then
do;
208 string=cats(
string,
',{"version": 1,"name": "_contextName","defaultValue":'
209 ,context,
',"type":"CHARACTER","label":"Context Name","required": false}');
211 string=cats(
string,
'],"code":"');
220 filename sasjs temp lrecl=3000;
223 put
"/* Created on %sysfunc(datetime(),datetime19.) by &sysuserid */";
226 put
'%macro mp_jsonout(action,ds,jref=_webout,dslabel=,fmt=Y,engine=PROCJSON,dbg=0 ';
227 put
')/*/STORE SOURCE*/; ';
228 put
'%put output location=&jref; ';
229 put
'%if &action=OPEN %then %do; ';
230 put
' data _null_;file &jref encoding=''utf-8''; ';
231 put
' put ''{"START_DTTM" : "'' "%sysfunc(datetime(),datetime20.3)" ''"''; ';
234 put
'%else %if (&action=ARR or &action=OBJ) %then %do; ';
235 put
' options validvarname=upcase; ';
236 put
' data _null_;file &jref mod encoding=''utf-8''; ';
237 put
' put ", ""%lowcase(%sysfunc(coalescec(&dslabel,&ds)))"":"; ';
239 put
' %if &engine=PROCJSON %then %do; ';
240 put
' data;run;%let tempds=&syslast; ';
241 put
' proc sql;drop table &tempds; ';
242 put
' data &tempds /view=&tempds;set &ds; ';
243 put
' %if &fmt=N %then format _numeric_ best32.;; ';
244 put
' proc json out=&jref pretty ';
245 put
' %if &action=ARR %then nokeys ; ';
246 put
' ;export &tempds / nosastags fmtnumeric; ';
248 put
' proc sql;drop view &tempds; ';
250 put
' %else %if &engine=DATASTEP %then %do; ';
251 put
' %local cols i tempds; ';
252 put
' %let cols=0; ';
253 put
' %if %sysfunc(exist(&ds)) ne 1 & %sysfunc(exist(&ds,VIEW)) ne 1 %then %do; ';
254 put
' %put &sysmacroname: &ds NOT FOUND!!!; ';
257 put
' data _null_;file &jref mod ; ';
258 put
' put "["; call symputx(''cols'',0,''l''); ';
259 put
' proc sort data=sashelp.vcolumn(where=(libname=''WORK'' & memname="%upcase(&ds)")) ';
263 put
' data _null_; ';
264 put
' set _last_ end=last; ';
265 put
' call symputx(cats(''name'',_n_),name,''l''); ';
266 put
' call symputx(cats(''type'',_n_),type,''l''); ';
267 put
' call symputx(cats(''len'',_n_),length,''l''); ';
268 put
' if last then call symputx(''cols'',_n_,''l''); ';
271 put
' proc format; /* credit yabwon for special null removal */ ';
272 put
' value bart ._ - .z = null ';
273 put
' other = [best.]; ';
275 put
' data;run; %let tempds=&syslast; /* temp table for spesh char management */ ';
276 put
' proc sql; drop table &tempds; ';
277 put
' data &tempds/view=&tempds; ';
278 put
' attrib _all_ label='''';
';
279 put ' %
do i=1 %to &cols;
';
280 put ' %
if &&type&i=
char %then %
do;
';
281 put ' length &&name&i $32767;
';
282 put ' format &&name&i $32767.;
';
286 put ' format _numeric_ bart.;
';
287 put ' %
do i=1 %to &cols;
';
288 put ' %
if &&type&i=
char %then %
do;
';
289 put ' &&name&i=
''"''!!trim(prxchange(''s/"/\
"/'',-1, ';
290 put ' prxchange(''s/''!!''0A''x!!''/\n/'',-1, ';
291 put ' prxchange(''s/''!!''0D''x!!''/\r/'',-1, ';
292 put ' prxchange(''s/''!!''09''x!!''/\t/'',-1, ';
293 put ' prxchange(''s/\\/\\\\/'',-1,&&name&i) ';
294 put ' )))))!!''"'';
';
299 put ' filename _sjs temp lrecl=131068 encoding=
''utf-8
'';
';
300 put ' data _null_; file _sjs lrecl=131068 encoding=
''utf-8
'' mod;
';
301 put ' set &tempds;
';
302 put ' if _n_>1 then put
"," @; put
';
303 put ' %
if &action=ARR %then
"[" ; %
else "{" ;
';
304 put ' %
do i=1 %to &cols;
';
305 put ' %
if &i>1 %then
"," ;
';
306 put ' %
if &action=OBJ %then
"""&&name&i"":" ;
';
309 put ' %
if &action=ARR %then
"]" ; %
else "}" ; ;
';
311 put ' drop view &tempds;
';
313 put ' data _null_;
';
314 put ' length filein 8 fileid 8;
';
315 put ' filein = fopen(
"_sjs",
''I
'',1,
''B
'');
';
316 put ' fileid = fopen(
"&jref",
''A
'',1,
''B
'');
';
317 put ' rec =
''20
''x;
';
318 put ' do while(fread(filein)=0);
';
319 put ' rc = fget(filein,rec,1);
';
320 put ' rc = fput(fileid, rec);
';
321 put ' rc =fwrite(fileid);
';
323 put ' rc = fclose(filein);
';
324 put ' rc = fclose(fileid);
';
326 put ' filename _sjs clear;
';
327 put ' data _null_; file &jref mod encoding=
''utf-8
'';
';
333 put '%
else %
if &action=CLOSE %then %
do;
';
334 put ' data _null_;file &jref encoding=
''utf-8
'';
';
339 put '%macro mv_webout(action,ds,fref=_mvwtemp,dslabel=,fmt=Y);
';
340 put '%global _webin_file_count _webin_fileuri _debug _omittextlog _webin_name
';
341 put ' sasjs_tables SYS_JES_JOB_URI;
';
342 put '%
if %index(
"&_debug",log) %then %let _debug=131;
';
344 put '%local i tempds;
';
345 put '%let action=%upcase(&action);
';
347 put '%
if &action=FETCH %then %
do;
';
348 put ' %
if %upcase(&_omittextlog)=FALSE or %str(&_debug) ge 131 %then %
do;
';
349 put ' options mprint notes mprintnest;
';
352 put ' %
if not %symexist(_webin_fileuri1) %then %
do;
';
353 put ' %let _webin_file_count=%eval(&_webin_file_count+0);
';
354 put ' %let _webin_fileuri1=&_webin_fileuri;
';
355 put ' %let _webin_name1=&_webin_name;
';
359 put ' %
if %length(&sasjs_tables.XX)>2 %then %
do;
';
360 put ' filename _sasjs
"%sysfunc(pathname(work))/sasjs.lua";
';
361 put ' data _null_;
';
362 put ' file _sasjs;
';
363 put ' put
''s=sas.symget(
"sasjs_tables")
'';
';
364 put ' put
''if(s:sub(1,7) ==
"%nrstr(")
'';
';
365 put ' put
''then
'';
';
366 put ' put
'' tablist=s:sub(8,s:len()-1)
'';
';
367 put ' put
''else'';
';
368 put ' put
'' tablist=s
'';
';
369 put ' put
''end
'';
';
370 put ' put
''for i = 1,sas.countw(tablist)
'';
';
371 put ' put
''do '';
';
372 put ' put
'' tab=sas.scan(tablist,i)
'';
';
373 put ' put
'' sasdata=
""'';
';
374 put ' put
'' if (sas.symexist(
"sasjs"..i..
"data0")==0)
'';
';
375 put ' put
'' then
'';
';
377 put ' put
'' s=sas.symget(
"sasjs"..i..
"data")
'';
';
378 put ' put
'' if(s:sub(1,7) ==
"%nrstr(")
'';
';
379 put ' put
'' then
'';
';
380 put ' put
'' sasdata=s:sub(8,s:len()-1)
'';
';
381 put ' put
'' else'';
';
382 put ' put
'' sasdata=s
'';
';
383 put ' put
'' end
'';
';
384 put ' put
'' else'';
';
385 put ' put
'' for d = 1, sas.symget(
"sasjs"..i..
"data0")
'';
';
386 put ' put
'' do'';
';
387 put ' put
'' s=sas.symget(
"sasjs"..i..
"data"..d)
'';
';
388 put ' put
'' if(s:sub(1,7) ==
"%nrstr(")
'';
';
389 put ' put
'' then
'';
';
390 put ' put
'' sasdata=sasdata..s:sub(8,s:len()-1)
'';
';
391 put ' put
'' else'';
';
392 put ' put
'' sasdata=sasdata..s
'';
';
393 put ' put
'' end
'';
';
394 put ' put
'' end
'';
';
395 put ' put
'' end
'';
';
396 put ' put
'' file = io.open(sas.pathname(
"work")..
"/"..tab..
".csv",
"a")
'';
';
397 put ' put
'' io.output(file)
'';
';
398 put ' put
'' io.write(sasdata)
'';
';
399 put ' put
'' io.close(file)
'';
';
400 put ' put
''end
'';
';
402 put ' %inc _sasjs;
';
405 put ' %
do i=1 %to %sysfunc(countw(&sasjs_tables));
';
406 put ' %local table; %let table=%scan(&sasjs_tables,&i);
';
407 put ' data _null_;
';
408 put ' infile
"%sysfunc(pathname(work))/&table..csv" termstr=crlf ;
';
410 put ' if _n_=1 then call symputx(
''input_statement
'',_infile_);
';
412 put ' data &table;
';
413 put ' infile
"%sysfunc(pathname(work))/&table..csv" firstobs=2 dsd termstr=crlf;
';
414 put ' input &input_statement;
';
418 put ' %
else %
do i=1 %to &_webin_file_count;
';
421 put ' filename indata filesrvc
"&&_webin_fileuri&i" lrecl=999999;
';
422 put ' data _null_;
';
423 put ' infile indata termstr=crlf lrecl=32767;
';
425 put ' if _n_=1 then call symputx(
''input_statement
'',_infile_);
';
426 put ' %
if %str(&_debug) ge 131 %then %
do;
';
427 put ' if _n_<20 then putlog _infile_;
';
434 put ' data &&_webin_name&i;
';
435 put ' infile indata firstobs=2 dsd termstr=crlf ;
';
436 put ' input &input_statement;
';
438 put ' %let sasjs_tables=&sasjs_tables &&_webin_name&i;
';
441 put '%
else %
if &action=OPEN %then %
do;
';
443 put ' OPTIONS NOBOMFILE;
';
444 put ' %
if "X&SYS_JES_JOB_URI.X"=
"XX" %then %
do;
';
445 put ' filename _webout temp lrecl=999999 mod;
';
448 put ' filename _webout filesrvc parenturi=
"&SYS_JES_JOB_URI" ';
449 put ' name=
"_webout.json" lrecl=999999 mod;
';
453 put ' %
if %upcase(&fref) ne _WEBOUT %then %
do;
';
454 put ' filename &fref temp lrecl=999999 permission=
''A::u::rwx,A::g::rw-,A::o::---
'' mod;
';
458 put ' data _null_;file &fref;
';
459 put ' put
''{
"START_DTTM" :
"'' "%sysfunc(datetime(),datetime20.3)
" ''"'';
';
462 put '%
else %
if &action=ARR or &action=OBJ %then %
do;
';
463 put ' %mp_jsonout(&action,&ds,dslabel=&dslabel,fmt=&fmt
';
464 put ' ,jref=&fref,engine=PROCJSON,dbg=%str(&_debug)
';
467 put '%
else %
if &action=CLOSE %then %
do;
';
468 put ' %
if %str(&_debug) ge 131 %then %
do;
';
470 put ' options obs=10;
';
471 put ' data;run;%let tempds=%scan(&syslast,2,.);
';
472 put ' ods output Members=&tempds;
';
473 put ' proc datasets library=WORK memtype=data;
';
474 put ' %local wtcnt;%let wtcnt=0;
';
475 put ' data _null_;
set &tempds;
';
476 put ' if not (name =:
"DATA");
';
478 put ' call symputx(
''wt
''!!left(i),name);
';
479 put ' call symputx(
''wtcnt
'',i);
';
480 put ' data _null_; file &fref mod; put
",""WORK"":{";
';
481 put ' %
do i=1 %to &wtcnt;
';
482 put ' %let wt=&&wt&i;
';
483 put ' proc contents noprint data=&wt
';
484 put ' out=_data_ (keep=name type length format:);
';
485 put ' run;%let tempds=%scan(&syslast,2,.);
';
486 put ' data _null_; file &fref mod;
';
487 put ' dsid=open(
"WORK.&wt",
''is
'');
';
488 put ' nlobs=attrn(dsid,
''NLOBS
'');
';
489 put ' nvars=attrn(dsid,
''NVARS
'');
';
490 put ' rc=close(dsid);
';
491 put ' if &i>1 then put
'',
''@;
';
492 put ' put
" ""&wt"" : {";
';
493 put ' put
''"nlobs":
'' nlobs;
';
494 put ' put
'',
"nvars":
'' nvars;
';
495 put ' %mp_jsonout(OBJ,&tempds,jref=&fref,dslabel=colattrs,engine=DATASTEP)
';
496 put ' %mp_jsonout(OBJ,&wt,jref=&fref,dslabel=first10rows,engine=DATASTEP)
';
497 put ' data _null_; file &fref mod;put
"}";
';
499 put ' data _null_; file &fref mod;put
"}";run;
';
503 put ' data _null_;file &fref mod;
';
504 put ' _PROGRAM=quote(trim(resolve(symget(
''_PROGRAM
''))));
';
505 put ' put
",""SYSUSERID"" : ""&sysuserid"" ";
';
506 put ' put
",""MF_GETUSER"" : ""%mf_getuser()"" ";
';
507 put ' SYS_JES_JOB_URI=quote(trim(resolve(symget(
''SYS_JES_JOB_URI
''))));
';
508 put ' put
'',
"SYS_JES_JOB_URI" :
'' SYS_JES_JOB_URI ;
';
509 put ' put
",""SYSJOBID"" : ""&sysjobid"" ";
';
510 put ' put
",""_DEBUG"" : ""&_debug"" ";
';
511 put ' put
'',
"_PROGRAM" :
'' _PROGRAM ;
';
512 put ' put
",""SYSCC"" : ""&syscc"" ";
';
513 put ' put
",""SYSERRORTEXT"" : ""&syserrortext"" ";
';
514 put ' put
",""SYSHOSTNAME"" : ""&syshostname"" ";
';
515 put ' put
",""SYSSITE"" : ""&syssite"" ";
';
516 put ' put
",""SYSWARNINGTEXT"" : ""&syswarningtext"" ";
';
517 put ' put
'',
"END_DTTM" :
"'' "%sysfunc(datetime(),datetime20.3)
" ''" '';
';
520 put ' %
if %upcase(&fref) ne _WEBOUT %then %
do;
';
521 put ' data _null_; rc=fcopy(
"&fref",
"_webout");run;
';
528 put '%macro mf_getuser(type=META
';
530 put ' %local user metavar;
';
531 put ' %
if &type=OS %then %let metavar=_secureusername;
';
532 put ' %
else %let metavar=_metaperson;
';
534 put ' %
if %symexist(SYS_COMPUTE_SESSION_OWNER) %then %let user=&SYS_COMPUTE_SESSION_OWNER;
';
535 put ' %
else %
if %symexist(&metavar) %then %
do;
';
536 put ' %
if %length(&&&metavar)=0 %then %let user=&sysuserid;
';
538 put ' %
else %let user=%scan(&&&metavar,1,@);
';
540 put ' %
else %let user=&sysuserid;
';
542 put ' %quote(&user)
';
548 put '%global __program _program;
';
549 put '%let _program=%sysfunc(coalescec(&__program,&_program));
';
551 put '%macro webout(action,ds,dslabel=,fmt=);
';
552 put ' %mv_webout(&action,ds=&ds,dslabel=&dslabel,fmt=&fmt)
';
556 /* insert the code, escaping double quotes and carriage returns */
557 %local x fref freflist;
558 %let freflist= &adapter &precode &code ;
559 %do x=1 %to %sysfunc(countw(&freflist));
560 %let fref=%scan(&freflist,&x);
561 %put &sysmacroname: adding &fref;
563 length filein 8 fileid 8;
564 filein = fopen("&fref","I",1,"B");
565 fileid = fopen("&fname3","A",1,"B");
567 do while(fread(filein)=0);
568 rc = fget(filein,rec,1);
570 rc =fput(fileid,'\');rc =fwrite(fileid);
571 rc =fput(fileid,'"');rc =fwrite(fileid);
573 else if rec='0A
'x then do;
574 rc =fput(fileid,'\
');rc =fwrite(fileid);
575 rc =fput(fileid,'r
');rc =fwrite(fileid);
577 else if rec='0D
'x then do;
578 rc =fput(fileid,'\
');rc =fwrite(fileid);
579 rc =fput(fileid,'n
');rc =fwrite(fileid);
581 else if rec='09
'x then do;
582 rc =fput(fileid,'\
');rc =fwrite(fileid);
583 rc =fput(fileid,'t
');rc =fwrite(fileid);
585 else if rec='5C
'x then do;
586 rc =fput(fileid,'\
');rc =fwrite(fileid);
587 rc =fput(fileid,'\
');rc =fwrite(fileid);
590 rc =fput(fileid,rec);
599 /* finish off the body of the code file loaded to JES */
601 file &fname3 mod TERMSTR=' ';
605 /* now we can create the job!! */
607 %let fname4=%mf_getuniquefileref();
608 proc http method='POST'
612 url="&base_uri/jobDefinitions/definitions?parentFolderUri=&parentFolderUri
";
613 headers 'Content-Type'='application/vnd.sas.job.definition+json'
614 %if &grant_type=authorization_code %then %do;
615 "Authorization
"="Bearer &&&access_token_var
"
617 "Accept
"="application/vnd.sas.job.definition+json
";
618 %if &debug=1 %then %do;
622 /*data _null_;infile &fname4;input;putlog _infile_;run;*/
623 %mp_abort(iftrue=(&SYS_PROCHTTP_STATUS_CODE ne 201)
625 ,msg=%str(&SYS_PROCHTTP_STATUS_CODE &SYS_PROCHTTP_STATUS_PHRASE)
628 filename &fname1 clear;
629 filename &fname2 clear;
630 filename &fname3 clear;
631 filename &fname4 clear;
632 filename &adapter clear;
633 libname &libref1 clear;
635 /* get the url so we can give a helpful log message */
638 if symexist('_baseurl') then do;
639 url=symget('_baseurl');
640 if subpad(url,length(url)-9,9)='SASStudio'
641 then url=substr(url,1,length(url)-11);
642 else url="&systcpiphostname
";
644 else url="&systcpiphostname
";
645 call symputx('url',url);
649 %put &sysmacroname: Job &name successfully created in &path;
651 %put &sysmacroname: Check it out here:;
652 %put &sysmacroname:;%put;
653 %put &url/SASJobExecution?_PROGRAM=&path/&name;%put;