28
loading...
This website collects cookies to deliver better user experience
print
statements or logging. I use the debugger all the time, and I’ve realized that some more techniques are worth covering./say-hello
) returns a certain JSON structure ({"message": "Hello world!"}
):#!/usr/bin/env perl
use Test::Most;
use Test::WWW::Mechanize::PSGI;
use JSON::MaybeXS;
use Local::MyApp; # name of app's main module
my $mech = Test::WWW::Mechanize::PSGI->new(
# a Dancer2 app, so to_app returns a PSGI coderef
app => Local::MyApp->to_app(),
);
$mech->get_ok('/say-hello');
lives_and {
my $json = decode_json($mech->content);
cmp_deeply( $json, {message => 'Hello world!'} );
} 'message is Hello world!';
done_testing;
decode_json
to fail? Eventually, you’ll rewrite the test in the script to output the offending content when something goes wrong, but right now you want to suss out the root cause.b
command or continue to a one-time breakpoint with the c
command, or we can insert them into the code ourselves before running it through the debugger in the first place.lives_and {
line:$DB::single = 1;
s
command in the debugger at that line, stopping execution at that point. Run our test with perl’s -d
option, and then type c
to continue to that breakpoint:$ perl -d -Ilib t/test_psgi.t
Loading DB routines from perl5db.pl version 1.60
Editor support available.
Enter h or 'h h' for help, or 'man perldebug' for more help.
[Local::MyApp:7170] core @2021-07-06 07:33:22> Built config from files: /Users/mgardner/Projects/blog/myapp/config.yml /Users/mgardner/Projects/blog/myapp/environments/development.yml in (eval 310)[/Users/mgardner/.plenv/versions/5.34.0/lib/perl5/site_perl/5.34.0/Sub/Quote.pm:3] l. 910
Test2::API::CODE(0x7ffabea39ee8)(/Users/mgardner/.plenv/versions/5.34.0/lib/perl5/site_perl/5.34.0/Test2/API.pm:71):
71: INIT { eval 'END { test2_set_is_end() }; 1' or die $@ }
DB<1> c
[...]
ok 1 - GET /say-hello
main::CODE(0x7f8069caf2c8)(t/test_psgi.t:14):
15: my $json = decode_json($mech->content);
DB<1>
DB<1> x $mech->content
0 '{"error":"Undefined subroutine &Local::MyApp::build_frog called at lib/Local/MyApp.pm line 11.\\n"}'
DB<2>
DB<2> f lib/Local/MyApp.pm
DB<3> l 10-20
10: my $method = 'build_frog';
11: $method->();
12 }
13: catch ($e) {
14: send_as JSON => {error => $e};
15 }
16: send_as JSON => {message => 'Hello world!'};
17: };
18
19 sub build_frob {
20: return;
DB<4>
$method
variable against the list of available methods in the Local::MyApp
package.DB<4> b 11
DB<5> $mech->get('/say-hello')
[...]
Local::MyApp::CODE(0x7f8066f2db60)(lib/Local/MyApp.pm:11):
11: $method->();
DB<<6>> x $method
0 'build_frog'
DB<<7>> m Local::MyApp
any
app
body_parameters
build_frob
captures
config
content
[...]
DB<<8>>
q
command, make the fix (we probably want errors to give something other than an HTTP 200 OK while we’re at it), and re-run the test:$ perl -Ilib t/test_psgi.t
[Local::MyApp:8277] core @2021-07-06 07:48:36> Built config from files: /Users/mgardner/Projects/blog/myapp/config.yml /Users/mgardner/Projects/blog/myapp/environments/development.yml in (eval 309) l. 910
Name "DB::single" used only once: possible typo at t/test_psgi.t line 13.
[Local::MyApp:8277] core @2021-07-06 07:48:36> looking for get /say-hello in /Users/mgardner/.plenv/versions/5.34.0/lib/perl5/site_perl/5.34.0/Dancer2/Core/App.pm l. 35
[Local::MyApp:8277] core @2021-07-06 07:48:36> Entering hook core.app.before_request in (eval 274) l. 1
[Local::MyApp:8277] core @2021-07-06 07:48:36> Entering hook core.app.before_file_render in (eval 274) l. 1
[Local::MyApp:8277] core @2021-07-06 07:48:36> Entering hook core.app.after_file_render in (eval 274) l. 1
[Local::MyApp:8277] core @2021-07-06 07:48:36> Entering hook core.app.after_request in (eval 274) l. 1
ok 1 - GET /say-hello
ok 2 - message is Hello world!
1..2
$DB::single
in there. While harmless, it’s a good reminder to remove such lines from your code so that they don’t surprise you or your teammates during future debugging sessions.