I had an interesting request this week. A Unix system with three printers (p1, p2,p3) and two locations (North and South). The requirement is simple enough: jobs to p1 always go to p1, but jobs to p2 go either to p2 or p3, dependent upon the location (North or South). The p3 jobs have the same duality, but in reverse.
In olden days, this sort of need was met with LPDEST, but of course that is only useful for one printer. This customer needs more.
That's hardly unusual, and the usual way to solve it is to let users pick their printers. The burden of choosing the correct printer is theirs, not the system. But what if you really need it to be the system that chooses?
We have touched on that before: How can different users have different default printers? suggests front-ending lp to choose the actual printer desired.
Front-ending or front-loading is simply putting a special version of a command earlier in $PATH than a system command of the same name. Often the script or program calls the real system command with certain options or flags set to make it easier for users. Because the new version is earler in $PATH, it gets used rather than the system command.
Determining the user's location can be done from a file or by setting an environment variable in their login scripts - MYLOCATION, for example. The front-end lp script tests that and sends jobs to the proper places.
Parsing the arguments is the hardest part of the script. I'd suggest using Perl and Getopt but it could be done in the shell with "getopt". Once you know where the job is going (it was either specified with -d or not, which would mean the default destination), you'd then look at your $LOCATION (and $LPDEST) to decide where to re-route it.
After the parsing is out of the way, you might just drop through tests as simple as this (handling of options and copies left out for simplicity):
[ "$LOCATION" = "North" ] && [ "$PRINTER" = "p2" ] && real_lp -dp2 $* [ "$LOCATION" = "South" ] && [ "$PRINTER" = "p2" ] && real_lp -dp2 $* [ "$LOCATION" = "North" ] && [ "$PRINTER" = "p3" ] && real_lp -dp3 $* [ "$LOCATION" = "South" ] && [ "$PRINTER" = "p3" ] && real_lp -dp3 $*
Of course this could all be much more complicated if needed. You just need more decision making in the front end script.
Nothing stops you from splitting this all off to seperate scripts if things get very nasty quickly. Have the front end lp spawn a North script or a South script if that helps keep someone from screwing things up later because the logic gets complicated. Sure, you lose some efficiency and waste some time, but is that really significant when submitting a print job? Probably not.
See How do I set default printers? for a similar approach that accounts for local vs. remote printing.
How would you do this in Windows? Well, basically the same idea, although tieing it to an application you don't direcly control could be harder.B ut that's the world of Windows: everything looks easy, but it is really much more difficult.
Got something to add? Send me email.
More Articles by Anthony Lawrence © 2013-08-11 Anthony Lawrence
Let us change our traditional attitude to the construction of programs: Instead of imagining that our main task is to instruct a computer what to do, let us concentrate rather on explaining to human beings what we want a computer to do. (Donald Knuth)