diff options
Diffstat (limited to 'lib/PublicInbox/Over.pm')
-rw-r--r-- | lib/PublicInbox/Over.pm | 57 |
1 files changed, 48 insertions, 9 deletions
diff --git a/lib/PublicInbox/Over.pm b/lib/PublicInbox/Over.pm index 786f9d92..3b7d49f5 100644 --- a/lib/PublicInbox/Over.pm +++ b/lib/PublicInbox/Over.pm @@ -12,6 +12,7 @@ use DBD::SQLite; use PublicInbox::Smsg; use Compress::Zlib qw(uncompress); use constant DEFAULT_LIMIT => 1000; +use List::Util (); # for max sub dbh_new { my ($self, $rw) = @_; @@ -81,7 +82,13 @@ sub dbh_close { } } -sub dbh ($) { $_[0]->{dbh} //= $_[0]->dbh_new } # dbh_new may be subclassed +sub dbh ($) { + my ($self) = @_; + $self->{dbh} // do { + my $dbh = $self->dbh_new; # dbh_new may be subclassed + $self->{dbh} = $dbh; + } +} sub load_from_row ($;$) { my ($smsg, $cull) = @_; @@ -193,15 +200,22 @@ ORDER BY $sort_col DESC # TODO separate strict and loose matches here once --reindex # is fixed to preserve `tid' properly push @$msgs, @$loose; + + # we wanted to retrieve the latest loose messages; but preserve + # chronological ordering for threading /$INBOX/$MSGID/[tT]/ + $sort_col eq 'ds' and + @$msgs = sort { $a->{ds} <=> $b->{ds} } @$msgs; } ($nr, $msgs); } # strict `tid' matches, only, for thread-expanded mbox.gz search results -# and future CLI interface +# and lei # returns true if we have IDs, undef if not sub expand_thread { my ($self, $ctx) = @_; + # previous maxuid for LeiSavedSearch is our min: + my $lss_min = $ctx->{min} // 0; my $dbh = dbh($self); do { defined(my $num = $ctx->{ids}->[0]) or return; @@ -214,7 +228,7 @@ SELECT num FROM over WHERE tid = ? AND num > ? ORDER BY num ASC LIMIT 1000 my $xids = $dbh->selectcol_arrayref($sql, undef, $tid, - $ctx->{prev} // 0); + List::Util::max($ctx->{prev} // 0, $lss_min)); if (scalar(@$xids)) { $ctx->{prev} = $xids->[-1]; $ctx->{xids} = $xids; @@ -253,9 +267,12 @@ SELECT ts,ds,ddd FROM over WHERE $s sub get_art { my ($self, $num) = @_; # caching $sth ourselves is faster than prepare_cached - my $sth = $self->{-get_art} //= dbh($self)->prepare(<<''); + my $sth = $self->{-get_art} // do { + my $sth = dbh($self)->prepare(<<''); SELECT num,tid,ds,ts,ddd FROM over WHERE num = ? LIMIT 1 + $self->{-get_art} = $sth; + }; $sth->execute($num); my $smsg = $sth->fetchrow_hashref; $smsg ? load_from_row($smsg) : undef; @@ -273,13 +290,35 @@ SELECT ibx_id,xnum,oidbin FROM xref3 WHERE docid = ? ORDER BY ibx_id,xnum ASC my $eidx_key_sth = $dbh->prepare_cached(<<'', undef, 1); SELECT eidx_key FROM inboxes WHERE ibx_id = ? - [ map { - my $r = $_; + for my $r (@$rows) { $eidx_key_sth->execute($r->[0]); my $eidx_key = $eidx_key_sth->fetchrow_array; $eidx_key //= "missing://ibx_id=$r->[0]"; - "$eidx_key:$r->[1]:".unpack('H*', $r->[2]); - } @$rows ]; + $r = "$eidx_key:$r->[1]:".unpack('H*', $r->[2]); + } + $rows; +} + +sub mid2tid { + my ($self, $mid) = @_; + my $dbh = dbh($self); + + my $sth = $dbh->prepare_cached(<<'', undef, 1); +SELECT id FROM msgid WHERE mid = ? LIMIT 1 + + $sth->execute($mid); + my $id = $sth->fetchrow_array or return; + $sth = $dbh->prepare_cached(<<'', undef, 1); +SELECT num FROM id2num WHERE id = ? AND num > ? +ORDER BY num ASC LIMIT 1 + + $sth->execute($id, 0); + my $num = $sth->fetchrow_array or return; + $sth = $dbh->prepare(<<''); +SELECT tid FROM over WHERE num = ? LIMIT 1 + + $sth->execute($num); + $sth->fetchrow_array; } sub next_by_mid { @@ -288,7 +327,7 @@ sub next_by_mid { unless (defined $$id) { my $sth = $dbh->prepare_cached(<<'', undef, 1); - SELECT id FROM msgid WHERE mid = ? LIMIT 1 +SELECT id FROM msgid WHERE mid = ? LIMIT 1 $sth->execute($mid); $$id = $sth->fetchrow_array; |