seguimiento - ¿Cómo puedo obtener Perl para dar un mensaje de advertencia cuando se importa un determinado paquete/etiqueta?
seguimiento de referencia de envío dhl (2)
Usted escribe su propia sub import
en el package Foo
que se llamará con la lista de parámetros del use Foo
.
Un ejemplo:
package Foo;
use Exporter;
sub import {
warn "called with paramters ''@_''";
# do the real import work
goto &{Exporter->can(''import'')};
}
Por lo tanto, en la import
secundaria puede buscar en la lista de argumentos la etiqueta en desuso y luego lanzar una advertencia.
Actualización : como señala Axeman, debe llamar a goto &{Exporter->can(''import'')}
. Esta forma de goto reemplaza la llamada de subrutina actual en la pila, conservando los argumentos actuales (si los hay). Eso es necesario porque el método import () de Exporter exportará al espacio de nombres de su interlocutor.
Tengo un paquete que acabo de crear y tengo un "modo antiguo" que básicamente hace que funcione como antes: importar todo en el espacio de nombres actual. Una de las cosas buenas de tener esto como un paquete es que ya no tenemos que hacer eso. De todos modos, lo que me gustaría hacer es tenerlo para que cada vez que alguien lo haga:
use Foo qw(:oldmode);
Lanzo una advertencia de que esto está en desuso y de que deben importar solo lo que necesitan o simplemente acceder a las funciones con Foo-> fun ();
¿Alguna idea sobre cómo hacer esto?
Bueno, como específicamente use Mod qw<:oldmode>;
que quieres alarmar en los casos de use Mod qw<:oldmode>;
Esto funciona mejor:
package Foo;
use base qw<Exporter>;
use Carp qw<carp>;
...
sub import {
#if ( grep { $_ eq '':oldmode'' } @_ ) { # Perl 5.8
if ( @_ ~~ '':oldmode'' ) { # Perl 5.10
carp( ''import called with :oldmode!'' );
}
goto &{Exporter->can( ''import'' )};
}
Gracias a Frew, por mencionar la sintaxis de concordancia inteligente de Perl 5.10. Estoy aprendiendo todas las formas de trabajar con Perl 5.10 en mi código.
Nota: la forma estándar de usar exporter en un sub de importación es manipular $Exporter::ExportLevel
o llamar a Foo->export_to_level( 1, @_ );
Pero me gusta el camino de arriba. Es más rápido y, creo, más simple.