Apa saja cara memengaruhi tempat modul Perl dicari? atau, Bagaimana Perl's @INC dibangun ?
Seperti yang kita ketahui, Perl menggunakan @INC
array yang berisi nama direktori untuk menentukan di mana mencari file modul Perl .
Tampaknya tidak ada posting tipe FAQ "@INC" yang komprehensif di StackOverflow, jadi pertanyaan ini dimaksudkan sebagai satu.
perl
perl-module
DVK
sumber
sumber
@INC
saat runtime, bukan konstruksi penuh.Jawaban:
Kami akan melihat bagaimana isi array ini dibangun dan dapat dimanipulasi untuk mempengaruhi di mana penerjemah Perl akan menemukan file-file modul.
Default
@INC
Interpreter perl dikompilasi dengan
@INC
nilai default tertentu . Untuk mengetahui nilai ini, jalankanenv -i perl -V
perintah (env -i
abaikanPERL5LIB
variabel lingkungan - lihat # 2) dan pada output Anda akan melihat sesuatu seperti ini:Catatan
.
di akhir; ini adalah direktori saat ini (yang tidak harus sama dengan direktori skrip). Itu hilang dalam Perl 5.26+, dan ketika Perl berjalan dengan-T
(pemeriksaan noda diaktifkan) .Untuk mengubah jalur default saat mengonfigurasi kompilasi biner Perl, tetapkan opsi konfigurasi
otherlibdirs
:Variabel lingkungan
PERL5LIB
(atauPERLLIB
)Perl pra-pends
@INC
dengan daftar direktori (dipisahkan dengan titik dua) yang terkandung dalamPERL5LIB
(jika tidak ditentukan,PERLLIB
digunakan) variabel lingkungan shell Anda. Untuk melihat konten variabel@INC
afterPERL5LIB
danPERLLIB
environment telah diterapkan, jalankanperl -V
.-I
opsi baris perintahPerl pra-pends
@INC
dengan daftar direktori (dipisahkan dengan titik dua) dilewatkan sebagai nilai-I
opsi baris perintah. Ini dapat dilakukan dengan tiga cara, seperti biasa dengan opsi Perl:Lulus di baris perintah:
Lulus melalui baris pertama (shebang) skrip Perl Anda:
Lulus sebagai bagian dari
PERL5OPT
(atauPERLOPT
) variabel lingkungan (lihat bab 19.02 di Pemrograman Perl )Berikan itu melalui
lib
pragmaPerl pra-pends
@INC
dengan daftar direktori yang dikirimkan kepadanyause lib
.Dalam sebuah program:
Di baris perintah:
Anda juga dapat menghapus direktori dari
@INC
viano lib
.Anda bisa langsung memanipulasi
@INC
sebagai array Perl biasa.Catatan: Karena
@INC
digunakan selama fase kompilasi, ini harus dilakukan di dalamBEGIN {}
blok, yang mendahuluiuse MyModule
pernyataan.Tambahkan direktori ke awal via
unshift @INC, $dir
.Tambahkan direktori ke bagian akhir via
push @INC, $dir
.Lakukan hal lain yang dapat Anda lakukan dengan array Perl.
Catatan: Direktori tidak diubah ke
@INC
dalam urutan yang tercantum dalam jawaban ini, misalnya default@INC
terakhir dalam daftar, didahului olehPERL5LIB
, didahului oleh-I
, didahului olehuse lib
dan diarahkan@INC
dimanipulasi , dua yang terakhir dicampur dalam urutan mana pun mereka berada dalam kode Perl.Referensi:
@INC
?Sepertinya tidak ada
@INC
posting tipe FAQ yang komprehensif di Stack Overflow, jadi pertanyaan ini dimaksudkan sebagai satu.Kapan harus menggunakan setiap pendekatan?
Jika modul dalam direktori perlu digunakan oleh banyak / semua skrip di situs Anda, terutama dijalankan oleh banyak pengguna, direktori itu harus dimasukkan dalam default yang
@INC
dikompilasi ke biner Perl.Jika modul dalam direktori akan digunakan secara eksklusif oleh pengguna tertentu untuk semua skrip yang dijalankan pengguna (atau jika mengkompilasi ulang Perl bukan opsi untuk mengubah default
@INC
dalam kasus penggunaan sebelumnya), atur penggunaPERL5LIB
, biasanya selama login pengguna.Catatan: Perlu diketahui perangkap variabel lingkungan Unix yang biasa - misalnya dalam menjalankan skrip tertentu sebagai pengguna tertentu tidak menjamin menjalankannya dengan pengaturan lingkungan pengguna itu, misalnya via
su
.Jika modul dalam direktori hanya perlu digunakan dalam keadaan tertentu (misalnya ketika skrip dieksekusi dalam mode pengembangan / debug, Anda dapat mengatur
PERL5LIB
secara manual, atau meneruskan-I
opsi ke perl.Jika modul hanya perlu digunakan untuk skrip tertentu, oleh semua pengguna yang menggunakannya, gunakan
use lib
/no lib
pragma dalam program itu sendiri. Ini juga harus digunakan ketika direktori yang akan dicari harus ditentukan secara dinamis selama runtime - misalnya dari parameter baris perintah skrip atau jalur skrip (lihat modul FindBin untuk kasus penggunaan yang sangat bagus).Jika direktori yang
@INC
perlu dimanipulasi sesuai dengan beberapa logika yang rumit, tidak mungkin terlalu sulit untuk diterapkan dengan kombinasiuse lib
/no lib
pragma, maka gunakan@INC
manipulasi langsung di dalamBEGIN {}
blok atau di dalam perpustakaan tujuan khusus yang ditunjuk untuk@INC
manipulasi, yang harus digunakan oleh skrip Anda (s) sebelum modul lain digunakan.Contoh dari hal ini adalah secara otomatis beralih antar perpustakaan dalam direktori prod / uat / dev, dengan pickup perpustakaan air terjun di prod jika hilang dari dev dan / atau UAT (kondisi terakhir membuat solusi standar "gunakan lib + FindBin" cukup rumit. A ilustrasi rinci dari skenario ini adalah di Bagaimana cara menggunakan modul Perl beta dari skrip Perl beta? .
Kasus penggunaan tambahan untuk memanipulasi secara langsung
@INC
adalah untuk dapat menambahkan referensi subrutin atau referensi objek (ya, Virginia,@INC
dapat berisi kode Perl khusus dan bukan hanya nama direktori, seperti yang dijelaskan dalam Kapan referensi subrutin dalam @INC disebut? ).sumber
Selain lokasi yang tercantum di atas, versi OS X dari Perl juga memiliki dua cara lagi:
File /Library/Perl/x.xx/AppendToPath. Jalur yang tercantum dalam file ini ditambahkan ke @INC saat runtime.
File /Library/Perl/x.xx/PrependToPath. Jalur yang tercantum dalam file ini ditambahkan ke @INC saat runtime.
sumber
Seperti yang sudah dikatakan @INC adalah array dan Anda bebas untuk menambahkan apa pun yang Anda inginkan.
Script CGI REST saya terlihat seperti:
Subroutine yang hilang diekspor oleh Rest.pm.
sumber