File Coverage

blib/lib/HTML/Highlighter.pm
Criterion Covered Total %
statement 60 60 100.0
branch 13 16 81.2
condition 1 3 33.3
subroutine 10 10 100.0
pod 1 1 100.0
total 85 90 94.4


line stmt bran cond sub pod time code
1             package HTML::Highlighter;
2              
3 1     1   34886 use strict;
  1         3  
  1         25  
4 1     1   4 use warnings;
  1         2  
  1         19  
5              
6 1     1   850 use HTML::Parser;
  1         7465  
  1         37  
7 1     1   778 use Plack::Request;
  1         69232  
  1         34  
8 1     1   10 use Plack::Util::Accessor qw/param callback/;
  1         2  
  1         12  
9 1     1   59 use List::Util qw/first/;
  1         2  
  1         114  
10              
11 1     1   6 use parent 'Plack::Middleware';
  1         2  
  1         7  
12              
13 1     1   1298 use 5.008_001;
  1         3  
  1         633  
14             our $VERSION = "0.05";
15             $VERSION = eval $VERSION;
16              
17             sub call {
18 6     6 1 31096 my ($self, $env) = @_;
19              
20 6         29 my $res = $self->app->($env);
21              
22             $self->response_cb( $res, sub {
23 6     6   150 my $res = shift;
24 6         18 my $h = Plack::Util::headers($res->[1]);
25              
26 6         145 my $type = $h->get("Content-Type");
27 6 50 33     261 return $res unless $type and $type =~ /html/i;
28              
29 6 100       21 $self->callback->($env) if $self->callback;
30              
31 6         66 my $req = Plack::Request->new($env);
32 6 100       56 $self->param("") unless defined $self->param;
33              
34 6         41 my $highlights = do {
35 6 100       17 if ($env->{'psgix.highlight'}) {
36 1         2 $env->{'psgix.highlight'};
37             } else {
38 5         40 my $param = first {$req->parameters->{$_}} ($self->param, qw/q query search highlight/);
  15         732  
39 5 50       232 $param ? $req->parameters->{$param} : undef;
40             }
41             };
42              
43 6 50       40 return $res unless $highlights;
44 6         14 my @highlights = split /\s+/, $highlights;
45              
46 6         7 my $html;
47             my $p = HTML::Parser->new(
48             api_version => 3,
49             handlers => {
50             default => [
51             sub {
52 54         148 $html .= $_[0]
53             }, "text"
54             ],
55             text => [
56             sub {
57 48         66 for my $highlight (@highlights) {
58 48         205 $_[0] =~ s/(\Q$highlight\E)/$1<\/span>/gi;
59             }
60 48         145 $html .= $_[0]
61             }, "text"
62             ],
63             end_document => [
64             sub {
65 6         17 $res->[2] = [$html];
66 6         40 $h->set('Content-Length' => length $html)
67             }
68 6         78 ],
69             }
70             );
71              
72 6         274 my $done;
73              
74             return sub {
75 18         2251 my $chunk = shift;
76 18 100       45 return if $done;
77              
78 12 100       20 if (defined $chunk) {
79 6         42 $p->parse($chunk);
80 6         20 return '';
81             } else {
82 6         30 $p->eof;
83 6         238 $done = 1;
84 6         20 return $html;
85             }
86 6         38 };
87 6         1614 });
88             }
89              
90             1;
91              
92             __END__