Me escribió recientemente un nuevo script en Perl para matar procesos basado en cualquiera de los procesos de nombre /nombre de usuario y la extendió a través de Clases para que yo pudiera reutilizar el código de proceso en otros programas. Mi diseño actual es –

/home/mutew/src/prod/pskill       <-- Perl script
/home/mutew/src/prod/Process.pm   <-- Package to handle process descriptions

He añadido a ~/src/prod en mi variable $PATH para acceder a la secuencia de comandos desde cualquier lugar. Sobre la ejecución de la secuencia de comandos desde cualquier directorio de su directorio de residentes conduce a un «no se Puede localizar Proceso.pm en @INC» (lo cual es comprensible dado que otro de los directorios compartidos en /usr, @INC incluye sólo el directorio actual – ‘.’). Una solución que he estado usando es el uso lib directiva como así

use lib '/home/mutew/src/prod';

pero esta es una de las principales portabilidad problema. Cualquier solución que permitirá también a mí exportar la secuencia de comandos a otros sistemas sin y cambios?


EDITAR

  1. Eligió ‘depesz respuesta como la correcta, debido a su simplicidad y el núcleo uso del módulo.
  2. brian d foy la respuesta, aunque sugiere otros métodos para lograr el mismo (TMTOWTDI), su contribución en perlfaq8 hace esta pregunta absolutamente redundante.
  • tal vez es sólo mi instalación, pero si ambos archivos están en el mismo directorio simplemente «utilizar nombre de archivo.pm». A continuación, «mi $newVar = PACKAGENAME->new();» para cualquier objeto de programación.
  • Wow esto debería ser mucho más fácil en perl que esto! Hacer las cosas fáciles fáciles etc.
InformationsquelleAutor aks | 2009-04-08

