File Coverage

blib/lib/Mojolicious/Plugin/Images/Util.pm
Criterion Covered Total %
statement 76 87 87.3
branch 31 48 64.5
condition 6 10 60.0
subroutine 11 13 84.6
pod 6 6 100.0
total 130 164 79.2


line stmt bran cond sub pod time code
1             package Mojolicious::Plugin::Images::Util;
2 9     9   676900 use Mojo::Base -base;
  9         13  
  9         55  
3 9     9   1288 use 5.20.0;
  9         30  
  9         291  
4 9     9   943 use experimental 'signatures';
  9         1265  
  9         46  
5              
6 9     9   836 use Exporter 'import';
  9         58  
  9         238  
7 9     9   2010 use IO::All;
  9         33773  
  9         55  
8              
9             our @EXPORT_OK = (
10             qw(install_route expand_static calc_static plugin_log check_dir check_id));
11             our %EXPORT_TAGS = (all => \@EXPORT_OK);
12              
13             my $INSECURE_IDS = $ENV{IMAGES_ALLOW_INSECURE_IDS};
14             my $INSECURE_DIRS = $ENV{IMAGES_ALLOW_INSECURE_DIRS};
15              
16 67 50   67 1 5401 sub check_dir($dir, $app) {
  67 50       136  
  67         89  
  67         67  
  67         66  
17 67 100       154 return $dir if $INSECURE_DIRS;
18 48         55 my $msg
19 48   100     194 = "insecure dir ${\ ( $dir // 'undef' ) }, set IMAGES_ALLOW_INSECURE_DIRS env to allow it";
20 48 100 100     1068 die $msg if !$dir || Mojo::Path->new($app->home)->contains("$dir");
21 29         4700 return $dir;
22             }
23              
24             # maybe too hard
25 70 50   70 1 142 sub check_id($id) {
  70 50       119  
  70         75  
  70         63  
26 70 100       171 return $id if $INSECURE_IDS;
27 48 100       360 die "insecure id $id, set IMAGES_ALLOW_INSECURE_IDS env to allow it"
28             unless $id =~ /^[\ \-\w\/]+$/;
29 43         277 return $id;
30             }
31              
32 41 50   41 1 1598 sub plugin_log($app, $tmpl, @args) {
  41         45  
  41         42  
  41         111  
  41         45  
33 41         113 my $msg = sprintf($tmpl, @args);
34 41         809 $app->log->debug("Mojolicious::Plugin::Images $msg");
35             }
36              
37 43 50   43 1 20618 sub calc_static($dir, $url_prefix, $home) {
  43 50       106  
  43         58  
  43         52  
  43         45  
  43         44  
38 43 100       92 return unless defined $url_prefix;
39              
40 41         119 $dir = io->dir($dir)->canonpath;
41 41 100       60991 $dir = $home->rel_dir($dir) unless io->dir($dir)->is_absolute;
42              
43 41         6232 my $prefix = Mojo::Path->new($url_prefix)->canonicalize->to_route;
44 41         6101 $prefix = Mojo::Path->new($prefix)->leading_slash(0)->trailing_slash(0);
45              
46 41 100       2735 $dir =~ s/$prefix$// or return;
47              
48 31         2074 io->dir($dir)->canonpath;
49             }
50              
51 32 50   32 1 21471 sub expand_static($dir, $url_prefix, $app) {
  32 50       74  
  32         47  
  32         33  
  32         35  
  32         36  
52 32 100       695 my $static_path = calc_static($dir, $url_prefix, $app->home) or return;
53 23         4008 $static_path = check_dir($static_path, $app);
54 20         436 my $paths = $app->static->paths;
55 20 100       566 push @$paths, $static_path unless grep { $_ eq $static_path } @$paths;
  30         159  
56             }
57              
58             # install route /$prefix/(*key)-$suffix.$ext
59 19 50   19 1 50 sub install_route($app, $moniker, $opts) {
  19 50       43  
  19         72  
  19         53  
  19         23  
  19         19  
60 19         173 my $placeholder = '(*images_id)';
61 19   50     51 my $end = $opts->{suffix} // '';
62 19 100       47 $end .= ".${\$opts->{ext}}" if $opts->{ext};
  18         40  
63 19         104 my $path = Mojo::Path->new($opts->{url_prefix})->leading_slash(1)
64             ->trailing_slash(1)->merge("${placeholder}${end}");
65              
66 19         4746 plugin_log($app, "Installing route GET $path for Images '$moniker'");
67 19     0   954 $app->routes->get("$path")->to(cb => sub { _action(shift, $moniker) });
  0            
68             }
69              
70 0 0   0     sub _action($c, $moniker) {
  0 0          
  0            
  0            
  0            
71 0           my $id = $c->stash('images_id');
72 0           my $img = $c->images->$moniker;
73              
74 0           plugin_log($c->app, "Generating $moniker: $id");
75 0 0 0       return $c->reply->static($img->url($id))
76             if $img->exists($id) || $img->sync($id);
77              
78 0           return $c->reply->not_found;
79             }
80              
81             1;
82              
83             __END__