X-Git-Url: http://www.git.stargrave.org/?a=blobdiff_plain;f=lib%2FPublicInbox%2FView.pm;h=4058bee775507c70e0c1a73ca82235c4f9026f78;hb=476fc666c223f0fb;hp=61eb890f2ff46f3a076753c25e2ccf0343b707bb;hpb=f5eb6bb83558f3dabdb2fbbf7c1c926a726bfed9;p=public-inbox.git diff --git a/lib/PublicInbox/View.pm b/lib/PublicInbox/View.pm index 61eb890f..4058bee7 100644 --- a/lib/PublicInbox/View.pm +++ b/lib/PublicInbox/View.pm @@ -11,10 +11,9 @@ use Date::Parse qw/str2time/; use Encode qw/find_encoding/; use Encode::MIME::Header; use Email::MIME::ContentType qw/parse_content_type/; -use PublicInbox::Hval; -use PublicInbox::MID qw/mid_clean id_compress mid2path/; -use Digest::SHA qw/sha1_hex/; -my $SALT = rand; +use PublicInbox::Hval qw/ascii_html/; +use PublicInbox::Linkify; +use PublicInbox::MID qw/mid_clean id_compress mid2path mid_mime/; require POSIX; # TODO: make these constants tunable @@ -23,8 +22,6 @@ use constant MAX_TRUNC_LEN => 72; use constant T_ANCHOR => '#u'; use constant INDENT => ' '; -*ascii_html = *PublicInbox::Hval::ascii_html; - my $enc_utf8 = find_encoding('UTF-8'); # public functions: @@ -51,10 +48,9 @@ sub msg_reply { $s = '(no subject)' if (!defined $s) || ($s eq ''); my $f = $hdr->header('From'); $f = '' unless defined $f; - $s = PublicInbox::Hval->new_oneline($s); - my $mid = $hdr->header('Message-ID'); + my $mid = $hdr->header_raw('Message-ID'); $mid = PublicInbox::Hval->new_msgid($mid); - my $t = $s->as_html; + my $t = ascii_html($s); my $se_url = 'https://kernel.org/pub/software/scm/git/docs/git-send-email.html'; @@ -93,11 +89,11 @@ sub feed_entry { sub in_reply_to { my ($hdr) = @_; - my $irt = $hdr->header('In-Reply-To'); + my $irt = $hdr->header_raw('In-Reply-To'); return mid_clean($irt) if (defined $irt); - my $refs = $hdr->header('References'); + my $refs = $hdr->header_raw('References'); if ($refs && $refs =~ /<([^>]+)>\s*\z/s) { return $1; } @@ -116,24 +112,24 @@ sub index_entry { my $enc = enc_for($hdr->header("Content-Type")); my $subj = $hdr->header('Subject'); - my $mid_raw = mid_clean($hdr->header('Message-ID')); + my $mid_raw = mid_clean(mid_mime($mime)); my $id = anchor_for($mid_raw); my $seen = $state->{seen}; $seen->{$id} = "#$id"; # save the anchor for children, later my $mid = PublicInbox::Hval->new_msgid($mid_raw); - my $from = PublicInbox::Hval->new_oneline($hdr->header('From'))->raw; + my $from = $hdr->header('From'); my @from = Email::Address->parse($from); $from = $from[0]->name; - $from = PublicInbox::Hval->new_oneline($from)->as_html; - $subj = PublicInbox::Hval->new_oneline($subj)->as_html; my $root_anchor = $state->{root_anchor} || ''; my $path = $root_anchor ? '../../' : ''; my $href = $mid->as_href; my $irt = in_reply_to($hdr); my $parent_anchor = $seen->{anchor_for($irt)} if defined $irt; + $from = ascii_html($from); + $subj = ascii_html($subj); if ($srch) { my $t = $ctx->{flat} ? 'T' : 't'; $subj = "$subj"; @@ -302,41 +298,6 @@ sub add_filename_line { "$pad " . ascii_html($fn) . " $pad\n"; } -my $LINK_RE = qr!\b((?:ftp|https?|nntp):// - [\@:\w\.-]+/ - ?[\@\w\+\&\?\.\%\;/#=-]*)!x; - -sub linkify_1 { - my ($link_map, $s) = @_; - $s =~ s!$LINK_RE! - my $url = $1; - # salt this, as this could be exploited to show - # links in the HTML which don't show up in the raw mail. - my $key = sha1_hex($url . $SALT); - $link_map->{$key} = $url; - 'PI-LINK-'. $key; - !ge; - $s; -} - -sub linkify_2 { - my ($link_map, $s) = @_; - - # Added "PI-LINK-" prefix to avoid false-positives on git commits - $s =~ s!\bPI-LINK-([a-f0-9]{40})\b! - my $key = $1; - my $url = $link_map->{$key}; - if (defined $url) { - $url = ascii_html($url); - "$url"; - } else { - # false positive or somebody tried to mess with us - $key; - } - !ge; - $s; -} - sub flush_quote { my ($quot, $n, $part_nr, $full_pfx, $final, $do_anchor) = @_; @@ -346,11 +307,11 @@ sub flush_quote { if ($full_pfx) { if (!$final && scalar(@$quot) <= MAX_INLINE_QUOTED) { # show quote inline - my %l; - my $rv = join('', map { linkify_1(\%l, $_) } @$quot); + my $l = PublicInbox::Linkify->new; + my $rv = join('', map { $l->linkify_1($_) } @$quot); @$quot = (); $rv = ascii_html($rv); - return linkify_2(\%l, $rv); + return $l->linkify_2($rv); } # show a short snippet of quoted text and link to full version: @@ -375,13 +336,13 @@ sub flush_quote { } else { # show everything in the full version with anchor from # short version (see above) - my %l; - my $rv .= join('', map { linkify_1(\%l, $_) } @$quot); + my $l = PublicInbox::Linkify->new; + my $rv .= join('', map { $l->linkify_1($_) } @$quot); @$quot = (); $rv = ascii_html($rv); - return linkify_2(\%l, $rv) unless $do_anchor; + return $l->linkify_2($rv) unless $do_anchor; my $nr = ++$$n; - "" . linkify_2(\%l, $rv); + "" . $l->linkify_2($rv); } } @@ -420,10 +381,10 @@ sub add_text_body { } # regular line, OK - my %l; - $cur = linkify_1(\%l, $cur); + my $l = PublicInbox::Linkify->new; + $cur = $l->linkify_1($cur); $cur = ascii_html($cur); - $s .= linkify_2(\%l, $cur); + $s .= $l->linkify_2($cur); } else { push @quot, $cur; } @@ -445,12 +406,12 @@ sub headers_to_html_header { my $srch = $ctx->{srch} if $ctx; my $rv = ""; my @title; - my $mid = $hdr->header('Message-ID'); + my $mid = $hdr->header_raw('Message-ID'); $mid = PublicInbox::Hval->new_msgid($mid); foreach my $h (qw(From To Cc Subject Date)) { my $v = $hdr->header($h); defined($v) && ($v ne '') or next; - $v = PublicInbox::Hval->new_oneline($v); + $v = PublicInbox::Hval->new($v); if ($h eq 'From') { my @from = Email::Address->parse($v->raw); @@ -488,7 +449,7 @@ sub headers_to_html_header { sub thread_inline { my ($dst, $ctx, $hdr, $upfx) = @_; my $srch = $ctx->{srch}; - my $mid = mid_clean($hdr->header('Message-ID')); + my $mid = mid_clean($hdr->header_raw('Message-ID')); my $res = $srch->get_thread($mid); my $nr = $res->{total}; my $expand = "expand " . @@ -545,7 +506,7 @@ sub _parent_headers_nosrch { $rv .= "$html>\n"; } - my $refs = $hdr->header('References'); + my $refs = $hdr->header_raw('References'); if ($refs) { # avoid redundant URLs wasting bandwidth my %seen; @@ -586,7 +547,7 @@ sub mailto_arg_link { my $subj = $hdr->header('Subject') || ''; $subj = "Re: $subj" unless $subj =~ /\bRe:/i; - my $mid = $hdr->header('Message-ID'); + my $mid = $hdr->header_raw('Message-ID'); push @arg, "--in-reply-to='" . ascii_html($mid) . "'"; my $irt = uri_escape_utf8($mid); delete $cc{$to}; @@ -618,7 +579,7 @@ sub html_footer { my $p = $ctx->{parent_msg}; my $next = $ctx->{next_msg}; if ($p) { - $p = PublicInbox::Hval->new_oneline($p); + $p = PublicInbox::Hval->new_msgid($p); $p = $p->as_href; $irt = "parent "; } else { @@ -662,8 +623,7 @@ sub thread_html_head { my ($cb, $header, $state) = @_; $$cb = $$cb->([200, ['Content-Type'=> 'text/html; charset=UTF-8']]); - my $s = PublicInbox::Hval->new_oneline($header->header('Subject')); - $s = $s->as_html; + my $s = ascii_html($header->header('Subject')); $$cb->write("$s". qq{! . @@ -673,7 +633,7 @@ sub thread_html_head { sub pre_anchor_entry { my ($seen, $mime) = @_; - my $id = anchor_for($mime->header('Message-ID')); + my $id = anchor_for(mid_mime($mime)); $seen->{$id} = "#$id"; # save the anchor for children, later } @@ -726,7 +686,7 @@ sub __thread_entry { # lazy load the full message from mini_mime: $mime = eval { - my $path = mid2path(mid_clean($mime->header('Message-ID'))); + my $path = mid2path(mid_clean(mid_mime($mime))); Email::MIME->new($git->cat_file('HEAD:'.$path)); } or return; @@ -816,10 +776,9 @@ sub _inline_header { my $dot = $level == 0 ? '' : '` '; my $cur = $state->{cur}; - my $mid = mid_clean($hdr->header('Message-ID')); - my $f = $hdr->header('X-PI-From'); + my $mid = mid_clean($hdr->header_raw('Message-ID')); + my $f = ascii_html($hdr->header('X-PI-From')); my $d = _msg_date($hdr); - $f = PublicInbox::Hval->new_oneline($f)->as_html; my $pfx = ' ' . $d . ' ' . indent_for($level); my $attr = $f; $state->{first_level} ||= $level; @@ -869,7 +828,7 @@ sub inline_dump { return unless $node; if (my $mime = $node->message) { my $hdr = $mime->header_obj; - my $mid = mid_clean($hdr->header('Message-ID')); + my $mid = mid_clean($hdr->header_raw('Message-ID')); if ($mid eq $state->{parent_cmp}) { $state->{parent} = $mid; } @@ -917,7 +876,7 @@ sub add_topic { push @{$state->{order}}, [ $level, $subj ]; } - my $mid = mid_clean($x->header('Message-ID')); + my $mid = mid_clean($x->header_raw('Message-ID')); my $ts = $x->header('X-PI-TS'); my $exist = $state->{latest}->{$subj};