I've found the problem, although I don't have a solution yet. In short,
a disabled dist tells Distrostatus "NO" but it's goodbye message is
"NA". I don't know if that's a bug, though. If I change that "NO" to
"NA" all the tests still pass, but I don't know enough about the long
range intent to know if that's a good change.

Here's the walkthrough. I know you guys know the code, but here it is
anyway:

In my CPAN.pm config, I set halt_on_failure to true. Of course, if I
had just searched for the error message, I would have found it in
Shell.pm:

        if ($CPAN::Config->{halt_on_failure}
                &&
                    CPAN::Distrostatus::something_has_just_failed()
              ) {
            $CPAN::Frontend->mywarn("Stopping: '$meth' failed for
'$s'.\n");
            CPAN::Queue->nullify_queue;
            last QITEM;
        }

So, when Distroprefs gets a hit, the Distrostatus gets set to a failure
because it has "NO" in the string.

   --------------CPAN::Distrostatus::new <-- CPAN::Distribution
CPAN::Distribution::get 1677
   $VAR1 = bless( {
                'COMMANDID' => 0,
                'TEXT' => 'NO Disabled via prefs file
\'/Users/brian/Desktop/DistroFailure/distroprefs/skip_expect.yml\' doc
0',
                'TIME' => 1259845689,
                'FAILED' => 1
               }, 'CPAN::Distrostatus' );

This comes from Distribution.pm's get():

        if ($self->prefs->{disabled} && ! $self->{force_update}) {
            my $why = sprintf(
                              "Disabled via prefs file '%s' doc %d",
                              $self->{prefs_file},
                              $self->{prefs_file_doc},
                             );
            push @e, $why;
            $self->{unwrapped} = CPAN::Distrostatus->new("NO $why");
            $goodbye_message = "[disabled] -- NA $why";
            # note: not intended to be persistent but at least visible
            # during this session
        } else {

Now, once something fails, the class variable
$CPAN::Distroprefs::something_has_failed_at becomes true and nothing
ever resets it. When something else checks something_has_just_failed(),
it gets the answer from a previous call to install().

So, there's the tricky part. If I call install() twice, I expect it to
be different than a recursive call to install():

     CPAN::Shell->install();
     CPAN::Shell->install(); # should start fresh

I could wrap that and reset stuff myself, but I'd rather see install()
knowing when it's at the top and when it's recursive. I'm still looking
through the code and seeing what is what.

Reply via email to