[rt.cpan.org #60622] Handle conditional loading
David Leadbeater [Mon, 20 Dec 2010 18:09:37 +0000 (18:09 +0000)]
Now uses a CHECK block to see what is actually loaded, rather than using
a @INC hook which sees what might be loaded.

Also add some basic tests for tracing module loading.

lib/App/FatPacker/Trace.pm
t/basic.t
t/mod/a.pm [new file with mode: 0644]
t/mod/b.pm [new file with mode: 0644]
t/mod/c.pm [new file with mode: 0644]
t/mod/cond.pm [new file with mode: 0644]
t/trace.t [new file with mode: 0644]

index 6d1f68a..1da5943 100644 (file)
@@ -4,14 +4,28 @@ use strict;
 use warnings FATAL => 'all';
 use B ();
 
+my $trace_file;
+my %initial_inc;
+
 sub import {
-  my $open = $_[1] || '>>fatpacker.trace';
-  open my $trace, $open
-    or die "Couldn't open ${open} to trace to: $!";
-  unshift @INC, sub {
-    print $trace "$_[1]\n";
-  };
+  $trace_file = $_[1] || '>>fatpacker.trace';
+  # For filtering out our own deps later.
+  # (Not strictly required as these are core only and won't have packlists, but 
+  # looks neater.)
+  %initial_inc = %INC;
   B::minus_c;
 }
 
+CHECK {
+  return unless $trace_file; # not imported
+
+  open my $trace, $trace_file
+      or die "Couldn't open $trace_file to trace to: $!";
+
+  for my $inc(keys %INC) {
+    next if exists $initial_inc{$inc};
+    print $trace "$inc\n";
+  }
+}
+
 1;
index 6e97616..9da7609 100644 (file)
--- a/t/basic.t
+++ b/t/basic.t
@@ -3,6 +3,5 @@ use warnings FATAL => 'all';
 use Test::More qw(no_plan);
 
 require App::FatPacker;
-require App::FatPacker::Trace;
 
 pass "Didn't blow up";
diff --git a/t/mod/a.pm b/t/mod/a.pm
new file mode 100644 (file)
index 0000000..c119640
--- /dev/null
@@ -0,0 +1,3 @@
+package t::mod::a;
+use t::mod::b;
+1;
diff --git a/t/mod/b.pm b/t/mod/b.pm
new file mode 100644 (file)
index 0000000..9127201
--- /dev/null
@@ -0,0 +1,3 @@
+package t::mod::b;
+use t::mod::c;
+1;
diff --git a/t/mod/c.pm b/t/mod/c.pm
new file mode 100644 (file)
index 0000000..09f8b20
--- /dev/null
@@ -0,0 +1,2 @@
+package t::mod::c;
+1;
diff --git a/t/mod/cond.pm b/t/mod/cond.pm
new file mode 100644 (file)
index 0000000..d4af160
--- /dev/null
@@ -0,0 +1,3 @@
+package t::mod::cond;
+eval { require t::mod::nothere };
+1;
diff --git a/t/trace.t b/t/trace.t
new file mode 100644 (file)
index 0000000..154e83c
--- /dev/null
+++ b/t/trace.t
@@ -0,0 +1,29 @@
+#!perl
+use Test::More;
+
+test_trace("t/mod/a.pm" => ("t/mod/b.pm", "t/mod/c.pm"));
+test_trace("t/mod/b.pm" => ("t/mod/c.pm"));
+test_trace("t/mod/c.pm" => ());
+
+# Attempts to conditionally load a module that isn't present
+test_trace("t/mod/cond.pm" => ());
+
+done_testing;
+
+sub test_trace {
+  my($file, @loaded) = @_;
+  local $Test::Builder::Level = $Test::Builder::Level + 1;
+
+  system($^X, "-Mblib", "-MApp::FatPacker::Trace", $file);
+
+  open my $trace, "<", "fatpacker.trace";
+  while(<$trace>) {
+    chomp;
+    my $load = $_;
+    @loaded = grep { $load ne $_ } @loaded;
+  }
+
+  ok !@loaded, "All expected modules loaded for $file";
+  unlink "fatpacker.trace";
+}
+