Bug 1293445 - Part 2: Make tag queries case insensitive and associated tests. r?mak draft
authorMilindL <i.milind.luthra@gmail.com>
Fri, 17 Nov 2017 23:29:03 +0530
changeset 700542 24008650188fb354a08a2df22d2f2382aa84f479
parent 700539 df80df559ca8bfee012d4c3a01dbd8e7021ca939
child 700543 c8faa268927996cb15738db00cecc5ac915b4d26
push id89887
push userbmo:i.milind.luthra@gmail.com
push dateMon, 20 Nov 2017 10:25:38 +0000
reviewersmak
bugs1293445
milestone58.0a1
Bug 1293445 - Part 2: Make tag queries case insensitive and associated tests. r?mak Additional tests added include testing for queries where tags have special characters. MozReview-Commit-ID: GDiAe1c7q4K
toolkit/components/places/nsNavHistory.cpp
toolkit/components/places/tests/queries/test_tags.js
--- a/toolkit/components/places/nsNavHistory.cpp
+++ b/toolkit/components/places/nsNavHistory.cpp
@@ -3264,24 +3264,24 @@ nsNavHistory::QueryToSelectClause(nsNavH
       clause.Str("NOT");
     clause.Str(
       "IN "
         "(SELECT bms.fk "
          "FROM moz_bookmarks bms "
          "JOIN moz_bookmarks tags ON bms.parent = tags.id "
          "WHERE tags.parent =").
            Param(":tags_folder").
-           Str("AND tags.title IN (");
+           Str("AND lower(tags.title) IN ( lower(");
     for (uint32_t i = 0; i < tags.Length(); ++i) {
       nsPrintfCString param(":tag%d_", i);
       clause.Param(param.get());
       if (i < tags.Length() - 1)
-        clause.Str(",");
+        clause.Str("), lower(");
     }
-    clause.Str(")");
+    clause.Str("))");
     if (!aQuery->TagsAreNot())
       clause.Str("GROUP BY bms.fk HAVING count(*) >=").Param(":tag_count");
     clause.Str(")");
   }
 
   // transitions
   const nsTArray<uint32_t>& transitions = aQuery->Transitions();
   for (uint32_t i = 0; i < transitions.Length(); ++i) {
--- a/toolkit/components/places/tests/queries/test_tags.js
+++ b/toolkit/components/places/tests/queries/test_tags.js
@@ -512,16 +512,80 @@ add_task(async function ORed_queries() {
   for (let [pURI, tags] of Object.entries(urisAndTags)) {
     let nsiuri = uri(pURI);
     if (tags)
       PlacesUtils.tagging.untagURI(nsiuri, tags);
   }
   await task_cleanDatabase();
 });
 
+add_task(async function tag_casing_uri() {
+  do_print("Querying history on associated tags should return " +
+           "correct results irrespective of casing of tags.");
+  await task_doWithVisit(["fOo", "bAr"], function(aURI) {
+    let [query, opts] = makeQuery(["Foo"]);
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+    [query, opts] = makeQuery(["Foo", "Bar"]);
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+    [query, opts] = makeQuery(["Foo"], true);
+    executeAndCheckQueryResults(query, opts, []);
+    [query, opts] = makeQuery(["Bogus"], true);
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+  });
+});
+
+add_task(async function tag_casing_bookmark() {
+  do_print("Querying bookmarks on associated tags should return " +
+           "correct results irrespective of casing of tags.");
+  await task_doWithBookmark(["fOo", "bAr"], function(aURI) {
+    let [query, opts] = makeQuery(["Foo"]);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+    [query, opts] = makeQuery(["Foo", "Bar"]);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    [query, opts] = makeQuery(["Foo"], true);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    executeAndCheckQueryResults(query, opts, []);
+    [query, opts] = makeQuery(["Bogus"], true);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+  });
+});
+
+add_task(async function tag_special_char_uri() {
+  do_print("Querying history on associated tags should return " +
+           "correct results even if tags contain special characters.");
+  await task_doWithVisit(["Space ☺️ Between"], function(aURI) {
+    let [query, opts] = makeQuery(["Space ☺️ Between"]);
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+    [query, opts] = makeQuery(["Space ☺️ Between"], true);
+    executeAndCheckQueryResults(query, opts, []);
+    [query, opts] = makeQuery(["Bogus"], true);
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+  });
+});
+
+add_task(async function tag_special_char_bookmark() {
+  do_print("Querying bookmarks on associated tags should return " +
+           "correct results even if tags contain special characters.");
+  await task_doWithBookmark(["Space ☺️ Between"], function(aURI) {
+    let [query, opts] = makeQuery(["Space ☺️ Between"]);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+    [query, opts] = makeQuery(["Space ☺️ Between"], true);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    executeAndCheckQueryResults(query, opts, []);
+    [query, opts] = makeQuery(["Bogus"], true);
+    opts.queryType = opts.QUERY_TYPE_BOOKMARKS;
+    executeAndCheckQueryResults(query, opts, [aURI.spec]);
+  });
+});
+
 // The tag keys in query URIs, i.e., "place:tag=foo&!tags=1"
 //                                          ---     -----
 const QUERY_KEY_TAG      = "tag";
 const QUERY_KEY_NOT_TAGS = "!tags";
 
 const TEST_URI = uri("http://example.com/");
 
 /**