2009-04-29 23 views
10

Sto scrivendo un piccolo script Perl che dipende da alcuni moduli che potrebbero essere disponibili, quindi durante l'installazione dovrei controllare se c'è tutto lì. Potrei semplicemente scrivere use some::module e vedere se arriva un errore, ma un messaggio breve come "Devi installare alcuni :: module" sarebbe più utile per gli utenti finali.Come verificare se è installato un modulo Perl?

Potrei anche cercare tutte le directory in @INC, ma dato che è Perl, ci deve essere un modo più semplice.

+1

Come verificare se un modulo perl è installato non è una domanda, è una dichiarazione. – cjk

risposta

19
perl -MSome::Module -e ';' 

Whoops, ho letto male la domanda. Pensavo volessi sapere in un'istanza una tantum, non scoprendola in modo recuperabile. Io uso sempre qualcosa di simile:

sub try_load { 
    my $mod = shift; 

    eval("use $mod"); 

    if ([email protected]) { 
    #print "\[email protected] = [email protected]\n"; 
    return(0); 
    } else { 
    return(1); 
    } 
} 

Che si utilizza in questo modo:

$module = 'Some::Module'; 
if (try_load($module)) { 
    print "loaded\n"; 
} else { 
    print "not loaded\n"; 
} 
+1

Desideriamo notare che l'eval sta facendo il doppio lavoro: ti consente di verificare la presenza di un modulo arbitrario e impedisce che l'istruzione use venga trasformata in un blocco BEGIN. Upshot è, se si dovesse scrivere codice come questo ma codificato per un modulo specifico, si utilizzerebbe comunque l'eval basato su stringhe. – chaos

+1

Mi è piaciuta la tua risposta, dal momento che voglio scoprirlo da bash, tuttavia, ho dei problemi con i moduli che richiedono un argomento. per esempio. [jens @ ca60c173 (perl) p] $ perl -MPackage :: DeprecationManager -e ';' È necessario fornire un parametro hash reference -deprecations durante l'importazione di Package :: DeprecationManager alla riga -e 0. –

3

ne dite:

die "Some::Module missing!" unless(eval{require Some::Module}); 
+1

È necessario chiamare l'importazione se si intende imitare l'utilizzo e aggiungere uno alla fine è una buona idea poiché l'importazione non è necessario per restituire un valore true: eval {require Some :: Module; Alcuni :: su moduli> importazione; 1}; Anche questo non sarà sufficiente se il modulo è di natura lessicale (come Autobox) poiché esso verrà importato nell'eval per poi uscire dall'ambito al termine dell'eval. –

1

Io uso qualcosa di simile:

BEGIN { 
    my $module_name = shift; # @ARGV 
    our $module_exp = $module_name; 
    eval "use $module_name;"; 
} 

$module_exp =~ s{::}{/}g; 
foreach my $key (grep { m/^$module_exp\./ } keys %INC) { 
    print "$key => $INC{$key}\n"; 
} 

Ma lo uso di più sotto forma di guscio korn unzione:

function wherperl 
{ 
    perl -M$1 <<EX_DOC 
    my \$module = '$1'; 
    \$module =~ s/::/\\//g; 

    for (keys %INC) { 
     next unless m/^\$module\./; 
     print \$_ . ' => ' . \$INC{\$_} . "\n"; 
    } 
EX_DOC 
} 
3

Come si installa la sceneggiatura? Se si utilizza un file standard Makefile.PL o Build.PL, le dipendenze di elenco sono banali.

2

Ho un piccolo script che elenca tutti i moduli Perl sul mio sistema;

#!/usr/bin/perl 

use ExtUtils::Installed; 
my $instmod = ExtUtils::Installed->new(); 
foreach my $module ($instmod->modules()) { 
    my $version = $instmod->version($module) || "???"; 
    print "$module -- $version\n"; 
} 

All'interno di quel ciclo foreach si potrebbe voler fare qualcosa come;

my $match; 
if ($module =~ /$match/) { 
    print "Found $match: $module\n"; 
} 
1

mi piace usare il cpan utility:

% cpan -D YAML 
YAML 
------------------------------------------------------------------------- 
    YAML Ain't Markup Language (tm) 
    A/AD/ADAMK/YAML-0.70.tar.gz 
    /usr/local/perls/perl-5.10.0/lib/site_perl/5.10.0/YAML.pm 
    Installed: 0.68 
    CPAN:  0.70 Not up to date 
    Ingy dot Net (INGY) 
    [email protected] 

questo può essere un po 'lento in quanto ha per la connessione a un mirror CPAN per andare a prendere alcuni dei dati, ma ho anche un locale Specchio CPAN. :)

Problemi correlati