BookmarkSubscribeRSS Feed
rbettinger
Lapis Lazuli | Level 10

I got tired of receiving error messages from SAS telling me that a particular folder was not authorized to receive output, as in

"WARNING: GPATH or PATH is not a writable directory. It will be ignored.

ERROR: Cannot write image to SGprint. Please ensure that proper disk permissions are set.".
So I wrote %ODS_GRAPHICS, which is designed to create ODS listing and ODS graphics statements to direct graphics output to a specified file in a specified folder. The complete macro code and test code are included in the attached SAS program file.
The macro uses the SAS_EXECFILEPATH macro variable so it must be run either in batch mode (not tested) or interactive mode (requiring the Enhanced Editor).
The argument GPATH_FILENAME specifies the mode of operation:
  • if &GPATH_FILENAME represents a complete Windows pathname, then the graphics output is put into the specified folder.
  • if &GPATH_FILENAME represents a filename only, then the graphics output is put into the folder containing the SAS program from which the %ODS_GRAPHICS macro was invoked.

For example, the macro invocation %ODS_GRAPHICS( "C:\Users\Username\Documents\My SAS Files\TestGraphics\TestODSGraphics.jpg" ) will put output into the TestGraphics folder, and %ODS_GRAPHICS( TestGraphics.tiff ) will put output into the folder containing the program in which the %ODS_GRAPHICS macro was invoked. Note that quotation marks around the name of the output file are optional.

 

Kudos to Art Carpenter, who wrote the original macro %ExecPrg , referenced in https://stackoverflow.com/questions/48199111/get-the-filename-and-filepath-of-the-code-running.

6 REPLIES 6
Tom
Super User Tom
Super User

No file was attached.  But why not just post the code for the macro in the pop-up window that appears when you push the Insert SAS Code button in the forum editor?

Ksharp
Super User

Did you used:

ods listing gpath='c:\temp';

https://blogs.sas.com/content/sgf/2015/11/20/how-to-increase-the-resolution-of-your-sas-graphics-out...

https://blogs.sas.com/content/graphicallyspeaking/2017/06/08/getting-started-output-formats/

 

 

And SAS_EXECFILEPATH macro variable is not working in batch mode (I tested), you need to set parameter  

-set SAS_EXECFILEPATH "c:\temp\"

in batch process file.

PaigeMiller
Diamond | Level 26

I got tired of receiving error messages from SAS telling me that a particular folder was not authorized to receive output, as in

"WARNING: GPATH or PATH is not a writable directory. It will be ignored.

ERROR: Cannot write image to SGprint. Please ensure that proper disk permissions are set.".
 
I have never received this error. What am I missing, can't you just direct the output via ODS HTML or ODS LISTING to a writable directory in your original SAS program (which is what I do)? 
--
Paige Miller
Tom
Super User Tom
Super User

You get that message when your code produces graphs that need to be embedded/linked in the HTML output.

 

Most often is happens when you have not set the GPATH location and it defaults to the current working directory, but that directory is readonly.  Most often for SAS sessions launched for use by Enterprise Guide or SAS/Studio since those typically start with the current working directory some place inside the SAS installation directories which normal SAS users cannot write to.

PaigeMiller
Diamond | Level 26

@Tom wrote:

You get that message when your code produces graphs that need to be embedded/linked in the HTML output.

 

Most often is happens when you have not set the GPATH location and it defaults to the current working directory, but that directory is readonly.  Most often for SAS sessions launched for use by Enterprise Guide or SAS/Studio since those typically start with the current working directory some place inside the SAS installation directories which normal SAS users cannot write to.


Which is why I never see this error message, I always use GPATH when I create graphics.

--
Paige Miller
rbettinger
Lapis Lazuli | Level 10

I apologize for submitting this posting without adequately checking that the SAS macro code was attached to it. I thought that I had included it as an attachment, but apparently I was mistaken. Here is the macro code and test code. Note that the HTML destination appears not to be supported. I am running SAS 9.4 TS Level 1M8 on X64_WIN+PRO platform.

 

