1f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov/* 2f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * Copyright (C) 2009 The Android Open Source Project 3f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * 4f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * Licensed under the Apache License, Version 2.0 (the "License"); 5f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * you may not use this file except in compliance with the License. 6f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * You may obtain a copy of the License at 7f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * 8f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * http://www.apache.org/licenses/LICENSE-2.0 9f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * 10f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * Unless required by applicable law or agreed to in writing, software 11f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * distributed under the License is distributed on an "AS IS" BASIS, 12f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * See the License for the specific language governing permissions and 14f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * limitations under the License. 15f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov */ 16f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov 17f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikovpackage com.android.providers.contacts; 18f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov 19f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikovimport android.content.ContentValues; 2003197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikovimport android.net.Uri; 215e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikovimport android.net.Uri.Builder; 226d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikovimport android.provider.ContactsContract.CommonDataKinds.Im; 23f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikovimport android.provider.ContactsContract.CommonDataKinds.Organization; 24eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikovimport android.provider.ContactsContract.CommonDataKinds.StructuredName; 25eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikovimport android.provider.ContactsContract.CommonDataKinds.StructuredPostal; 2603197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikovimport android.provider.ContactsContract.Contacts; 2754b97025256764a01f927792e64de8bf369e12f1Yorke Leeimport android.provider.ContactsContract.SearchSnippets; 28116d86ddd67330428f9128613b4886fc0ea66221Makoto Onukiimport android.test.MoreAsserts; 29f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikovimport android.test.suitebuilder.annotation.MediumTest; 30d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmannimport android.test.suitebuilder.annotation.Suppress; 31f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov 328ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Chengimport com.android.providers.contacts.testutil.DataUtil; 338ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Chengimport com.android.providers.contacts.testutil.RawContactUtil; 348ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng 3592ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikovimport java.text.Collator; 3692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikovimport java.util.Arrays; 3792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikovimport java.util.Locale; 3892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 39f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov/** 40f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * Unit tests for {@link SearchIndexManager}. 41f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * 42f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * Run the test like this: 43f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * <code> 44f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * adb shell am instrument -e class com.android.providers.contacts.SearchIndexManagerTest -w \ 45f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * com.android.providers.contacts.tests/android.test.InstrumentationTestRunner 46f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov * </code> 47f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov */ 48f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov@MediumTest 49f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikovpublic class SearchIndexManagerTest extends BaseContactsProvider2Test { 50f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov 51eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov public void testSearchIndexForStructuredName() { 528ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 53eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov long contactId = queryContactId(rawContactId); 548ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, "John", "Doe"); 55eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov ContentValues values = new ContentValues(); 56eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.DISPLAY_NAME, "Bob I. Parr"); 578ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 58eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.clear(); 59eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.PREFIX, "Mrs."); 60eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.GIVEN_NAME, "Helen"); 61eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.MIDDLE_NAME, "I."); 62eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.FAMILY_NAME, "Parr"); 63eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.SUFFIX, "PhD"); 64eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.PHONETIC_FAMILY_NAME, "par"); 65eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredName.PHONETIC_GIVEN_NAME, "helen"); 668ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 67eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 68eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov assertSearchIndex( 69bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov contactId, null, "John Doe Bob I Parr Helen I Parr PhD par helen parhelen", null); 7092ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 7192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 728a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki public void testSearchIndexForStructuredName_phoneticOnly() { 738a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki long rawContactId = RawContactUtil.createRawContact(mResolver); 748a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki long contactId = queryContactId(rawContactId); 758a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki DataUtil.insertStructuredName(mResolver, rawContactId, "John", "Doe"); 768a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki ContentValues values = new ContentValues(); 778a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.DISPLAY_NAME, "Bob I. Parr"); 788a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki DataUtil.insertStructuredName(mResolver, rawContactId, values); 798a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.clear(); 808a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.PREFIX, "Mrs."); 818a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.GIVEN_NAME, "Helen"); 828a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.MIDDLE_NAME, "I."); 838a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.FAMILY_NAME, "Parr"); 848a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.SUFFIX, "PhD"); 858a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.PHONETIC_FAMILY_NAME, "yamada"); 868a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki values.put(StructuredName.PHONETIC_GIVEN_NAME, "taro"); 878a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki DataUtil.insertStructuredName(mResolver, rawContactId, values); 888a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki 89598aec69d5b7e26dbe18b330ef65f137645c86d9Makoto Onuki assertSearchIndex(contactId, null, "yamada taro", null); 908a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki } 918a8ddc3d1ceee9872ace06326ebe999ba171f70bMakoto Onuki 9292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov public void testSearchIndexForChineseName() { 9392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Only run this test when Chinese collation is supported 9492ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov if (!Arrays.asList(Collator.getAvailableLocales()).contains(Locale.CHINA)) { 9592ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov return; 9692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 9792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 988ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 9992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov long contactId = queryContactId(rawContactId); 10092ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov ContentValues values = new ContentValues(); 10192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov values.put(StructuredName.DISPLAY_NAME, "\u695A\u8FAD"); // CHUCI 1028ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 10392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 10492ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov assertSearchIndex( 105bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov contactId, null, "\u695A\u8FAD \u695A\u8FAD CI \u8FAD CHUCI CC C", null); 10692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 10792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 10892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov public void testSearchByChineseName() { 10992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Only run this test when Chinese collation is supported 11092ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov if (!Arrays.asList(Collator.getAvailableLocales()).contains(Locale.CHINA)) { 11192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov return; 11292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 1130f4b7a9bfe4b2079a7c5bb22b4114b5672639b05Jay Shrauner ContactLocaleUtils.setLocale(Locale.SIMPLIFIED_CHINESE); 11492ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 1158ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 11692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov ContentValues values = new ContentValues(); 11792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov values.put(StructuredName.DISPLAY_NAME, "\u695A\u8FAD"); // CHUCI 1188ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 11992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 12054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\u695A\u8FAD"), SearchSnippets.SNIPPET, null); 12154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\u8FAD"), SearchSnippets.SNIPPET, null); 12254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("CI"), SearchSnippets.SNIPPET, null); 12354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("CHUCI"), SearchSnippets.SNIPPET, null); 12454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("CC"), SearchSnippets.SNIPPET, null); 12554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("C"), SearchSnippets.SNIPPET, null); 12692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 12792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 12892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov public void testSearchIndexForKoreanName() { 12992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Only run this test when Korean collation is supported 13092ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov if (!Arrays.asList(Collator.getAvailableLocales()).contains(Locale.KOREA)) { 13192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov return; 13292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 13392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 1348ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 13592ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov long contactId = queryContactId(rawContactId); 13692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov ContentValues values = new ContentValues(); 13792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov values.put(StructuredName.DISPLAY_NAME, "\uC774\uC0C1\uC77C"); // Lee Sang Il 1388ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 13992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 140bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov assertSearchIndex(contactId, null, 141bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov "\uC774\uC0C1\uC77C \uC0C1\uC77C \u1109\u110B \u110B\u1109\u110B", null); 14292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 14392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 14492ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov public void testSearchByKoreanName() { 14592ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Only run this test when Korean collation is supported 14692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov if (!Arrays.asList(Collator.getAvailableLocales()).contains(Locale.KOREA)) { 14792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov return; 14892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 14992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 1508ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 15192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov ContentValues values = new ContentValues(); 15292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov values.put(StructuredName.DISPLAY_NAME, "\uC774\uC0C1\uC77C"); // Lee Sang Il 1538ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 15492ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 15592ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Full name: Lee Sang Il 15654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\uC774\uC0C1\uC77C"), SearchSnippets.SNIPPET, null); 15792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 15892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Given name: Sang Il 15954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\uC0C1\uC77C"), SearchSnippets.SNIPPET, null); 16092ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 16192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Consonants of given name: SIOS IEUNG 16254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\u1109\u110B"), SearchSnippets.SNIPPET, null); 16392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 16492ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Consonants of full name: RIEUL SIOS IEUNG 16554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\u110B\u1109\u110B"), SearchSnippets.SNIPPET, null); 16692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 16792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 16892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov public void testSearchByKoreanNameWithTwoCharactersFamilyName() { 16992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Only run this test when Korean collation is supported. 17092ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov if (!Arrays.asList(Collator.getAvailableLocales()).contains(Locale.KOREA)) { 17192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov return; 17292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov } 17392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 1748ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 17592ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 17692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Sun Woo Young Nyeu 17792ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov ContentValues values = new ContentValues(); 17892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov values.put(StructuredName.DISPLAY_NAME, "\uC120\uC6B0\uC6A9\uB140"); 17992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 1808ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 18192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 18292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Full name: Sun Woo Young Nyeu 18392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov assertStoredValue( 18454b97025256764a01f927792e64de8bf369e12f1Yorke Lee buildSearchUri("\uC120\uC6B0\uC6A9\uB140"), SearchSnippets.SNIPPET, null); 18592ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 18692ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Given name: Young Nyeu 18754b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\uC6A9\uB140"), SearchSnippets.SNIPPET, null); 18892ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 18992ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Consonants of given name: IEUNG NIEUN 19054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("\u110B\u1102"), SearchSnippets.SNIPPET, null); 19192ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov 19292ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov // Consonants of full name: SIOS IEUNG IEUNG NIEUN 19392ddc5cdc4d89ee2c6e861ae7b3a3a913ffa0100Dmitri Plotnikov assertStoredValue( 19454b97025256764a01f927792e64de8bf369e12f1Yorke Lee buildSearchUri("\u1109\u110B\u110B\u1102"), SearchSnippets.SNIPPET, null); 195eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov } 196eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 197f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov public void testSearchIndexForOrganization() { 1988ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 199f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov long contactId = queryContactId(rawContactId); 200f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov ContentValues values = new ContentValues(); 201f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov values.put(Organization.COMPANY, "Acme Inc."); 202f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov values.put(Organization.TITLE, "Director"); 203f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov values.put(Organization.DEPARTMENT, "Phones and tablets"); 204f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov values.put(Organization.JOB_DESCRIPTION, "full text search"); 205f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov values.put(Organization.SYMBOL, "ACME"); 206f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov values.put(Organization.PHONETIC_NAME, "ack-me"); 207f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov values.put(Organization.OFFICE_LOCATION, "virtual"); 208f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov insertOrganization(rawContactId, values); 209f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov 210f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov assertSearchIndex(contactId, 211f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov "Director, Acme Inc. (ack-me) (ACME)/Phones and tablets/virtual/full text search", 212bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov null, null); 213f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov } 214f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov 215eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov public void testSearchIndexForPhoneNumber() { 2168ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 217eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov long contactId = queryContactId(rawContactId); 218eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov insertPhoneNumber(rawContactId, "800555GOOG"); 219eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov insertPhoneNumber(rawContactId, "8005551234"); 220eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 221bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov assertSearchIndex(contactId, null, null, "8005554664 +18005554664 8005551234 +18005551234"); 222eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov } 223eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 224eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov public void testSearchIndexForEmail() { 2258ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 226eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov long contactId = queryContactId(rawContactId); 227eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov insertEmail(rawContactId, "Bob Parr <incredible@android.com>"); 228eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov insertEmail(rawContactId, "bob_parr@android.com"); 229eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 230eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov assertSearchIndex(contactId, "Bob Parr <incredible@android.com>\nbob_parr@android.com", 231bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov null, null); 232eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov } 233eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 234eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov public void testSearchIndexForNickname() { 2358ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 236eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov long contactId = queryContactId(rawContactId); 237eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov insertNickname(rawContactId, "incredible"); 238eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 239bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov assertSearchIndex(contactId, "incredible", null, null); 240eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov } 241eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 242eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov public void testSearchIndexForStructuredPostal() { 2438ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 244eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov long contactId = queryContactId(rawContactId); 245eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov insertPostalAddress(rawContactId, "1600 Amphitheatre Pkwy\nMountain View, CA 94043"); 246eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov ContentValues values = new ContentValues(); 247eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredPostal.CITY, "London"); 248eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredPostal.STREET, "76 Buckingham Palace Road"); 249eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredPostal.POSTCODE, "SW1W 9TQ"); 250eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov values.put(StructuredPostal.COUNTRY, "United Kingdom"); 251eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov insertPostalAddress(rawContactId, values); 252eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 253eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov assertSearchIndex(contactId, "1600 Amphitheatre Pkwy Mountain View, CA 94043\n" 254bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov + "76 Buckingham Palace Road London SW1W 9TQ United Kingdom", null, null); 255eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov } 256eeeed5669d98897501bf2b18c88579c7effd0955Dmitri Plotnikov 2576d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov public void testSearchIndexForIm() { 2588ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 2596d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov long contactId = queryContactId(rawContactId); 2606d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov insertImHandle(rawContactId, Im.PROTOCOL_JABBER, null, "bp@android.com"); 2616d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov insertImHandle(rawContactId, Im.PROTOCOL_CUSTOM, "android_im", "android@android.com"); 2626d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov 263bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov assertSearchIndex( 264bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov contactId, "Jabber/bp@android.com\nandroid_im/android@android.com", null, null); 2656d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov } 2666d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov 2676d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov public void testSearchIndexForNote() { 2688ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 2696d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov long contactId = queryContactId(rawContactId); 2706d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov insertNote(rawContactId, "Please note: three notes or more make up a chord."); 2716d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov 272bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov assertSearchIndex( 273bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov contactId, "Please note: three notes or more make up a chord.", null, null); 2746d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov } 2756d9702cec82fd27a1c3093c64df9dcc22744899aDmitri Plotnikov 27603197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov public void testSnippetArgs() { 2778ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 27803197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov insertNote(rawContactId, "Please note: three notes or more make up a chord."); 27903197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov 28003197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov assertStoredValue( 28154b97025256764a01f927792e64de8bf369e12f1Yorke Lee buildSearchUri("thr", "[,],-,2", false), SearchSnippets.SNIPPET, 2826f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro "-note: [three]-"); 2835e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov } 2845e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov 2855e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov public void testEmptyFilter() { 2868ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng RawContactUtil.createRawContactWithName(mResolver, "John", "Doe"); 2875e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov assertEquals(0, getCount(buildSearchUri(""), null, null)); 2885e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov } 2895e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov 290f482a4e25759d2c144eb41a3de56a342bd473435Dmitri Plotnikov public void testSearchByName() { 2918ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng RawContactUtil.createRawContactWithName(mResolver, "John Jay", "Doe"); 292f482a4e25759d2c144eb41a3de56a342bd473435Dmitri Plotnikov 293f482a4e25759d2c144eb41a3de56a342bd473435Dmitri Plotnikov // We are supposed to find the contact, but return a null snippet 29454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("john"), SearchSnippets.SNIPPET, null); 29554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("jay"), SearchSnippets.SNIPPET, null); 29654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("doe"), SearchSnippets.SNIPPET, null); 297d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann } 298d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 299d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann public void testSearchByPrefixName() { 3008ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng RawContactUtil.createRawContactWithName(mResolver, "John Jay", "Doe"); 301d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 302d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // prefix searches 30354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("jo ja"), SearchSnippets.SNIPPET, null); 30454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("J D"), SearchSnippets.SNIPPET, null); 30554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Doe, John"), SearchSnippets.SNIPPET, null); 306d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann } 307d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 308d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann public void testGermanUmlautFullameCapitalizationSearch() { 3098ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng RawContactUtil.createRawContactWithName(mResolver, "Matthäus BJÖRN Bünyamin", "Reißer"); 310d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 311d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // make sure we can find those, independent of the capitalization 31254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("matthäus"), SearchSnippets.SNIPPET, null); 31354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Matthäus"), SearchSnippets.SNIPPET, null); 31454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("MATTHÄUS"), SearchSnippets.SNIPPET, null); 315d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 31654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("björn"), SearchSnippets.SNIPPET, null); 31754b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Björn"), SearchSnippets.SNIPPET, null); 31854b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("BJÖRN"), SearchSnippets.SNIPPET, null); 319d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 32054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("bünyamin"), SearchSnippets.SNIPPET, null); 32154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Bünyamin"), SearchSnippets.SNIPPET, null); 32254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("BUNYAMIN"), SearchSnippets.SNIPPET, null); 323d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 324d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // There is no capital version of ß. It is capitalized as double-S instead 32554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Reißer"), SearchSnippets.SNIPPET, null); 32654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Reisser"), SearchSnippets.SNIPPET, null); 32754b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("REISSER"), SearchSnippets.SNIPPET, null); 328d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann } 329d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 330d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann public void testHangulNameLeadConsonantAsYouTypeSearch() { 331d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann createRawContactWithDisplayName("홍길동"); 332d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // the korean name uses three compound characters. this test makes sure 333d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // that the name can be found by typing in only the lead consonant 33454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎ"), SearchSnippets.SNIPPET, null); 33554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㄱ"), SearchSnippets.SNIPPET, null); 33654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㄱㄷ"), SearchSnippets.SNIPPET, null); 337d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 338d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // same again, this time only for the first name 33954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱ"), SearchSnippets.SNIPPET, null); 34054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱㄷ"), SearchSnippets.SNIPPET, null); 341d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann } 342d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 343d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann public void testHangulNameFullAsYouTypeSearch() { 344d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann createRawContactWithDisplayName("홍길동"); 345d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 346d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // the korean name uses three compound characters. this test makes sure 347d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // that the name can be found by typing in the full nine letters. the search string 348d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // shows the name is being built "as you type" 34954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎ"), SearchSnippets.SNIPPET, null); 35054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("호"), SearchSnippets.SNIPPET, null); 35154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("홍"), SearchSnippets.SNIPPET, null); 35254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("홍ㄱ"), SearchSnippets.SNIPPET, null); 35354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("홍기"), SearchSnippets.SNIPPET, null); 35454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("홍길"), SearchSnippets.SNIPPET, null); 35554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("홍길ㄷ"), SearchSnippets.SNIPPET, null); 35654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("홍길도"), SearchSnippets.SNIPPET, null); 35754b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("홍길동"), SearchSnippets.SNIPPET, null); 358d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 359d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // same again, this time only for the first name 36054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱ"), SearchSnippets.SNIPPET, null); 36154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("기"), SearchSnippets.SNIPPET, null); 36254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("길"), SearchSnippets.SNIPPET, null); 36354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("길ㄷ"), SearchSnippets.SNIPPET, null); 36454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("길도"), SearchSnippets.SNIPPET, null); 36554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("길동"), SearchSnippets.SNIPPET, null); 366d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann } 367d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 368d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 369d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann /** Decomposed Hangul is not yet supported. This text is how we would test it */ 370d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann @Suppress 371d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann public void testHangulNameDecomposedSearch() { 372d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann createRawContactWithDisplayName("홍길동"); 373d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 374d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // the korean name uses three compound characters. this test makes sure 375d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // that the name can be found by typing each syllable as a single character. 376d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // This can be achieved using the Korean IM by pressing ㅎ, space, backspace, ㅗ and so on 37754b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎ"), SearchSnippets.SNIPPET, null); 37854b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗ"), SearchSnippets.SNIPPET, null); 37954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗㅇ"), SearchSnippets.SNIPPET, null); 38054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗㅇㄱ"), SearchSnippets.SNIPPET, null); 38154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗㅇㄱㅣ"), SearchSnippets.SNIPPET, null); 38254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗㅇㄱㅣㄹ"), SearchSnippets.SNIPPET, null); 38354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗㅇㄱㅣㄹㄷ"), SearchSnippets.SNIPPET, null); 38454b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗㅇㄱㅣㄹㄷㅗ"), SearchSnippets.SNIPPET, null); 38554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㅎㅗㅇㄱㅣㄹㄷㅗㅇ"), SearchSnippets.SNIPPET, null); 386d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 387d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // same again, this time only for the first name 38854b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱ"), SearchSnippets.SNIPPET, null); 38954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱㅣ"), SearchSnippets.SNIPPET, null); 39054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱㅣㄹ"), SearchSnippets.SNIPPET, null); 39154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱㅣㄹㄷ"), SearchSnippets.SNIPPET, null); 39254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱㅣㄹㄷㅗ"), SearchSnippets.SNIPPET, null); 39354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("ㄱㅣㄹㄷㅗㅇ"), SearchSnippets.SNIPPET, null); 394f482a4e25759d2c144eb41a3de56a342bd473435Dmitri Plotnikov } 395f482a4e25759d2c144eb41a3de56a342bd473435Dmitri Plotnikov 396f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki public void testNameWithHyphen() { 3978ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng RawContactUtil.createRawContactWithName(mResolver, "First", "Last-name"); 398f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki 39954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("First"), SearchSnippets.SNIPPET, null); 40054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last"), SearchSnippets.SNIPPET, null); 40154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last-"), SearchSnippets.SNIPPET, null); 40254b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last-n"), SearchSnippets.SNIPPET, null); 40354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last-name"), SearchSnippets.SNIPPET, null); 404f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki 405116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki // This will work too. 40654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Lastname"), SearchSnippets.SNIPPET, null); 407116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki 408116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki // This doesn't have to work, but it does with the current implementation. 40954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("name"), SearchSnippets.SNIPPET, null); 410f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki } 411f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki 412f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki /** Same as {@link #testNameWithHyphen} except the name has double hyphens. */ 413f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki public void testNameWithDoubleHyphens() { 4148ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng RawContactUtil.createRawContactWithName(mResolver, "First", "Last--name"); 415f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki 41654b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("First"), SearchSnippets.SNIPPET, null); 41754b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last"), SearchSnippets.SNIPPET, null); 41854b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last-"), SearchSnippets.SNIPPET, null); 41954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last-n"), SearchSnippets.SNIPPET, null); 42054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Last-name"), SearchSnippets.SNIPPET, null); 421116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki 422116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki // This will work too. 42354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("Lastname"), SearchSnippets.SNIPPET, null); 424f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki } 425f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki 426f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki public void testNameWithPunctuations() { 4278ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng RawContactUtil.createRawContactWithName(mResolver, "First", "O'Neill"); 428f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki 42954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("first"), SearchSnippets.SNIPPET, null); 43054b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("oneill"), SearchSnippets.SNIPPET, null); 43154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("o'neill"), SearchSnippets.SNIPPET, null); 432f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki } 433f5f038faf7f3ef460e1c11028d467954840e5f6fMakoto Onuki 4345e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov public void testSearchByEmailAddress() { 4358ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 4365e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov insertPhoneNumber(rawContactId, "1234567890"); 4375e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov insertEmail(rawContactId, "john@doe.com"); 4385e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov insertNote(rawContactId, "a hundred dollar note for doe@john.com and bob parr"); 4395e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov 440471923b8d71fb7f9632cad2de4f1583eeda61b62Yorke Lee assertStoredValue(buildSearchUri("john@d"), SearchSnippets.SNIPPET, 4415e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov "[john@doe.com]"); 4423d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov } 4433d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov 4443d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov public void testSearchByPhoneNumber() { 4458ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 4463d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov insertPhoneNumber(rawContactId, "330142685300"); 4473d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov insertPhoneNumber(rawContactId, "(800)GOOG-123"); 4483d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov insertEmail(rawContactId, "john@doe.com"); 4493d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov insertNote(rawContactId, "the eighteenth episode of Seinfeld, 650-253-0000"); 4503d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov 45154b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("33 (0)1 42 68 53 00"), SearchSnippets.SNIPPET, 4523d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov "[330142685300]"); 45354b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("8004664"), SearchSnippets.SNIPPET, 4543d0f0e0a1325ae306842b3ad1487d3507df0821dDmitri Plotnikov "[(800)GOOG-123]"); 45554b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("650-2"), SearchSnippets.SNIPPET, 456471923b8d71fb7f9632cad2de4f1583eeda61b62Yorke Lee "\u2026of Seinfeld, [650]-[253]-0000"); 457d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 458d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // for numbers outside of the real phone field, any order (and prefixing) is allowed 45954b97025256764a01f927792e64de8bf369e12f1Yorke Lee assertStoredValue(buildSearchUri("25 650"), SearchSnippets.SNIPPET, 460471923b8d71fb7f9632cad2de4f1583eeda61b62Yorke Lee "\u2026of Seinfeld, [650]-[253]-0000"); 4615e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov } 4625e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov 463fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki /** 464fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki * Test case for bug 5904515 465fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki */ 466fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki public void testSearchByPhoneNumber_diferSnippetting() { 4678ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 468fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki insertPhoneNumber(rawContactId, "505-123-4567"); 469fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki 470471923b8d71fb7f9632cad2de4f1583eeda61b62Yorke Lee // If snippeting is deferred, the returned snippet will not contain any markers. 471fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki assertStoredValue(buildSearchUri("505", "\u0001,\u0001,\u2026,5", true), 472471923b8d71fb7f9632cad2de4f1583eeda61b62Yorke Lee SearchSnippets.SNIPPET, "505-123-4567"); 473fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki } 474fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki 475fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki /** 476471923b8d71fb7f9632cad2de4f1583eeda61b62Yorke Lee * Equivalent to {@link #testSearchByPhoneNumber_diferSnippetting} for email addresses 477fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki */ 478fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki public void testSearchByEmail_diferSnippetting() { 4798ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 480fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki insertEmail(rawContactId, "john@doe.com"); 481fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki 482fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki assertStoredValue(buildSearchUri("john", "\u0001,\u0001,\u2026,5", true), 483471923b8d71fb7f9632cad2de4f1583eeda61b62Yorke Lee SearchSnippets.SNIPPET, "john@doe.com"); 484fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki } 485fba89ea92f519d77ec1d762724ed11bf4ebb7d20Makoto Onuki 486116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki public void testSplitIntoFtsTokens() { 487116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki checkSplitIntoFtsTokens("a", "a"); 488116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki checkSplitIntoFtsTokens("a_b c%d-e'f", "a_b", "c", "d", "e", "f"); 489116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki checkSplitIntoFtsTokens(" ", new String[0]); 490116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki // There's are all "control" characters, but treated as "letters". 491116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki // (See http://en.wikipedia.org/wiki/C1_Controls_and_Latin-1_Supplement for what they are) 492116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki checkSplitIntoFtsTokens("\u0080 \u0081 \u0082", "\u0080", "\u0081", "\u0082"); 493116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki 494116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki // FFF0 is also a token. 495116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki checkSplitIntoFtsTokens(" \ufff0 ", "\ufff0"); 496116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki } 497116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki 498116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki private void checkSplitIntoFtsTokens(String input, String... expectedTokens) { 499116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki MoreAsserts.assertEquals(expectedTokens, 500116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki SearchIndexManager.splitIntoFtsTokens(input).toArray(new String[0])); 501116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki } 502116d86ddd67330428f9128613b4886fc0ea66221Makoto Onuki 5035e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov private Uri buildSearchUri(String filter) { 5046f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro return buildSearchUri(filter, false); 50503197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov } 50603197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov 5076f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro private Uri buildSearchUri(String filter, boolean deferredSnippeting) { 5086f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro return buildSearchUri(filter, null, deferredSnippeting); 5096f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro } 5106f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro 5116f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro private Uri buildSearchUri(String filter, String args, boolean deferredSnippeting) { 5125e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov Builder builder = Contacts.CONTENT_FILTER_URI.buildUpon().appendPath(filter); 5135e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov if (args != null) { 51454b97025256764a01f927792e64de8bf369e12f1Yorke Lee builder.appendQueryParameter(SearchSnippets.SNIPPET_ARGS_PARAM_KEY, args); 5155e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov } 5166f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro if (deferredSnippeting) { 51754b97025256764a01f927792e64de8bf369e12f1Yorke Lee builder.appendQueryParameter(SearchSnippets.DEFERRED_SNIPPETING_KEY, "1"); 5186f983fd835f0cdd5ac7931ccd49d44e9ea4c87c0Dave Santoro } 5195e70c0772ef2b975c95787112ac0f15047a4ff0cDmitri Plotnikov return builder.build(); 52003197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov } 52103197a00e17386aa9b1971bde3cda034bc17e0c3Dmitri Plotnikov 522d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann private void createRawContactWithDisplayName(String name) { 5238ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng long rawContactId = RawContactUtil.createRawContact(mResolver); 524d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann ContentValues values = new ContentValues(); 525d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann values.put(StructuredName.DISPLAY_NAME, name); 5268ed367fdc0b086d54c489f68d555e2f0a4035f63Chiao Cheng DataUtil.insertStructuredName(mResolver, rawContactId, values); 527d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann } 528d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann 529d1746e09bc7739f3d1449cececc66d5045ada498Daniel Lehmann // TODO: expectedName must be tested. Many tests in here are quite useless at the moment 530bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov private void assertSearchIndex( 531bee8da0696b04b5bbbdf71a05d20e3214e1b5100Dmitri Plotnikov long contactId, String expectedContent, String expectedName, String expectedTokens) { 532f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov ContactsDatabaseHelper dbHelper = (ContactsDatabaseHelper) getContactsProvider() 533f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov .getDatabaseHelper(); 534383d8aa53aa2f74a4b71642de7df2e4b9f2242c8Dmitri Plotnikov assertEquals(expectedContent, dbHelper.querySearchIndexContentForTest(contactId)); 535383d8aa53aa2f74a4b71642de7df2e4b9f2242c8Dmitri Plotnikov assertEquals(expectedTokens, dbHelper.querySearchIndexTokensForTest(contactId)); 536f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov } 537f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov} 538f262d56495ac4ea30d31bd050efb116bd4bb4235Dmitri Plotnikov 539