Match names better for PotentialMatches
authorAlexander Larsson <alexl@redhat.com>
Mon, 23 Jan 2012 15:30:58 +0000 (16:30 +0100)
committerAlexander Larsson <alexl@redhat.com>
Mon, 23 Jan 2012 15:34:56 +0000 (16:34 +0100)
We match alias as well as full name, to e.g. match an EDS contact (full name)
with an IM contact (alias).

Also, we make exact name matches bring the priority to HIGH alone, which
is needed in the IM case since the alias is the only piece of data
we have to match on.

https://bugzilla.gnome.org/show_bug.cgi?id=668499

folks/potential-match.vala

index 0f2c6dd..0760d8a 100644 (file)
@@ -167,6 +167,7 @@ public class Folks.PotentialMatch : Object
   private void _name_similarity ()
     {
       double similarity = 0.0;
+      bool exact_match = false;
 
       if (this._look_alike (this._individual_a.nickname,
               this._individual_b.nickname))
@@ -174,8 +175,18 @@ public class Folks.PotentialMatch : Object
           similarity += 0.20;
         }
 
-      if (this._look_alike (this._individual_a.full_name,
-              this._individual_b.full_name))
+      if (this._look_alike_or_identical (this._individual_a.full_name,
+              this._individual_b.full_name,
+              out exact_match) ||
+          this._look_alike_or_identical (this._individual_a.alias,
+             this._individual_b.full_name,
+             out exact_match) ||
+          this._look_alike_or_identical (this._individual_a.full_name,
+              this._individual_b.alias,
+              out exact_match) ||
+          this._look_alike_or_identical (this._individual_a.alias,
+              this._individual_b.alias,
+              out exact_match))
         {
           similarity += 0.70;
         }
@@ -217,7 +228,16 @@ public class Folks.PotentialMatch : Object
       debug ("[name_similarity] Got %f\n", similarity);
 
       if (similarity >= this._DIST_THRESHOLD)
-        this._result = this._inc_match_level (this._result, 2);
+        {
+          int inc = 2;
+         /* We need exact matches to go to at least HIGH, or otherwise its
+            not possible to get a HIGH match for e.g. a facebook telepathy
+            persona, where alias is the only piece of information
+            available */
+          if (exact_match)
+            inc += 1;
+          this._result = this._inc_match_level (this._result, inc);
+        }
     }
 
   /**
@@ -392,9 +412,27 @@ public class Folks.PotentialMatch : Object
       return ret;
     }
 
+  private bool _look_alike_or_identical (string? a, string? b, out bool exact)
+    {
+      exact = false;
+      if (a == null || a == "" || b == null || b == "")
+        {
+          return false;
+        }
+
+      if (a == b)
+        {
+          exact = true;
+          return true;
+        }
+
+      // a and b look alike if their Jaro distance is over the threshold.
+      return (this.jaro_dist ((!) a, (!) b) >= this._DIST_THRESHOLD);
+    }
+
   private bool _look_alike (string? a, string? b)
     {
-      if (a == null || b == null)
+      if (a == null || a == "" || b == null || b == "")
         {
           return false;
         }