3

In OSX, I want to print to a file from the terminal.

I have two solutions, but both have drawbacks.

1. Use 'cupsfilter'

cupsfilter -m application/vnd.cups-postscript \
     -p /etc/cups/ppd/my_printer.ppd \
     -o Duplex=DuplexNoTumble \
     -o PageSize=A4 \
     -o landscape my_document.pdf \
     > my_document.ps

(The .ppd file is from my default printer)

I can now send this file to the printer with the raw option (avoiding any cupsfilters)

lp -o raw my_document.ps

But the drawback is that the printing result is not correct and not the same as when I print the normal way to my default printer.

lp -o Duplex=DuplexNoTumble -o PageSize=A4 -o landscape my_document.pdf 

On some investigation, I can see that some of PJL headers are different for both methods.

-@PJL SET BINDING = SHORTEDGE
+%@PJL SET BINDING = LONGEDGE

When running the cupsfilter command with the option --list-filters I see:

cgpdftops
pstops

It seems two filters are run. I think this is wrong, but I don't know for sure and I don't know how to change this.

2. Creating a File backend

You can do this with:

sudo lpadmin -p to_file \
   -P /etc/cups/ppd/my_printer.ppd \
   -E \
   -v file:///tmp/my_document.ps \
   -m raw

You probably get a warning and have to uncomment the following line in /private/etc/cups/cups-files.conf and set it to yes

FileDevice Yes

and then restart cups

sudo launchctl stop org.cups.cupsd
sudo launchctl start org.cups.cupsd

You can now print to a file with the following command:

lp -d to_file \
   -o Duplex=DuplexNoTumble \
   -o PageSize=A4 \
   -o landscape my_document.pdf

The created .ps file is owned by root, so to print it to the default printer I have to use sudo

sudo lp -o raw /tmp/my_document.ps

The problem with this solution is (besides the hassle with the file permission) that I can not define the name of the output file. I don't like to re-create the to_file backend for every print job.

So is there any other solution that gives me a file with the exact same data that otherwise was send to the printer?

Kurt Pfeifle
  • 86,724
  • 23
  • 248
  • 345
Paul Verschoor
  • 1,479
  • 1
  • 14
  • 27

2 Answers2

1

Have a look at this answer:

It explains how to set up my 2dir backend, which is an extension over the to_file method you used:

  • Your to_file printer has a fixed output file name, /tmp/my_document.ps, which is overwritten every time a new job is created.

  • My 2dir backend uses the same directory for every job sent to it, but it puts the job ID, date and time into each new jobfile name to make it uniq.

The 2dir as is described there creates a PDF from every job. You can easily modify the script there to skip the last step creating the PDF and to preserve whatever file type would be sent to the printer.

Community
  • 1
  • 1
Kurt Pfeifle
  • 86,724
  • 23
  • 248
  • 345
0

Found the answer a long time ago, but forgot to answer my own question

I currently do this in two steps, I create a new virtual printer Canon_IPC650_PS_to_file that use the .ppd file from my printer, and set the filename (a postscript file).

After that I can print to this new virtual printer and the postscript file will be created, including any options that I like to have.

lpadmin -p Canon_IPC650_PS_to_file -E -v file:'/Some/Path/name-of-postscript-file.ps' -m 'Library/Printers/PPDs/Contents/Resources/Canon_IPC650.ppd'
lp -d Canon_IPC650_PS_to_file some-file.pdf -o media="A4" -o InputSlot="Tray3" 
Paul Verschoor
  • 1,479
  • 1
  • 14
  • 27