WebReference.com - Perl Module Primer (4/5) | WebReference

WebReference.com - Perl Module Primer (4/5)

To page 1To page 2To page 3current pageTo page 5
[previous] [next]

Perl Module Primer

On the previous page, we accessed the hello_message routine of our new module via this statement:

print SayHello::hello_message()."\n";

Since we cannot access a sub routine in another namespace (recall from page 2 that a separate namespace is defined every time we use the package declaration) directly, we must instead use a qualified name to access our module's symbols (i.e. variables, or sub routines). To qualify a variable or sub routine reference, simply prefix it with the name of the package it is in, followed by a double colon. Thus, SayHello::hello_message() is one way we can reference the hello_message routine from outside the SayHello module. (We can also access the routines by importing them; more on that a little further down this page.)

While they may not look familiar to you, you are already using packages in your existing scripts. The fact is that all Perl scripts assume (until you tell them otherwise via a package declaration) that the variables and sub routines defined within them belong to the package main. Thus, in our earlier foobar example, we could also have written:

$myVariable="foobar";
print $main::myVariable;

with the same result. Note that when we refer to variables in this fashion, we place the $ sign on the left of the package declaration, and not next to the variable name:

$myVariable="foobar";
print main::$myVariable;  # incorrect

This rule is true when you reference your package variables and subroutines in your new modules, too. If we had moved our module to the Local sub directory, as we discussed on the previous page, then the reference would look like this:

print Local::SayHello::hello_message()."\n";

Watch Out For my

You can access variables in modules via their package qualifications, the same way you access the sub routine as in the example above. But note that if you define the variable with the keyword my when you create it within the module, you will not be able to access it from outside the module. Just like my variables in local sub routines, the my variables in modules only exist directly within the module itself, subject to the normal scoping rules for my. Using the qualified form of the variable name as above will not retrieve the variable for you.

If you must access a module variable from outside the package you are declaring it in, then you can declare it using the our function (available in later Perl versions, I believe 5.6 and later), in effect creating a package variable that is then accessible to all other packages via a qualified name. A good example of this would be the $VERSION variable; which authors include by convention (and is therefore recommended) in most Perl modules, and which is automatically used by various Perl utilities. Let's add a $VERSION variable to our module and access it from our main script:

package SayHello;
use strict;
our $VERSION=0.10;
my $hello_string="Hello World!";
sub hello_message {
    return $hello_string;
}
1;

And then to access it from the script:

#!/usr/bin/perl
use strict;
use SayHello;
print "You are using version: $SayHello::VERSION of SayHello.\n";
print SayHello::hello_message()."\n";

Note that we added a use strict pragma to both code segments. This does not prevent us from accessing the our variable, while still helping us to write cleaner code. We could also have defined the $VERSION variable by fully qualifying it; i.e., $SayHello::VERSION = 0.10;. Note also that the new $hello_string variable is a my variable, and is therefore not accessible from the main script. But that doesn't mean we can't use it in the module itself! Our hello_message routine now returns the value of this variable; and in fact, this is a recommended way for you to provide access to the variables within your modules that should be accessible from other packages. Simply define a separate routine--or routines--within the module that will return (and perhaps set, if warranted) the value of the variable, and then the caller can access the variable through that routine. This allows you to separate the logic from within the modules from the logic outside of the modules, while still allowing access to those module components that need to be accessed from the outside world.

Before we move on, note one further use for the $VERSION variable. If you load the module like this:

use SayHello 0.20;

then Perl will automatically check the version number of the module that is loaded and will not continue unless it (the version number stored in the module) is greater than or equal to the version number specified in the use statement.

Exporting

On the previous page, we mentioned that one side effect of loading a module into our script with use is that the import routine of the module is automatically called. This functionality provides you with a way to set certain module variables and sub routines such that the calling program can directly import them into their own namespaces; and therefore access them directly without the qualified naming structure. The specifics of how this is actually accomplished is just a bit outside the scope of this article, but to see what it would look like, let's alter our module and script to allow the hello_message sub routine to be exported as needed:

package SayHello;
use strict;
require Exporter;
our @ISA = qw(Exporter);
our @EXPORT_OK = qw(hello_message);
our $VERSION=0.10;
my $hello_string="Hello World!";
sub hello_message {
    return $hello_string;
}
1;

And in the code:

#!/usr/bin/perl
use strict;
use SayHello qw(hello_message);
print "You are using version: $SayHello::VERSION of SayHello.\n";
print hello_message()."\n";

Note that in this case, we did not need to qualify our hello_message call; since we imported it via

use SayHello qw(hello_message);

Again, the above code is just a bit outside the scope of where I want to go with this article, but here's some basic information about what's going on behind the scenes:

  1. require Exporter;
    allows us to utilize the export facilities in the standard Perl module Exporter. specifically, the import routine in Exporter will be called each time our module is used.
  2. our @ISA = qw(Exporter);
    informs Perl that our module will inherit functions from the Exporter module. This is how the import module of Exporter is called when our module is used. Since our module does not have an import module, Perl searches the modules that we inherit from, and finds the import module in Exporter instead.
  3. our @EXPORT_OK = qw(hello_message);
    a list of those variable names that we designate as exportable to scripts that use our module.
  4. use SayHello qw(hello_message);
    our new use statement includes a list of those module symbols that we want to import into our namespace. Note that this does not prevent us from continuing to access $VERSION via its qualified name; even though it is not in the @EXPORT_OK array.

We could also have automatically exported symbols (without having to specifically request them in the use statement) by including the symbols to export by default in the @EXPORT array. However, doing this would automatically add symbols into the calling script by default; which is generally not a good thing to do. Remember, you don't know what variables and symbol names the calling script may be using; the best course is to simply stay out of their code and let them pull in the symbols of your module that they need as they need them.

Armed with this basic information, you should have all you need to start writing helpful modules for your own projects, and I encourage you to do so. But there remains much to be discussed about module usage that is not covered in this basic tutorial. On the next page, we'll conclude by looking at some of the module-related topics you may want to continue pursuing on your own.


To page 1To page 2To page 3current pageTo page 5
[previous] [next]

Created: April 7, 2005
Revised: April 7, 2005

URL: http://webreference.com/programming/perl/modules/5.html