Labels with PostScript::MailLabels Getting Started (Open Source)

by Nathan Willis


Alan Jackson’s PostScript::MailLabels is a Perl utility to automate production of high-quality label layouts. it is designed to be useful to Perl scripters, who can easily incorporate high-quality PostScript output into their scripts, but the scripts included in the base package are, themselves, an easy-to-use set of command-line tools for label printing. Best of all, the package provides printer calibration and alignment tools.


PostScript::MailLabels is available through two routes — you can download the package as a bundle from Jackson’s site, or you can have Perl automatically fetch it for you from the Comprehensive Perl Archive Network (CPAN).

The latest version on Jackson’s site is 2.30 (CPAN’s may be slightly behind, but is from the same major release version and incorporates the same features). To install, download and unpack the .tar.gz archive on your system. From a command line, switch to the unpacked directory and type perl Makefile.PL, followed by make to build the installable package.

At this point, you can optionally run make test, which will have PostScript::MailLabels generate some test pages — useful the first time you install, but not required. Finally, sudo make install will install the package system-wide.


“PostScript::MailLabels can produce two calibration aids, one that allows you to measure the printable area of the page (left), and one that lets you test X- and Y-alignment (right).”

To fetch PostScript::MailLabels from CPAN, just type perl -MCPAN -e 'install PostScript::MailLabels', and Perl will take care of the rest. CPAN support is common to the vast majority of Linux distributions, but you should check to see if your distro’s package is installed, just to be sure.


Because PostScript::MailLabels is a Perl module, not a standalone script, it can only be used inside of other Perl scripts. Fortunately, Jackson provides a few demonstration scripts that will let even the complete Perl novice get started easily printing labels.

In practical usage, PostScript::MailLabels lets you define a label set by the dimensions of the paper and label sheet (including the standard Avery and Dymo product codes), the address format you wish to use (which is completely flexible, suitable for home and business use, in any country, and supports postal bar codes), and font. In addition, you can specify adjustments to account for the printable area and alignment of your printer.

For example, a label setup in your script could be as simple as

$labels -> labelsetup(
            Avery       => $labels->averycode(5160),
            PaperSize   => 'letter',
            Font        => 'Helvetica',

You set up the address layout line-by-line, such as


Each of the fields requires a simple definition including its name, the component “type” (name, road, place, or bar), whether the field can be trimmed for length to fit onto the label, the field’s index number in the input array, and the font to use (possibly overriding the default). For example,

$labels->editcomponent('attentionline','name','no', 0, 'Helvetica');
$labels->editcomponent('firmname','name','no', 1, 'Helvetica');
$labels->editcomponent('city','name', 'no',  3, 'Helvetica');
$labels->editcomponent('state','name','no', 4, 'Helvetica');
$labels->editcomponent('zip','place', 'yes', 5, 'Helvetica');
$labels->editcomponent('country','name','no', 6, 'Helvetica');

Note in these two examples that the city, state, and zip fields appear on different lines in the input array, but that PostScript::MailLabels lets us place them all on the same line of the address label layout. The component “type” is important because PostScript::MailLabels attempts to automatically trim extra-long lines to fit, and uses different strategies depending on the data type. ‘name’ fields get their first name abbreviated to initials first, while ‘road’ fields get suffixes like “Road” and “Street” excised first.


“PostScript::MailLabels’s demo output, showcasing the tool’s ability to produce postal barcodes, as well as to save paper by starting in the middle of a previously-used sheet of labels.”

Adjustments to the printing settings border widths for the printable area of the page (Printable_Left, Printable_Right, Printable_Top, and Printable_Bot), specifications for where the labels begin on the page (Output_Left, Output_Top, etc), and shifts that can be applied to the entire generated output (X_Adjust and Y_Adjust).

Finally, $output = $labels->makelabels(\@addrs); produces the output. By default, the file is named, and you can print it directly on any PostScript printer.

TAKING  PostScript::MailLabels FOR A TEST SPIN

If you are not a Perl hacker, assembling a script from scratch might sound a bit daunting. Jackson has complete documentation of PostScript::MailLabels on his site, including the full options for layout and font handling, working with Avery and Dymo codes, postal barcodes, and more. Just as good is that he provides code for a test program that both explains the options and produces helpful reference output.

You can copy-and-save the code posted under the example heading as, and run it from the command line. In addition to the PostScript sample defined in the script, it will write several output lines to the terminal. These include a list of the defined address components, a sample of the defined layout, a list of the fonts available on the system, a list of the acceptable paper sizes, a list of the known Avery template types, and the widths of various test strings (including zip codes and bar codes, because fitting them to the label is so critical to proper delivery).

For a simpler, more straightforward usage scenario, look at the demonstration scripts in the package’s /demo/ directory. Even if you are new to Perl, these demo scripts will let you get started with easy modifications to learn the ropes.

In particular, take a look at, which prints addresses on standard letter-sized paper. The __DATA__ section at the end of the script holds a “virtual” data file of sample addresses, including a mix of different name and addressing options, in the United States and abroad. Running perl will produce a PostScript output file called based on this data. You can run the script as-is to get a feel for what it does, after which modifying it for your own data, label definitions, and layout may be an easier path to customization than writing a script from scratch.

As you make your own modifications, though, don’t overlook two very important options: starting in the middle of a label sheet, and running the test output to calibrate your layout.

The FirstLabel directive tells PostScript:MailLabels where on the grid of labels you have defined to print the first entry (starting from the top left); you use this to begin printing on a sheet where some of the labels have already been printed. Just add the line FirstLabel => 4 (or whichever the appropriate number) to your labelsetup parameters.

You run the test output by calling $output = $labels->labelcalibration; and $output = $labels->labeltest; instead of $labels->makelabels. The first will create a PostScript page of the appropriate side with a set of calibrated X and Y axes at the center and extending to the edges of the page — you can use it to precisely measure the printable dimensions of your page. The second will generate a blank “template” page with outlines marking where the labels should be; you can hold this up next to a sheet of real labels to test for proper alignment before printing.

If you like Perl, you’ll want to dig into PostScript::MailLabels to uncover even more of what it can do. But even if you’re new to Perl, the easy to use syntax and support options make it a breeze to pick up.


Other Resource:

Visit for all your labels

2 thoughts on “Labels with PostScript::MailLabels Getting Started (Open Source)

  1. Pingback: Links 17/1/2010: New Pardus, Puredyne GNU/Linux | Boycott Novell

  2. Pingback: Links 29/1/2010: Many New Releases of GNU/Linux, Oracle Makes Promises | Boycott Novell

Leave a Reply

Your email address will not be published. Required fields are marked *