1*5486feefSafresh1use strict;
2*5486feefSafresh1use warnings;
3*5486feefSafresh1use Test2::Tools::Defer;
4*5486feefSafresh1# HARNESS-NO-FORK
5*5486feefSafresh1
6*5486feefSafresh1my $file = __FILE__;
7*5486feefSafresh1
8*5486feefSafresh1my $START_LINE;
9*5486feefSafresh1BEGIN {
10*5486feefSafresh1    $START_LINE = __LINE__;
11*5486feefSafresh1    def ok => (1, "truth");
12*5486feefSafresh1    def is => (1, 1, "1 is 1");
13*5486feefSafresh1    def is => ({}, {}, "hash is hash");
14*5486feefSafresh1
15*5486feefSafresh1    def ok => (0, 'lies');
16*5486feefSafresh1    def is => (0, 1, "1 is not 0");
17*5486feefSafresh1    def is => ({}, [], "a hash is not an array");
18*5486feefSafresh1}
19*5486feefSafresh1
20*5486feefSafresh1use Test2::Bundle::Extended -target => 'Test2::Tools::Defer';
21*5486feefSafresh1
22*5486feefSafresh1sub capture(&) {
23*5486feefSafresh1    my $code = shift;
24*5486feefSafresh1
25*5486feefSafresh1    my ($err, $out) = ("", "");
26*5486feefSafresh1
27*5486feefSafresh1    my ($ok, $e);
28*5486feefSafresh1    {
29*5486feefSafresh1        local *STDOUT;
30*5486feefSafresh1        local *STDERR;
31*5486feefSafresh1
32*5486feefSafresh1        ($ok, $e) = Test2::Util::try(sub {
33*5486feefSafresh1            open(STDOUT, '>', \$out) or die "Failed to open a temporary STDOUT: $!";
34*5486feefSafresh1            open(STDERR, '>', \$err) or die "Failed to open a temporary STDERR: $!";
35*5486feefSafresh1
36*5486feefSafresh1            $code->();
37*5486feefSafresh1        });
38*5486feefSafresh1    }
39*5486feefSafresh1
40*5486feefSafresh1    die $e unless $ok;
41*5486feefSafresh1
42*5486feefSafresh1    return {
43*5486feefSafresh1        STDOUT => $out,
44*5486feefSafresh1        STDERR => $err,
45*5486feefSafresh1    };
46*5486feefSafresh1}
47*5486feefSafresh1
48*5486feefSafresh1is(
49*5486feefSafresh1    intercept { do_def },
50*5486feefSafresh1    array {
51*5486feefSafresh1        filter_items { grep { $_->isa('Test2::Event::Ok') || $_->isa('Test2::Event::Fail') } @_ };
52*5486feefSafresh1
53*5486feefSafresh1        event Ok => sub {
54*5486feefSafresh1            call pass => 1;
55*5486feefSafresh1            call name => 'truth';
56*5486feefSafresh1            prop file => "(eval in Test2::Tools::Defer) " . __FILE__;
57*5486feefSafresh1            prop line => $START_LINE + 1;
58*5486feefSafresh1            prop package => __PACKAGE__;
59*5486feefSafresh1        };
60*5486feefSafresh1
61*5486feefSafresh1        event Ok => sub {
62*5486feefSafresh1            call pass => 1;
63*5486feefSafresh1            call name => '1 is 1';
64*5486feefSafresh1            prop file => "(eval in Test2::Tools::Defer) " . __FILE__;
65*5486feefSafresh1            prop line => $START_LINE + 2;
66*5486feefSafresh1            prop package => __PACKAGE__;
67*5486feefSafresh1        };
68*5486feefSafresh1
69*5486feefSafresh1        event Ok => sub {
70*5486feefSafresh1            call pass => 1;
71*5486feefSafresh1            call name => 'hash is hash';
72*5486feefSafresh1            prop file => "(eval in Test2::Tools::Defer) " . __FILE__;
73*5486feefSafresh1            prop line => $START_LINE + 3;
74*5486feefSafresh1            prop package => __PACKAGE__;
75*5486feefSafresh1        };
76*5486feefSafresh1
77*5486feefSafresh1        event Ok => sub {
78*5486feefSafresh1            call pass => 0;
79*5486feefSafresh1            call name => 'lies';
80*5486feefSafresh1            prop file => "(eval in Test2::Tools::Defer) " . __FILE__;
81*5486feefSafresh1            prop line => $START_LINE + 5;
82*5486feefSafresh1            prop package => __PACKAGE__;
83*5486feefSafresh1        };
84*5486feefSafresh1
85*5486feefSafresh1        event Fail => sub {
86*5486feefSafresh1            call name => '1 is not 0';
87*5486feefSafresh1            prop file => "(eval in Test2::Tools::Defer) " . __FILE__;
88*5486feefSafresh1            prop line => $START_LINE + 6;
89*5486feefSafresh1            prop package => __PACKAGE__;
90*5486feefSafresh1        };
91*5486feefSafresh1
92*5486feefSafresh1        event Fail => sub {
93*5486feefSafresh1            call name => 'a hash is not an array';
94*5486feefSafresh1            prop file => "(eval in Test2::Tools::Defer) " . __FILE__;
95*5486feefSafresh1            prop line => $START_LINE + 7;
96*5486feefSafresh1            prop package => __PACKAGE__;
97*5486feefSafresh1        };
98*5486feefSafresh1
99*5486feefSafresh1        end;
100*5486feefSafresh1    },
101*5486feefSafresh1    "got expected events"
102*5486feefSafresh1);
103*5486feefSafresh1
104*5486feefSafresh1def ok => (1, "truth");
105*5486feefSafresh1def is => (1, 1, "1 is 1");
106*5486feefSafresh1def is => ({}, {}, "hash is hash");
107*5486feefSafresh1
108*5486feefSafresh1# Actually run some that pass
109*5486feefSafresh1do_def();
110*5486feefSafresh1
111*5486feefSafresh1like(
112*5486feefSafresh1    dies { do_def() },
113*5486feefSafresh1    qr/No tests to run/,
114*5486feefSafresh1    "Fails if there are no tests"
115*5486feefSafresh1);
116*5486feefSafresh1
117*5486feefSafresh1my $line1 = __LINE__ + 1;
118*5486feefSafresh1sub oops { die 'oops' }
119*5486feefSafresh1
120*5486feefSafresh1my $line2 = __LINE__ + 1;
121*5486feefSafresh1def oops => (1);
122*5486feefSafresh1like( dies { do_def() }, <<EOT, "Exceptions in the test are propagated");
123*5486feefSafresh1Exception: oops at $file line $line1.
124*5486feefSafresh1--eval--
125*5486feefSafresh1package main;
126*5486feefSafresh1# line $line2 "(eval in Test2::Tools::Defer) $file"
127*5486feefSafresh1&oops(\@\$args);
128*5486feefSafresh11;
129*5486feefSafresh1--------
130*5486feefSafresh1Tool:   oops
131*5486feefSafresh1Caller: main, $file, $line2
132*5486feefSafresh1\$args:  [
133*5486feefSafresh1          1
134*5486feefSafresh1        ];
135*5486feefSafresh1EOT
136*5486feefSafresh1
137*5486feefSafresh1
138*5486feefSafresh1{
139*5486feefSafresh1    {
140*5486feefSafresh1        package Foo;
141*5486feefSafresh1        main::def ok => (1, "pass");
142*5486feefSafresh1    }
143*5486feefSafresh1    def ok => (1, "pass");
144*5486feefSafresh1
145*5486feefSafresh1    my $new_exit = 0;
146*5486feefSafresh1    my $out = capture { Test2::Tools::Defer::_verify(undef, 0, \$new_exit) };
147*5486feefSafresh1
148*5486feefSafresh1    is($new_exit, 255, "exit set to 255 due to unrun tests");
149*5486feefSafresh1    like(
150*5486feefSafresh1        $out->{STDOUT},
151*5486feefSafresh1        qr/not ok - deferred tests were not run/,
152*5486feefSafresh1        "Got failed STDOUT line"
153*5486feefSafresh1    );
154*5486feefSafresh1
155*5486feefSafresh1    like(
156*5486feefSafresh1        $out->{STDERR},
157*5486feefSafresh1        qr/# 'main' has deferred tests that were never run/,
158*5486feefSafresh1        "We see that main failed"
159*5486feefSafresh1    );
160*5486feefSafresh1
161*5486feefSafresh1    like(
162*5486feefSafresh1        $out->{STDERR},
163*5486feefSafresh1        qr/# 'Foo' has deferred tests that were never run/,
164*5486feefSafresh1        "We see that Foo failed"
165*5486feefSafresh1    );
166*5486feefSafresh1}
167*5486feefSafresh1
168*5486feefSafresh1{
169*5486feefSafresh1    local $? = 101;
170*5486feefSafresh1    def ok => (1, "pass");
171*5486feefSafresh1    my $out = capture { Test2::Tools::Defer::_verify() };
172*5486feefSafresh1    is($?, 101, "did not change exit code");
173*5486feefSafresh1    like(
174*5486feefSafresh1        $out->{STDOUT},
175*5486feefSafresh1        qr/not ok - deferred tests were not run/,
176*5486feefSafresh1        "Got failed STDOUT line"
177*5486feefSafresh1    );
178*5486feefSafresh1
179*5486feefSafresh1    like(
180*5486feefSafresh1        $out->{STDERR},
181*5486feefSafresh1        qr/# 'main' has deferred tests that were never run/,
182*5486feefSafresh1        "We see that main failed"
183*5486feefSafresh1    );
184*5486feefSafresh1}
185*5486feefSafresh1
186*5486feefSafresh1done_testing;
187