Динамически загружаемые модули Perl - PullRequest
3 голосов
/ 29 ноября 2011

Я пытаюсь создать расширяемую систему, с помощью которой я могу написать новый модуль для обработки.Я хочу, чтобы программа автоматически загружала любой новый файл .pm, который помещается в каталог Handlers и соответствует интерфейсу Moose :: Role.

Мне интересно, существует ли модуль Perl или более санкционированный Mooseспособ сделать это автоматически?Вот то, что я построил до сих пор, но это кажется немного многословным, и должен быть более простой способ сделать это.

handler.pl содержит:

    #!/usr/bin/perl
            use Handler;
    use Data::Dumper;

    my $base_handler = Handler->new();
    $base_handler->load_modules('SysG/Handler');
    print Dumper($base_handler);

Handler.pm содержит:

    package Handler;
    use Moose;

    has 'handlers' => ( traits => ['Array'], handles => { add_handler => 'push' } );

    sub load_modules {
        my ($self,$dir) = @_;

        push(@INC, $dir);

        my @modules = find_modules_to_load($dir);
        eval { 
            # Note that this sort is important. The processing order will be critically important.
            # The sort implies the sort order
            foreach my $module ( sort @modules) {
                (my $file = $module) =~ s|::|/|g;
                print "About to load $file.pm for module $module\n" ;
                require $file . '.pm';
                $module->import();
                my $obj = $module->new();
                $self->add_handler($obj);
                1;
            }
        } or do {
            my $error = $@;
            print "Error loading modules: $error" if $error;
        };

    }

    sub find_modules_to_load {
        my ($dir) = @_;
        my @files = glob("$dir/*.pm");
        my $namespace = $dir;
        $namespace =~ s/\//::/g;

        # Get the leaf name and add the System::Module namespace to it
        my @modules = map { s/.*\/(.*).pm//g;  "${namespace}::$1"; } @files;
        die "ERROR: No classifier modules found in $dir\n" unless @modules;
        return @modules;
    }

    1;

Затем я создал каталог с именем SysG / Handler и добавил два файла .pm, которые обычно будут соответствовать Moose :: Role (как будто для определения интерфейса, который также должен быть привязан).).

Заглушка SysG::Handler::0001_HandleX.pm содержит:

package SysG::Handler::0001_HandleX;
use Moose;
1;

Заглушка SysG::Handler::0002_HandleX.pm содержит:

package SysG::Handler::0002_HandleY;
use Moose;
1;

Соберите все это вместе и Data :: Dumperрезультат:

$VAR1 = bless( {
             'handlers' => [
                             bless( {}, 'SysG::Handler::0001_HandleX' ),
                             bless( {}, 'SysG::Handler::0002_HandleY' )
                           ]
           }, 'Handler' );

Итак, теперь я повторяю свой оригинальный вопрос: должен быть более простой способ, либо модуль или способ Moose, чтобы автоматически загружать любые модули в определенную директорию.

Любые эксперты по лося могут помочь здесь?

1 Ответ

1 голос
/ 29 ноября 2011
...