Perl: Difference between revisions
m prefix shell commands with "$" and use syntax highlighting |
Starfish2228 (talk | contribs) →Adding something from CPAN to nixpkgs: Clean up examples |
||
| Line 54: | Line 54: | ||
==Adding something from CPAN to nixpkgs== | ==Adding something from CPAN to nixpkgs== | ||
# Enter a <tt>nix-shell</tt> that provides the necessary dependencies: < | # Enter a <tt>nix-shell</tt> that provides the necessary dependencies: <syntaxhighlight lang="console">$ nix-shell -p nix-generate-from-cpan</syntaxhighlight> | ||
# Use the <tt>nix-generate-from-cpan.pl</tt> script (see <tt>nixpkgs/maintainers/scripts/</tt>) to generate something appropriate.<br/>Example usage: < | # Use the <tt>nix-generate-from-cpan.pl</tt> script (see <tt>nixpkgs/maintainers/scripts/</tt>) to generate something appropriate.<br/>Example usage: <syntaxhighlight lang="console">$ nix-generate-from-cpan Devel::REPL</syntaxhighlight> | ||
# After reviewing the result from the previous step and making appropriate modifications, add it to <code>pkgs/top-level/perl-packages.nix</code>. Note that some things use <code>buildPerlPackage</code> while some use <code>buildPerlModule</code>. Also note the mostly-followed naming convention as well as the mostly-followed alphabetical ordering. There are plenty of examples in <tt>perl-packages.nix</tt> | # After reviewing the result from the previous step and making appropriate modifications, add it to <code>pkgs/top-level/perl-packages.nix</code>. Note that some things use <code>buildPerlPackage</code> while some use <code>buildPerlModule</code>. Also note the mostly-followed naming convention as well as the mostly-followed alphabetical ordering. There are plenty of examples in <tt>perl-packages.nix</tt>. | ||
# Build and test. | # Build and test. | ||
Latest revision as of 23:32, 7 June 2026
Running a Perl script
Replacing #! with nix-shell
Perl scripts normally start something like this:
#!/usr/bin/env perl
In Nix, we often make isolated environments using nix-shell. You can do this in the #! (shabang) section directly in the script too. Here is an example from the manual — a Perl script that specifies that it requires Perl and the HTML::TokeParser::Simple and LWP packages:
#! /usr/bin/env nix-shell
#! nix-shell -i perl -p perl perlPackages.HTMLTokeParserSimple perlPackages.LWP
use HTML::TokeParser::Simple;
# Fetch nixos.org and print all hrefs.
my $p = HTML::TokeParser::Simple->new(url => 'http://nixos.org/');
while (my $token = $p->get_tag("a")) {
my $href = $token->get_attr("href");
print "$href\n" if $href;
}
Invoking nix-shell on command-line
If you run a perl script and encounter a dependency error like this:
Can't locate DB_File.pm in @INC (you may need to install the DB_File module)
... use nix-shell to create a shell environment which includes the dependency. Here we searched NixOS packages and found an existing perl package which suits, like so.
$ nix-shell -p perl perl534Packages.DBFile --run ./myscript.pl
There is no /usr/bin/perl
By design, there is no /usr/bin/perl in Nix. So you may encounter messages like:
./myscript.pl: bad interpreter: /usr/bin/perl: no such file or directory
Change the first line of the script to
#!/usr/bin/env -S perl
or start it with perl ./myscript.pl
Adding something from CPAN to nixpkgs
- Enter a nix-shell that provides the necessary dependencies:
$ nix-shell -p nix-generate-from-cpan
- Use the nix-generate-from-cpan.pl script (see nixpkgs/maintainers/scripts/) to generate something appropriate.
Example usage:$ nix-generate-from-cpan Devel::REPL
- After reviewing the result from the previous step and making appropriate modifications, add it to
pkgs/top-level/perl-packages.nix. Note that some things usebuildPerlPackagewhile some usebuildPerlModule. Also note the mostly-followed naming convention as well as the mostly-followed alphabetical ordering. There are plenty of examples in perl-packages.nix. - Build and test.
Adding something without a Makefile.PL
The perlPackages.buildPerlPackage assumes a Makefile.PL to exist as part of the configurePhase. If no such file is present in the project you are building, it is easiest to add a Makefile.PL into the source yourself.
The example below does so by adding it using the postPatch hook:
postPatch = ''
cat <<EOF > Makefile.PL
use v5.10;
use ExtUtils::MakeMaker;
WriteMakefile(
NAME => 'RevBank',
VERSION_FROM => 'revbank',
ABSTRACT_FROM => 'lib/RevBank.pod',
EXE_FILES => [ 'revbank' ],
);
EOF
'';
The documentation for ExtUtils::MakeMaker can be found here.
Wrappers for installed programs
To make perl modules available to a program in your derivation:
- Add
makeWrappertonativeBuildInputs - Add
postFixup = '' wrapProgram $out/bin/something \ --prefix PERL5LIB : "${with perlPackages; makePerlPath [ something ]}" '';
Also keep in mind that makePerlPath would not resolve transitive dependencies of Perl packages. Hence if you want to just reference top-level packages, then use makeFullPerlPath which would recursively resolve dependency graph for you.