Smitty has asked for the wisdom of the Perl Monks concerning the following question:

I have a couple of Perl programs that share common code. I've placed the common code into packages, each package in its own file, creating modules.

However, each program is currently distributed as a single file, so I have another script that essentially concatenates the main file and the packages files, by replacing use package::name with the contents of package/name.pm, and adding the necessary BEGIN and import lines. This generally works, but seems clumsy.

Is there an easier or sanctioned way of accomplishing my goal?

  • Comment on Cat'ing perl modules into single file script

Replies are listed 'Best First'.
Re: Cat'ing perl modules into single file script
by Fletch (Bishop) on Nov 24, 2008 at 03:00 UTC

    PAR (and PAR::Packer) might be another solution into which to look.

    The cake is a lie.
    The cake is a lie.
    The cake is a lie.

Re: Cat'ing perl modules into single file script
by GrandFather (Saint) on Nov 24, 2008 at 02:14 UTC

    I did exactly the same sort of thing to generate the script for PerlMonks Editor. I'm now in the process of refactoring the code with the intent of adding a suite of related, somewhat more general purpose, modules to CPAN and include a two line script as an example that provides the equivalent of the current PMEdit.pl (see What to do with PMEdit? for related discussion).

    I don't know what your context or distribution target is, but distributing the modules probably makes it easier to maintain, test and reuse the code.


    Perl reduces RSI - it saves typing
Re: Cat'ing perl modules into single file script
by Smitty (Beadle) on Nov 24, 2008 at 03:31 UTC

    Thanks folks.

    The script is most easily distributed (and installed) as a single file, that can be called as any standard (*nix) utility would be called, w/o additional command line arguments or forced interpreters (and I want to avoid a wrapper script). In one usage scenario, I do not control the calling context, so it must be callable as:

    /path/to/script

    and that's it.

    In the second usage scenario, the script is used standalone, where I could distribute and require installing the modules. But because of the requirement above, I don't want to have two different running contexts, where some unforeseen problem creeps in due to my misunderstanding the process required to translate modules into a single, standalone script. (I just encountered such a problem this evening, where running the single-file version produced an error, but the module-based version did not.)

      I don't see why scenario 1's calling constraint precludes installing a number of modules and a script that uses them into a single directory. I do know it was a PITA getting a number of modules merged together into a single script file and that it is easier to maintain the code in a number of module files than as one monolithic file.

      Perhaps you need to paint a bigger picture so it's easier to see where the issues really are?


      Perl reduces RSI - it saves typing

        Agreed, a PITA it has been to manage.

        Bigger picture...

        Originally, I developed A.pl, and then later B.pl. Since there was much common code, I split the common code into M/*.pm. The management of code in this fashion, while convenient for me to develop, doesn't fit/install naturally into an existing software package.

        I don't want to pollute the file namespace of the existing software package by placing *.pm into the same directory as A.pl or B.pl. And A.pl and B.pl may both be installed at the same time, but use (eg. be built with) different versions of *.pm at the same time, so I can't just create a single M module subdirectory for M/*.pm. The existing software package already reserves the file namespace of the installation directory (so I don't want to usurp any name M inwhich to install M/*.pm).

        If there is a way to avoid the contrived single-file packaging as I do now, that would be fine. Or if there is some (better) tool that does what my build packaging script already does, that would be fine too.