02-27-2018 11:05 AM - edited 02-27-2018 11:05 AM
Here's my code:
%sysfunc(ifc(%sysfunc(libref(LIBNAME)) ,%nrstr(%put ERROR: LIBNAME Libref does not exist.; %goto exit;) ,%nrstr(%put NOTE: LIBNAME Libref exists.;) ));
My issue is of course that the %NRSTR is causing an issue with the %goto statement:
ERROR: The %GOTO statement is not valid in open code.
%NRSTR must exist to allow the 'ifc' to properly run the true/false statements. Without %NRSTR, ifc executes all of the statements regardless of the outcome.
%unquote, %bquote %nrbquote %str etc etc have all been used to varying degrees of failure. Any idea how I break that portion of the code out of the %NRSTR to allow the %GOTO to work?
02-27-2018 11:17 AM
No, I think your problem is in understanding the difference between Base SAS code and Macro code. The log is telling you that you can't do macro code in datastep. What you likely want is:
%if %sysfunc(libref(LIBRARY)) %then %do; %put NOTE: LIBNAME Libref exists; %end; %else %do; %put ERROR: LIBNAME does not exist; %end;
02-27-2018 11:35 AM - edited 02-27-2018 11:35 AM
I can't promise how this will work in the context of your macro, but the usual way to mask the effect of % within %NRSTR is to refer to the % as %%:
,%nrstr(%%put ERROR: LIBNAME Libref does not exist.; %%goto exit; )
There is the possibility of needing to %unquote, but first try it without %unquote to see if that will work.
02-27-2018 11:39 AM
So basically everything works apart from the %goto. I've had various methods of running this little checker, usually the end result would be a %let statement instead of this %goto. That works fine.
Essentially, the only problem is the %goto. There's no need for double %% because I'm not trying to escape anything (that's not what NRSTR is doing here). In fact, I want the %GOTO to work, and in theory it does, but SAS is seeing it outside of the context of it being inside of a %macro. I could literally write this statement anywhere else right now and it would work, just not inside of the %NRSTR.
I've also tried UNQUOTE around the %goto bit but EGuide acts very strange - clearly it's causing a mismatch of some sorts and EGuide has no idea how to compile and run the entire macro.
02-27-2018 11:51 AM
Unfortunately, next suggestion would be to follow the @RW9 advice and get rid of IFC. There should be no problem using %goto in this context:
%put ERROR: LIBNAME does not exist;
02-27-2018 11:48 AM - edited 02-27-2018 11:48 AM
Question seems silly.
For %GOTO to work you need to be in a macro. If you are in a macro then why the heck are you using data step function IFC instead of just use %IF?
Are you trying to see if you can build a computed %GOTO?
02-28-2018 02:00 AM
Approach is 50% programmatic and 50% cosmetic. I've replaced it with a %let error = 1 and then I query this later. There's more than one of these statements so I just let them all run and now I query the outcome afterwards. %goto is now called by its own %if error = 1 %then...
02-28-2018 03:37 AM
The %goto statement can only be used inside a macro. However, even inside a macro you will get the same message when trying to use %goto like that (because the statement has not been compiled as part of the macro). If you are inside a macro, there is ho need to make things so complicated, though, just use:
%if %sysfunc(libref(libname)) %then %do; %put ERROR: LIBNAME Libref does not exist.;
%put NOTE: LIBNAME Libref exists.;
Except that unless you have some cleanup code that you want to execute at the %exit label, you could just use %return to stop macro execution.
02-28-2018 03:41 AM
Thanks for that, I'd been using %if %then %do for a long time but wanted to use IFC more after seeing (and using) some very good examples. Looks like that's just not possible when calling another macro function but everything else works without issue. Shame, it's the only time I ever needed to use %goto as well.