NAME

CPAN::Dependency - Analyzes CPAN modules and generates their dependency tree

VERSION

Version 0.04

SYNOPSIS

use CPAN::Dependency;

my $cpandeps = CPAN::Dependency->new(process => ALL_CPAN);
$cpandeps->run;  # this may take some time..

my %score = $cpandep->score_by_dists;
my @dists = sort { $score{$b} <=> $score{$a} } keys %score;
print "Top 10 modules\n";
for my $dist (@dists[0..9]) {
    printf "%5d %s\n", $score{$dist}, $dist;
}

DESCRIPTION

This module can process a set of distributions, up to the whole CPAN, and extract the dependency relations between these distributions. It also calculates a score for each distribution based on the number of times it appears in the prerequisites of other distributions. The algorithm is descibed in more details in "SCORE CALCULATION".

METHODS

new()

Creates and returns a new object.

Options

  • process - adds modules or distributions to the list of packages to process.

  • skip - adds modules or distributions you don't want to process.

  • color - use colors (when verbose is also set).

  • debug - sets debug level.

  • prefer_bin - tells CPANPLUS to prefer binaries programs.

  • verbose - sets the verbose mode.

Examples

Create a new CPAN::Dependency object with verbose mode enabled and adds three "big" modules to the process list:

my $cpandeps = new CPAN::Dependency verbose => 1, 
        process => [qw(WWW::Mechanize Maypole Template CPAN::Search::Lite)]

Create a new CPAN::Dependency object with verbose mode enabled and adds all the distributions from the CPAN to the process list:

my $cpandeps = new CPAN::Dependency verbose =>1, process => ALL_CPAN;
process()

Adds given distribution or module names to the list of packages to process. The special argument ALL_CPAN can be used to specify that you want to process all packages in the CPAN.

Examples

Add distributions and modules to the process list, passing as a list:

$cpandep->process('WWW::Mechanize', 'Maypole', 'CPAN-Search-Lite');

Add distributions and modules to the process list, passing as an arrayref:

$cpandep->process(['WWW-Mechanize', 'Maypole::Application', 'CPAN::Search::Lite']);
skip()

Adds given distribution or module names to the list of packages that you don't want to process.

Examples

Add distributions and modules to the skip list, passing as a list:

$cpandep->skip('LWP::UserAgent', 'Net_SSLeay.pm', 'CGI');

Add distributions and modules to the skip list, passing as an arrayref:

$cpandep->skip('libwww-perl', 'Net::SSLeay', 'CGI.pm');
run()

Launches the execution of the CPAN::Dependency object.

calculate_score()

Calculate the score of each distribution by walking throught the dependency tree.

deps_by_dists()

Return the hashref of the object that contains the dependency tree indexed by distribution names.

save_deps_tree()

Saves the dependency tree of the object to a YAML stream. Expect one of the following options.

Options

  • file - saves to the given YAML file.

Examples

$cpandep->save_deps_tree(file => 'deps.yml');
load_deps_tree()

Loads a YAML stream that contains a dependency tree into the current object. Expect one of the following options.

Options

  • file - loads from the given YAML file.

Examples

$cpandep->load_deps_tree(file => 'deps.yml');
score_by_dists()

Returns a new hash that contains the score of the processed distributions, indexed by the distribution names.

Internal Methods

_tree_walk()

Walks throught the dependency tree and updates the score of each distribution. See "SCORE CALCULATION".

_vprint()

Like print() but prints only when option verbose is set.

_vprintf()

Like printf() but prints only when option verbose is set.

OPTIONS

color()

Selects whether to use ANSI colors or not when verbose is enabled. Defaults to yes (1).

debug()

Set debug level. Defaults to 0.

prefer_bin()

Tells CPANPLUS to use binary programs instead of Perl modules when there is the choice (i.e. use tar(1) instead of Archive::Tar).

verbose()

Sets verbose mode to on (1) or off (0). Defaults to off.

SCORE CALCULATION