%macro ODS_GRAPHICS( GPATH_FILENAME ) / minoperator ;

   /* purpose: direct SAS graphics output into specified folder/file under ODS control
    *
    * GPATH_FILENAME ::= complete Windows path to folder\filename into which to store ODS graphics image
    *                    filename of ODS graphics image created in interactively submitted program
    *
    * Examples of use:
    *    %ODS_GRAPHICS( 'C:\Users\Username\Documents\My SAS Files\ODS Graphics Output\Plot Y vs X.PNG' ) ; *** store image in explicitly-specified directory
    *
    *    %ODS_GRAPHICS( 'Plot Y vs X.jpg' ) ; *** store image in directory in which %ODS_GRAPHICS macro is invoked
    *
    * NOTA BENE: this code works only for SAS running in 1) batch mode or in 2) interactive mode using the Enhanced Editor
    *
    * reference: https://stackoverflow.com/questions/48199111/get-the-filename-and-filepath-of-the-code-running
    *            Art Carpenter created the macro %ExecPrg which has been adapted for use in this macro
    */

   /* fetch complete Windows folder pathname, replace macro name ODS_GRAPHICS with user-specified filename that will contain ODS graphics output */

   %if %sysfunc( getoption( sysin )) ne %str() /* determine mode of operation: batch | interactive */
   %then %do ;
      %let PATHNAME = %sysfunc( getoption( sysin )) ; /* batch execution */
   %end ;
   %else %do ;
      %let PATHNAME = %sysget( SAS_EXECFILEPATH ) ; /* interactive execution */
   %end ;

   %if ^%index( &GPATH_FILENAME, \ ) /* not a Windows path, just filename for ODS graphics output in current working directory */
   %then %do ;
      %let REV_STRING     = %sysfunc( reverse( &PATHNAME )) ;
      %let NDX            = %index( &REV_STRING, \ ) ;
      %let GPATH          = %substr( &REV_STRING, &NDX + 1 ) ;
      %let GPATH          = %sysfunc( reverse( &GPATH )) ;
      %let GPATH_FILENAME = &GPATH.\&GPATH_FILENAME ; /* create complete Windows folder path and ODS output file name */
   %end ;
   
   %let STRING     = %sysfunc( dequote( &GPATH_FILENAME )) ; /* remove quotes, if any, from path\filename.imagetype string */
   %let REV_STRING = %sysfunc( reverse( &STRING )) ;
   %let NDX        = %index( &REV_STRING, . ) ; /* find location of '.' for image type */
   %let IMAGETYPE  = %substr( &REV_STRING, 1, &NDX - 1 ) ; /* parse for image type */

   %let REV_STRING = %substr( &REV_STRING, &NDX + 1 ) ; /* exclude image type */
   %let NDX        = %index( &REV_STRING, \ ) ;
   %let IMAGENAME  = %substr( &REV_STRING, 1, &NDX - 1 ) ;

   %let IMAGETYPE = %upcase( %sysfunc( reverse( &IMAGETYPE ))) ;

   %if ^%eval( &IMAGETYPE in BMP DIB EMF EPS EPSI GIF JFIF JPEG JPG PBM PCD PCL PDF PICT PNG PS STATIC SVG TIFF WMF XBM XPM )
   %then %do ;
      %put /-----------------------------------------------------------------\ ;
      %put | ODS destination not one of BMP, DIB, EMF, EPS, EPSI, GIF, JFIF, | ;
      %put |     JPEG, JPG, PBM, PCD, PCL, PDF, PICT, PNG, PS, STATIC, SVG,  | ;
      %put |     TIFF, WMF, XBM, XPM.                                        | ;
      %put | Terminating forthwith.                                          | ;
      %put \-----------------------------------------------------------------/ ;

      %goto EXIT ;
  %end ; 

   /* quote gpath and imagename macro strings */
   %let GPATH     = %substr( &REV_STRING, &NDX + 1 ) ;
   %let GPATH     = %sysfunc( quote( &GPATH )) ;
   %let IMAGENAME = %sysfunc( quote( &IMAGENAME )) ;

   /* assemble ODS statements */
   ods listing gpath=%sysfunc( reverse( &GPATH )) ;
   ods graphics / imagename=%sysfunc( reverse( &IMAGENAME )) imagefmt=&IMAGETYPE ;

%EXIT:

%mend ODS_GRAPHICS ;

/* test complete Windows path/filename, imagefmt=png */

%ODS_GRAPHICS( 'C:\Users\UserName\Documents\My SAS Files\TestGraphics\ods_graphics_test.png' ) ;

proc sgplot data=sashelp.class ; scatter x=height y=weight ; quit ;

proc print data=sashelp.class ; run ;

/* test ODS graphics filename only, imagefmt=tiff */

%ODS_GRAPHICS( filename_only_ods_graphics_test.tiff ) ;

proc sgplot data=sashelp.class ; scatter x=height y=weight ; quit ;

proc print data=sashelp.class ; run ;

/* test ODS graphics filename only, imagefmt=html THIS ODS DESTINATION IS NOT SUPPORTED FOR LISTING OUTPUT */

%ODS_GRAPHICS( filename_only_ods_graphics_test.html )

proc sgplot data=sashelp.class ; scatter x=height y=weight ; quit ;

proc print data=sashelp.class ; run ;

/* note that separate non-macro test code for HTML destination results in error */

ods listing gpath='C:\Users\UserName\Documents\My SAS Files\TestGraphics\ods_graphics_test.html';
1157 ods graphics / imagename="ods_graphics_test" imagefmt=html;
----
22
76
ERROR 22-322: Syntax error, expecting one of the following: BMP, DIB, EMF, EPS, EPSI, GIF, JFIF, JPEG, JPG, PBM, PCD, PCL, PDF,
PICT, PNG, PS, STATIC, SVG, TIFF, WMF, XBM, XPM.
ERROR 76-322: Syntax error, statement will be ignored.

To those who answered me, thank you for your interest in my work. I have tried to address your comments below.

 

I did not test the ODS_GRAPHICS macro code in batch mode because I am using SAS interactively on a PC. I included the batch mode code because Art Carpenter's macro %ExecPrg did so.

 

The folder into which I wrote graphical output did not have write permission so I tried to create code that would eliminate the need for a separate intervention.

 

Tom (Super User), thank you for your informative comment. Yes, the directory to which default output without a defined GPATH statement is somewhere in the SAS Foundation directory path which is not writeable by default and which I do not want to make writeable so that I don't inadvertently overwrite some file of importance.

 

Catch up on SAS Innovate 2026

Nearly 200 sessions are now available on demand with the SAS Innovate Digital Pass.

Explore Now →
How to Concatenate Values

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.

SAS Training: Just a Click Away

 Ready to level-up your skills? Choose your own adventure.

Browse our catalog!

Discussion stats
  • 6 replies
  • 206 views
  • 0 likes
  • 4 in conversation