File Coverage

lib/mocked.pm
Criterion Covered Total %
statement 38 38 100.0
branch 7 10 70.0
condition 5 5 100.0
subroutine 7 7 100.0
pod 0 1 0.0
total 57 61 93.4


line stmt bran cond sub pod time code
1             package mocked;
2 2     2   113973 use strict;
  2         5  
  2         68  
3 2     2   13 use warnings;
  2         4  
  2         75  
4 2     2   11 use base 'Exporter'; # load this so mocked libraries can export things
  2         8  
  2         239  
5 2     2   2331 use unmocked;
  2         5  
  2         11  
6              
7             =head1 NAME
8              
9             mocked - use mocked libraries in unit tests
10              
11             =head1 SYNOPSIS
12              
13             # use a fake LWP::Simple for testing from t/lib/LWP/Simple.pm
14             use mocked 'LWP::Simple';
15             my $text = get($url);
16              
17             # use a fake WWW::Mechanize for testing from t/mock-libs/WWW/Mechanize.pm
18             use mocked [qw(WWW::Mechanize t/mock-libs)];
19            
20              
21             =head1 DESCRIPTION
22              
23             Often during unit testing, you may find the need to use mocked libraries
24             to test edge cases, or prevent unit tests from using slow or external
25             code.
26              
27             This is where mocking libraries can help.
28              
29             When you mock a library, you are creating a fake one that will be used
30             in place of the real one. The code can do as much or as little as is
31             needed.
32              
33             Use mocked.pm as a safety measure (be sure you're actually using the
34             mocked module), and as a way to document the tests for future
35             maintainers.
36              
37             =cut
38              
39             our $VERSION = '0.09';
40              
41             =head1 VARIABLES
42              
43             =head2 real_inc_paths
44              
45             The real @INC that we are over-ridding is stored here while we are
46             loading the mocked library.
47              
48             =cut
49              
50             our $real_inc_paths;
51              
52             =head1 FUNCTIONS
53              
54             =head2 import
55              
56             With a package name, this function will ensure that the module you specify
57             is loaded from t/lib.
58              
59             You can also pass an array reference containing the package name and a
60             directory from which to load it from.
61              
62             =cut
63              
64             sub import {
65 7     7   1538 my $class = shift;
66 7         9 my $module = shift;
67 7 50       21 return unless $module;
68            
69             {
70 2     2   11 no strict 'refs';
  2         13  
  2         943  
  7         9  
71 7         19 my $sym = $module . '::';
72 7 100 100     16 if(
73 6         54 exists $INC{ convert_package_to_file($module) }
74             || (keys %{$sym})
75             ){
76 2         15 die q{Attempting to mock an already loaded library};
77             }
78             }
79              
80 5         10 my $mock_path = 't/lib';
81 5 100       17 if(ref($module) eq 'ARRAY'){
82 1         2 ($module, $mock_path) = @$module;
83             }
84            
85             # Load the real inc paths the first time we're called.
86 5   100     19 $real_inc_paths ||= \@INC;
87             {
88 5         7 local @INC = ($mock_path);
  5         12  
89 5         524 eval "require $module";
90             }
91 5 50       927 die $@ if $@;
92              
93 5         59 my $import = $module->can('import');
94 5         15 @_ = ($module, @_);
95 5 50       331 goto &$import if $import;
96             }
97              
98             sub convert_package_to_file {
99 7     7 0 12 my $package = shift;
100 7         33 (my $filename = $package) =~ s{::}{/}g;
101 7         12 $filename .= q{.pm};
102 7         33 return $filename;
103             }
104              
105             =head1 AUTHOR
106              
107             Luke Closs, C<< <cpan at 5thplane.com> >>
108             Scott McWhirter, C<< <kungfuftr at cpan.org> >>
109              
110             =head1 MAD CREDS TO
111              
112             Ingy döt net, for only.pm
113              
114             =head1 LICENSE
115              
116             This program is free software; you can redistribute it and/or modify it
117             under the same terms as Perl itself.
118              
119             =cut
120              
121             1;