Once the prerequisites for each distribution have been found, the score of each distribution is calculated using the following algorithm:

  1. for each distribution D

  2. for each prerequisite P of this distribution

  3. if both D and P are not made by the same auhor, update the score of P by adding it the current dependency depth

  4. recurse step 1 using P

The aim of this algorithm is to increase the score of distributions that are depended upon by many other distributions, while avoiding the cases where one author releases a horde of modules which depend upon each others.

SPEED TIPS

Here are a few tips to speed up the processing when you want to process many modules (or the whole CPAN).

Local mirror

If it's not the case yet, you should use CPAN::Mini to create your own mini-CPAN local mirror. Then you just need to configure CPANPLUS to use your mini-CPAN instead of a network mirror. A mini-CPAN can also be shared using a web server but if you want speed, you should keep one on your local filesystem.

Note that you can also add your own private distributions into your mini-CPAN using CPAN::Mini::Inject. This is useful if you want to use CPAN::Dependency on modules that are not publicly shared on the CPAN.

More information at http://search.cpan.org/dist/CPAN-Mini/ and http://search.cpan.org/dist/CPAN-Mini-Inject/.

Ramdisk

If your system supports this feature (most modern systems do), you should create a ramdisk and move the CPANPLUS build directory onto the ramdisk. Here are the instructions for Linux. Other systems are left as an exercice for the reader :-)

Ramdisk for Linux

The following commands must be executed as root. cpanplus is assumed to be the user that will executes this module.

  • Create a ramdisk of 24 MB:

    dd if=/dev/zero of=/dev/ram0 bs=1M count=24
  • Format it and creates and Ext2 filesystem:

    mke2fs -L ramdisk0 /dev/ram0
  • Now mount it:

    mkdir /mnt/ramdisk
    mount /dev/ram0 /mnt/ramdisk/
    mkdir /mnt/ramdisk/cpanplus
    chown cpanplus /mnt/ramdisk/cpanplus/
  • Now, as the user cpanplus, move the build directory onto the ramdisk and symlink it:

    mv .cpanplus/5.8.5 /mnt/ramdisk/maddingue/
    ln -s /mnt/ramdisk/maddingue/5.8.5 .cpanplus/5.8.5

Note that we are explicitly avoiding to move the whole .cpanplus/ directory because it will grow really big during the processing: some CPANPLUS cache files are already big, and the sub-directory author/ will contain a copy of each processed archive. When processing the whole CPAN, it means that you'll have here a complete copy of your mini-CPAN, so be sure that you have enought disk space (or symlink this directory as well to another volume when you have enought space).

Ramdisk for Mac OS X

Here is a small shell script that creates, format and mount a ramdisk of 32 MB. Its size can be changed by changing the number of blocks, where one block is 512 bytes.

#!/bin/sh
BLOCK=64000
dev=`hdid -nomount ram://$BLOCKS`
newfs_hfs -v RAMDisk $dev
mkdir /Volumes/RAMDisk
chmod 777 /Volumes/RAMDisk
mount -t hfs $dev /Volumes/RAMDisk

Then follow the same instructions for moving the build/ directory as given for Linux.

DIAGNOSTICS

Can't create CPANPLUS::Backend object

(F) CPANPLUS::Backend was unable to create and return a new object.

No argument given to atribute '%s'

(W) As the message implies, you didn't supply the expected argument to the attribute.

Unknown option '%s': ignoring

(W) You gave to new() an unknown attribute name.

AUTHOR

Sébastien Aperghis-Tramoni, <sebastien@aperghis.net>

BUGS

Please report any bugs or feature requests to bug-cpan-dependency@rt.cpan.org, or through the web interface at https://rt.cpan.org/NoAuth/ReportBug.html?Queue=CPAN-Dependency. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes.

ACKNOWLEDGEMENTS

COPYRIGHT & LICENSE

Copyright 2005 Sébastien Aperghis-Tramoni, All Rights Reserved.

This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself.