Как построен Perl @INC? (aka каковы все способы влияния на то, где ищутся модули Perl?)
каковы все способы влияния на поиск модулей Perl?
или, Как построен Perl @INC?
Как известно, Perl использует @INC массив, содержащий имена каталогов, чтобы определить, где искать файлы модуль Perl.
похоже, что на StackOverflow нет исчерпывающего сообщения типа FAQ "@INC", поэтому этот вопрос предназначен как один.
3 ответов:
мы рассмотрим, как содержимое этого массива строится и может быть обработано, чтобы повлиять на то, где интерпретатор Perl найдет файлы модуля.
по умолчанию
@INCинтерпретатор Perl является составлен с конкретным
@INCзначение по умолчанию. Чтобы узнать это значение, запустите (env -iигнорироватьPERL5LIBпеременная окружения-см. #2) и на выходе вы увидите что-то вроде это:$ env -i perl -V ... @INC: /usr/lib/perl5/site_perl/5.18.0/x86_64-linux-thread-multi-ld /usr/lib/perl5/site_perl/5.18.0 /usr/lib/perl5/5.18.0/x86_64-linux-thread-multi-ld /usr/lib/perl5/5.18.0 .Примечание
.в конце; это текущий каталог (который не обязательно совпадает с скрипт каталог). Он отсутствует в Perl 5.26+, и когда Perl работает с-T(проверка заражения включена).чтобы изменить путь по умолчанию при настройке двоичной компиляции Perl, установите параметр конфигурации
otherlibdirs:
Configure -Dotherlibdirs=/usr/lib/perl5/site_perl/5.16.3
переменные среды
PERL5LIB(илиPERLLIB)Perl pre-pends
@INCсо списком каталогов (разделенных двоеточием), содержащегося вPERL5LIB(если он не определен,PERLLIBиспользуется) переменная окружения вашей оболочки. Чтобы увидеть содержимое@INCпослеPERL5LIBиPERLLIBпеременные среды вступили в силу, запуститеperl -V.$ perl -V ... %ENV: PERL5LIB="/home/myuser/test" @INC: /home/myuser/test /usr/lib/perl5/site_perl/5.18.0/x86_64-linux-thread-multi-ld /usr/lib/perl5/site_perl/5.18.0 /usr/lib/perl5/5.18.0/x86_64-linux-thread-multi-ld /usr/lib/perl5/5.18.0 .Perl pre-pends
@INCсо списком каталогов (разделенных двоеточием) передается как значение . Это можно сделать тремя способами, как обычно с вариантами Перл:
передайте его в командной строке:
perl -I /my/moduledir your_script.plпередайте его через первую строку (shebang) вашего Perl сценарий:
#!/usr/local/bin/perl -w -I /my/moduledirпередайте его как часть
PERL5OPT(илиPERLOPT) переменной окружения (см. главу 19.02 в Программирование На Perl)передайте его через
libpragmaPerl pre-pends
@INCсо списком каталогов, переданных в него черезuse lib.в программе:
use lib ("/dir1", "/dir2");в командной линия:
perl -Mlib=/dir1,/dir2вы можете удалить каталоги от
@INCчерезno lib.вы можете непосредственно манипулировать
@INCкак обычный массив Perl.Обратите Внимание:
@INCиспользуется на этапе компиляции, это должно быть сделано внутриBEGIN {}блок, который предшествуетuse MyModuleзаявление.
добавить каталоги в начало через
unshift @INC, $dir.добавить каталоги в конец через
push @INC, $dir.сделайте все, что вы можете сделать с массивом Perl.
Примечание: директории unshifted на
@INCв порядке, указанном в этом ответе, например, по умолчанию@INCявляется последним в списке, передPERL5LIB, предшествуют-I, предшествуютuse libи направить@INCманипуляции, последние два смешанные в любом порядке они находятся в коде Perl.ссылки:
- perldoc perlmod
- perldoc lib
- Perl Module Mechanics-отличное руководство, содержащее практические инструкции
- как мне "использовать" модуль Perl в каталоге не в
@INC?- Программирование На Perl - глава 31 часть 13, ch 7.2.41
- как программа Perl знает, где найти файл, содержащий модуль Perl, который он использует?
там не кажется, чтобы быть всеобъемлющим
@INCFAQ-тип сообщения о переполнении стека, поэтому этот вопрос предназначен как один.когда использовать каждый подход?
если модули в каталоге должны использоваться многими / всеми скриптами на вашем сайте, особенно запущенными несколькими пользователями, этот каталог должно быть включено в значение по умолчанию
@INCкомпилируется в двоичный файл Perl.если модули в каталоге будут использоваться исключительно определенным пользователем для всех сценариев, которые запускает пользователь (или если перекомпиляция Perl не является опцией для изменения default
@INCв предыдущем случае использования), установите пользователейPERL5LIB, обычно во время входа пользователя.Примечание: пожалуйста, имейте в виду обычные подводные камни переменной среды Unix-например, в некоторых случаях работает скрипты как конкретный пользователь не гарантируют их выполнение с настроенной средой этого пользователя, например, через
su.если модули в каталоге необходимо использовать только в определенных обстоятельствах (например, когда скрипт(ы) выполняется в режиме разработки/отладки, вы можете установить
PERL5LIBвручную, или пройти-Iопция для perl.если модули должны использоваться только для определенных сценариев, по все пользователи, использующие их, используйте
use lib/no libпрагмы в самой программе. Он также должен использоваться, когда каталог для поиска должен быть динамически определен во время выполнения - например, из параметров командной строки скрипта или пути скрипта (см. FindBin модуль для очень хорошего случая использования).если каталоги в
@INCнужно манипулировать в соответствии с какой-то сложной логикой, либо невозможно тоже громоздко реализовать комбинациейuse lib/no libпрагмы, затем используйте direct@INCманипуляции внутриBEGIN {}блок или внутри библиотеки специального назначения, предназначенной для@INCманипуляции, которые должны использоваться вашим скриптом(АМИ) перед использованием любых других модулей.примером этого является автоматическое переключение между библиотеками в каталогах prod/uat/dev, с помощью waterfall library pickup в prod, если он отсутствует в dev и / или UAT (последнее условие делает стандартное решение "use lib + FindBin" довольно сложное. Подробная иллюстрация этого сценария находится в как использовать модули beta Perl из сценариев beta Perl?.
дополнительный вариант использования для непосредственного управления
@INCдолжна быть возможность добавлять ссылки на подпрограммы или ссылки на объекты (да, Вирджиния,@INCможет содержать пользовательский код Perl, а не только имена каталогов, как описано в когда ссылка на подпрограмму в @INC называется?).
в дополнение к расположениям, перечисленным выше, версия OS X Perl также имеет еще два способа:
файл/Library/Perl/x.xx / AppendToPath. Пути, перечисленные в этом файле, добавляются в @INC во время выполнения.
файл/Library/Perl/x.xx / PrependToPath. Пути, перечисленные в этом файле, добавляются к @INC во время выполнения.
как уже было сказано, @INC-это массив, и вы можете добавить все, что хотите.
мой скрипт CGI REST выглядит так:
#!/usr/bin/perl use strict; use warnings; BEGIN { push @INC, 'fully_qualified_path_to_module_wiht_our_REST.pm'; } use Modules::Rest; gone(@_);подпрограмма gone экспортируется Rest.pm.
Comments