]> Sergey Matveev's repositories - public-inbox.git/blobdiff - lib/PublicInbox/SearchIdx.pm
search: make xap_terms easier-to-use and use it more
[public-inbox.git] / lib / PublicInbox / SearchIdx.pm
index 7d46489c00202d19cde1d203e18c5c34f26559b6..65764cc81a81b167a7e5a59561d4e1084401531e 100644 (file)
@@ -35,7 +35,7 @@ use constant DEBUG => !!$ENV{DEBUG};
 my $xapianlevels = qr/\A(?:full|medium)\z/;
 my $hex = '[a-f0-9]';
 my $OID = $hex .'{40,}';
-my @VMD_MAP = (kw => 'K', label => 'L');
+my @VMD_MAP = (kw => 'K', L => 'L');
 our $INDEXLEVELS = qr/\A(?:full|medium|basic)\z/;
 
 sub new {
@@ -435,8 +435,9 @@ sub add_xapian ($$$$) {
        if (my $old = $merge_vmd ? _get_doc($self, $smsg->{num}) : undef) {
                my @x = @VMD_MAP;
                while (my ($field, $pfx) = splice(@x, 0, 2)) {
-                       my $vals = xap_terms($pfx, $old);
-                       $doc->add_boolean_term($pfx.$_) for keys %$vals;
+                       for my $term (xap_terms($pfx, $old)) {
+                               $doc->add_boolean_term($pfx.$term);
+                       }
                }
        }
        $self->{xdb}->replace_document($smsg->{num}, $doc);
@@ -567,16 +568,39 @@ sub set_vmd {
        $self->{xdb}->replace_document($docid, $doc);
 }
 
+sub apply_vmd_mod ($$) {
+       my ($doc, $vmd_mod) = @_;
+       my $updated = 0;
+       my @x = @VMD_MAP;
+       while (my ($field, $pfx) = splice(@x, 0, 2)) {
+               # field: "L" or "kw"
+               for my $val (@{$vmd_mod->{"-$field"} // []}) {
+                       eval {
+                               $doc->remove_term($pfx . $val);
+                               ++$updated;
+                       };
+               }
+               for my $val (@{$vmd_mod->{"+$field"} // []}) {
+                       $doc->add_boolean_term($pfx . $val);
+                       ++$updated;
+               }
+       }
+       $updated;
+}
+
 sub add_vmd {
        my ($self, $docid, $vmd) = @_;
        begin_txn_lazy($self);
        my $doc = _get_doc($self, $docid) or return;
        my @x = @VMD_MAP;
+       my $updated = 0;
        while (my ($field, $pfx) = splice(@x, 0, 2)) {
                my $add = $vmd->{$field} // next;
                $doc->add_boolean_term($pfx . $_) for @$add;
+               $updated += scalar(@$add);
        }
-       $self->{xdb}->replace_document($docid, $doc);
+       $updated += apply_vmd_mod($doc, $vmd);
+       $self->{xdb}->replace_document($docid, $doc) if $updated;
 }
 
 sub remove_vmd {
@@ -601,21 +625,7 @@ sub update_vmd {
        my ($self, $docid, $vmd_mod) = @_;
        begin_txn_lazy($self);
        my $doc = _get_doc($self, $docid) or return;
-       my $updated = 0;
-       my @x = @VMD_MAP;
-       while (my ($field, $pfx) = splice(@x, 0, 2)) {
-               # field: "label" or "kw"
-               for my $val (@{$vmd_mod->{"-$field"} // []}) {
-                       eval {
-                               $doc->remove_term($pfx . $val);
-                               ++$updated;
-                       };
-               }
-               for my $val (@{$vmd_mod->{"+$field"} // []}) {
-                       $doc->add_boolean_term($pfx . $val);
-                       ++$updated;
-               }
-       }
+       my $updated = apply_vmd_mod($doc, $vmd_mod);
        $self->{xdb}->replace_document($docid, $doc) if $updated;
        $updated;
 }