2008-12-29 159 views
29

A recent question在這裏讓我思考。使用包管理器時,您如何管理Perl模塊?

在我嘗試的大多數Linux發行版中,一些Perl模塊將通過包管理器提供。其他人當然不是。在我需要安裝一些CPAN模塊來確定軟件包是否可用以及是否安裝它時,我會使用我的軟件包管理器很長一段時間。

一個明顯的優點是,只要新版本的軟件包可用,就可以更新模塊。

但是,當模塊不可用於預封裝格式並且該模塊存在依賴關係時,您會遇到麻煩。每次cpan shell詢問它是否應該遵循依賴關係時,打包你的包管理器會非常累人。

通常,另一個缺點是預封裝模塊的版本。如果您正在運行Debian或Ubuntu,您很快就會發現,您將無法生活在流血的邊緣,就像許多CPAN模塊作者似乎所做的那樣。

Linux上的其他Perl人員如何處理該問題?你只是忽略你的軟件包管理者必須提供什麼?是否有任何工具可以幫助(例如)和更好的隊友?或者你只是不通過cpan外殼安裝任何東西?

+0

我已將標題從「如何在Linux上管理Perl模塊?到「如何在使用包管理器時管理Perl模塊?「,因爲這與任何包管理器可能用於安裝Perl本身的系統有關,而不是嚴格的Linux - 例如OSX的macports(http://macports.org)發行版 – Ether 2009-12-29 00:48:01

回答

7

由於本問題最初是詢問perlbrew已經發布。它使得安裝自定義的,獨立的perl安裝變得微不足道。而這些版本之間的切換也很簡單:

perlbrew switch $version 
12

我們通過CPAN shell安裝所有東西。這確實忽略了軟件包管理者必須提供的功能,但是它避免了在嘗試使用它們時所提到的令人頭疼的問題(使用正確版本解決依賴性問題)。

此外,這意味着我們的軟件包可以在CPAN運行的任何平臺上以編程方式構建(或通過shell手動構建)。依賴於軟件包管理器會影響您將軟件分發到不使用/支持軟件包管理器的平臺的能力。

+0

是否有自動的方式,在你安裝了更新你的perl版本(比如說5.6.1到5.6.2)的操作系統更新之後,升級你安裝的所有CPAN模塊? – 2008-12-29 18:23:58

+1

哦,不要緊 - 我從對另一個問題的回答中看到, – 2008-12-29 18:25:53

+0

Paul:預計它是兼容的,任何在5.6.1上編譯的XS模塊都可以在5.6.2上工作,即使在5.6.2到5.61之間也是可以兼容的, – 2009-02-14 00:44:29

0

我建議只使用cpan。在Linux發行版中包含的模塊僅包括軟件包依賴性。當你只用CD安裝沒有互聯網訪問的linux時,它不能使用cpan,因此一些模塊被包含在軟件包中,但是對於Perl開發者來說這是不好的。

此外,我曾經有一個cpan配置爲在我的家庭(.perl)沒有根登錄需要安裝模塊。

35

爲了開發,我安裝了自己的Perl,並讓系統Perl獨自一人。如果我想升級系統Perl,我使用系統包管理器。對於我的Perl開發,我使用cpan工具。因爲我將這些分離開來,所以我絕對不應該搞砸系統爲其維護任務等所需的Perl,但我不必依靠系統的開發決策。

安裝單獨的Perls非常簡單。當您從源代碼分發中運行Configure時,它會詢問您要在何處安裝所有內容。給它任何你喜歡的路徑。例如,我在/usr/local/perls中安裝了許多Perls,並且每個安裝的所有內容都單獨存在。然後,我爲它們在/usr/local/bin(如perl5.8.9,perl.5.10.0,perl5.10.0-線程)中創建符號鏈接。當我需要一個特定的版本,我只是用一個我想要的:在特定的二進制確保該方案拿起正確模塊搜索路徑等(它在配置相同的東西

$ perl5.10.0 program.pl 

。pm模塊)。

這是我用來創建符號鏈接的腳本。它在bin目錄中查找,找出Perl版本,並生成鏈接,如cpan5.10.1等。每個程序已經知道正確的Perl調用:

#!perl 

use 5.010; 

use strict; 
use warnings; 

use File::Basename; 
use File::Spec::Functions; 

my $perls_directory = catfile(
    $ARGV[0] // '/usr/local/perls', 
    'perl*' 
); 
die "$perls_directory does not exist!\n" 
    unless -d dirname $perls_directory; 

my $links_directory = $ARGV[1] // catfile($ENV{HOME}, 'bin'); #/ 
die "$links_directory does not exist!\n" unless -d $links_directory; 

foreach my $directory (glob($perls_directory)) 
{ 
    say "Processing $directory..."; 

    unless(-e catfile($directory, 'bin')) 
    { 
     say "\tNo bin/ directory. Skipping!"; 
     next; 
    } 

    my @perls = glob(catfile($directory, qw(bin perl5*)));  

    my($perl_version) = $perls[0] =~ m/(5\.\d+\.\d+)\z/; 
    say "\tperl version is $perl_version"; 

    foreach my $bin (glob(catfile($directory, 'bin', '*'))) 
    { 
     say "\tFound $bin"; 
     my $basename = basename($bin); 

     my $link_basename = do { 
      if($basename =~ m/5\.\d+\.\d+\z/) { $basename } 
      else        { "$basename$perl_version" } 
     }; 

     my $link = catfile($links_directory, $link_basename); 
     next if -e $link; 
     say "\t\tlinking $bin => $link"; 
     symlink $bin => $link or 
      warn "\t\tCould not create symlink [$!]: $bin => $link!"; 
    } 
} 

一切都安裝在該特定的Perl的正確位置。

我也一直在想,我應該把這些Perl目錄放在某種源代碼控制之下。如果我添加一個我不喜歡的模塊,我只是退回到以前的版本。我只是開始這樣做,並沒有玩得太多。

我已經寫了更多關於這種事情在有效Perler博客:

+4

太多人在腳下自動拍攝手動回答配置問題請始終推薦相應的開關代替:./Configure -de -Dprefix =/some/path。-Dversiononly也很好 – ysth 2008-12-30 07:50:56

6

我對我所有的箱子下面:

  • 我編譯我自己的Perl:我仍然使用5.8。[89]大多數情況下,股票5.10.0的表現回落打擊了我很多,等待5.10.1再次嘗試;
  • 我使用(並強烈建議)local :: lib模塊爲每個項目保留一個模塊目錄。現在,該目錄已rsync到所有安裝項目的服務器,但我正在使用git進行測試;
  • 我爲每個項目創建一個Task ::模塊,這樣我就可以用一個命令安裝所有的依賴項。
6

我正在使用Debian進行開發和生產,並依賴隨發行版提供的debian Perl軟件包。

對於我需要debian中沒有的Perl模塊的情況,我通常會創建自己的debian軟件包並安裝它。當然,這種方法並非沒有問題,因爲許多debian perl模塊已經過時(至少在當前的debian穩定版本 - etch中),並且backporting像Catalyst這樣有很多依賴關係是不切實際的。但是,依靠OS軟件包管理器,我保留了它的所有優點,這使得易於維護,尤其是對於已部署的服務器,因爲您確切知道安裝了哪些軟件包,以及簡單的apt-get update;apt-get upgrade(來自debian,或來自本地存儲庫)將所有服務器升級到相同的狀態,包括Perl模塊。

4

我也使用cpan shell和local :: lib。

你不應該爲每個項目需要一個Task ::。只要使用模塊::安裝(我喜歡用模塊::啓動這樣的:

$ module-starter --mi --module=Module::Name --author="Me" [email protected] 

,然後就彈出你的依賴關係,需要「模塊::依賴」;在Makefile.PL。最後,當它的安裝時間,你只是perl Makefile.PL(回答是),則make installdeps

[編輯5年的時候我給了這個答案原本]

這些天perlbrew和cpanm是使用的東西。 local :: lib仍然有一個用例,但是perlbrew和cpanm的組合解決了這些情況的一個超集。如果您不準備編譯自己的Perl,請使用local :: lib。

0

對於生產:

在發展中,選擇一個版本,它似乎是正確的要求進行的Perl模塊;如果可能的話選擇目標操作系統的發貨版本(這使得以下大部分是多餘的),否則,選擇另一個。爲它創建一個RPM spec文件。使用clean build VM以可重現的方式(從相應分支中籤入的specfile/source)構建RPM。

當可以構建最終構建(合併後)時,從發佈分支執行相同的構建,將生成的RPM提交到部署存儲庫。這將用於最終驗證,然後通過複製到生產存儲庫發佈到生產。

生產中的所有服務器都使用完全相同的二進制文件;他們使用與開發者預期的相同的spec文件和源代碼。

Perl模塊不會被任何不遵循此模型的進程升級。也沒有任何其他生產軟件。

0

我使用FreeBSD ports並將所有CPAN依賴關係作爲local port的一個「元端口」來包裝。 FreeBSD有相當多的CPAN模塊和它們的build system is approachable enough,你可以很容易地編寫自己的端口,如果它不存在 - 只是不要忘記submit said port,所以它被包含在端口樹中。如果該端口沒有庫存的當前版本,則可以隨時編輯該端口的Makefile,以便使用新版本,don't forget to submit the change :-)。

最後,我使用Tinderbox將整個混亂構建爲二進制包,然後安裝在所有生產和開發機器上。底線 - 一旦你克服了編輯Makefiles的恐懼症,FreeBSD的端口是維護你的perl應用程序及其依賴關係的好方法。

0

我最近使用Gentoo的開始和Gentoo在這方面有幾個非常重要的優勢。首先,g-cpan通常可以安裝CPAN中的許多(儘管不是全部)模塊,因爲Gentoo軟件包本地安裝,儘管更新會有點問題。

通常在Gentoo上,我的方法是使用g-cpan創建一個ebuild文件,然後根據需要進行安裝,然後進行調整。優點是升級變得非常簡單。然後我將文件從g-cpan/perl移動到dev-perl,並將其放在覆蓋層中供其他人使用。這使我能夠快速處理這些情況下,g-cpan不會和gentoo包裝變得輕而易舉/