9 Comentarios

  1. 52

    El enfoque más simple que he encontrado es usar FindBin módulo. Como este:

    use FindBin;
    use lib $FindBin::Bin;

    Generalmente prefiero tener mis scripts proporcionados de tal manera que los programas son en lo que sea/bin, y a las bibliotecas en lo que sea/lib

    En estas situaciones yo uso un poco más complicado enfoque:

    use Cwd qw(abs_path);
    use FindBin;
    use lib abs_path("$FindBin::Bin/../lib");

    La abs_path llamado es a hacer los @INC contener todo lo/lib, y no lo que/bin/../lib – es sólo un ligero cambio, pero hace que la lectura de los mensajes de error más fácil.

    • No olvides que abs_path devuelve contaminados como resultado de contaminación modo. Debe utilizar use lib (abs_path("$FindBin::Bin/../lib")=~m{^(/.*)})[0]; o, simplemente, utilizar use lib "$FindBin::Bin/../lib"; porque no hay ninguna razón para canonizó camino.
    • Esta solución funcionó, pero me fui con la segunda solución (abajo) porque FindBin tuvo que ser instalado con CPAN, y prefiero no comprometido aspecto de Archivo::Basename como módulo central, cuando se ejecuta a través de múltiples máquinas.
  2. 57

    Tengo curiosidad de saber por qué la solución simplista

    use File::Basename;
    use lib dirname (__FILE__);
    use SomeModuleLocatedInTheSameDirectoryAsThisPerlScriptOrModule;

    no. El FindBin módulo parece tener algunos problemas si el archivo no es ejecutable principal script de perl, pero simplemente no ejecutables módulo de Perl. Al menos eso es lo que me interpretar el comentario en el documentación. No se realmente a prueba.

    Tener cualquier otra ruta de acceso relativa a la ubicación de este Perl de archivo, hacer algo como

    use File::Basename;
    use lib dirname (__FILE__) . "/MyModules";
    • Me gusta este enfoque mucho – yo sólo tenía que usar use Cwd qw(abs_path); use lib dirname (abs_path(__FILE__)); para hacer que el script se puede llamar a través de un enlace simbólico. Saludos!
    • Esta es la única respuesta que trabajó aquí
    • Esta es la única respuesta que funcionó para mí buscando en Google varios minutos. Y es bastante simple, lo suficientemente claro y amigable para los novatos.
    • Esto no funciona bien con nombres de espacios de módulos, por ejemplo, si en virtud de somedir/Foo/Bar tiene Foo::Bar::Baz en Baz.pm y desea importar desde Foo::Bar::Qux en Qux.pm en el mismo directorio.
    • Gracias, David, punto interesante a tener en cuenta. Sólo quiero añadir que si el uso de espacios de nombres, no de la mejor práctica para, a continuación, importar los módulos de siempre con su nombre completo? De lo contrario puede acabar importando el mal módulo dependiendo de la lib ruta de búsqueda utilizado.
  3. 13

    De perlfaq8, que responde a «¿Cómo puedo añadir un directorio a la ruta de inclusión (@INC) en tiempo de ejecución?». Hay varias respuestas para las preguntas alrededor de este tema también.


    ¿Cómo puedo añadir un directorio a la ruta de inclusión (@INC) en tiempo de ejecución?

    Aquí son las formas sugeridas de modificar su ruta, incluyendo las variables de entorno de tiempo de ejecución de los interruptores, y en las instrucciones de código:

    la PERLLIB variable de entorno

    $ export PERLLIB=/path/to/my/dir
    $ perl program.pl

    la PERL5LIB variable de entorno

    $ export PERL5LIB=/path/to/my/dir
    $ perl program.pl

    perl-Idir línea de comandos de la bandera

    $ perl -I/path/to/my/dir program.pl

    el uso lib pragma:

    use lib "$ENV{HOME}/myown_perllib";

    El último es particularmente útil debido a que se sabe acerca de la máquina dependen de las arquitecturas. El lib.pm pragmática módulo se incluyó por primera vez con el 5.002 versión de Perl.

    • He leído perlfaq8 más tarde el mismo día y encontró la respuesta que yo necesitaba en su contribuido artículo. Me pregunto por qué lo hizo incluir el segundo método (el uso Cwd), aunque ya que @INC ya tiene una entrada para el directorio actual – ‘.’
  4. 3

    Echa un vistazo a Par::Packer. Se crea un archivo ejecutable con todas las de la escritura, dependencias incluidas. Se facilita la distribución. Usted también podría también proporcionar a los usuarios una versión de su módulo que puede ser instalado en su sistema. Ver Módulo::Starter para una manera fácil de crear todos los archivos necesarios para hacer un estándar de CPAN-estilo de la distribución.

  5. 2

    Usted puede hacer perl buscar en cualquier directorio mediante el -I bandera. Aquí, -I significa @INC que es la matriz de caminos en el que perl busca de los módulos. El uso de -I añade el camino dado a la @INC matriz para esta ejecución.

    por ejemplo:

    perl -I lib bin/script.pl

    donde lib contiene los módulos que quiero usar.

    Sé que esto funciona para perl 5. No estoy seguro acerca de otras versiones.

    • Esta es la mejor respuesta. Por ejemplo: #! /usr/bin/env perl -I ./ Las soluciones simples son siempre mejor que incluso todavía otro oscuro módulo CPAN.
  6. 2

    Además de los ya declaró soluciones:

    1. uso FindBin /lib
    2. Perl Faq 8 ¿Cómo puedo añadir un directorio a la ruta de inclusión (@INC) en tiempo de ejecución?

    ‘El enfoque más simple’ (™) que uso mientras dev/prueba de un módulo antes de
    para la implementación de la misma (en /usr/local/lib/site_perl/o en otros lugares en @INC) es
    para modificar @INC antes de cargar el módulo de la siguiente manera:

    #!/usr/bin/perl
    use strict;
    use warnings;
    # Modify @INC prior to module loading.
    BEGIN { unshift @INC, '.'; }
    use YourModuleInCWD;

    (Agregar directorio de trabajo actual a @INC? – PerlMonks)

  7. 0

    Para convertir vínculos relativos a la absoluta y agregar a @INC, yo normalmente uso ex::lib. Por supuesto, esto sólo es útil si se va a mantener la posición relativa de la secuencia de comandos y el módulo idéntico en todos los equipos donde se va a ejecutar la secuencia de comandos.

  8. -1

    Solo mantenerlo simple. No hay necesidad de importar cualquier bibliotecas; sólo tienes que encontrar tu directorio de trabajo actual:

    use lib "$ENV{PWD}/relativ_path_own_perllib";

    Para problemas similares, puede leer la variable de entorno que le da a su información acerca de dónde se encuentra, su directorio de inicio del sistema operativo cosas, y así sucesivamente, con una sola fila de código de programación en la capa del terminal, como:

    perl -e 'map { print; print " : ". $ENV{$_}." \n\r"; } sort keys %ENV '

    No hay necesidad de enlazar algunas bibliotecas; simplemente utilice el %ENV-Hash.

    • $ENV{PWD} no resuelve el problema, sino todo lo contrario. Devuelve el de usuario del directorio de trabajo, no en la ubicación de la secuencia de comandos.

Dejar respuesta

Please enter your comment!
Please enter your name here