blob: d9007fc12e66a1bc6eb9d6d4a9291e1575824065 [file] [log] [blame]
/*
* Copyright (C) 2009 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.providers.contacts;
import android.provider.ContactsContract.FullNameStyle;
import android.provider.ContactsContract.PhoneticNameStyle;
import android.test.suitebuilder.annotation.SmallTest;
import com.android.providers.contacts.NameSplitter.Name;
import junit.framework.TestCase;
import java.util.Locale;
/**
* Tests for {@link NameSplitter}.
*
* Run the test like this:
* <code>
* adb shell am instrument -e class com.android.providers.contacts.NameSplitterTest -w \
* com.android.providers.contacts.tests/android.test.InstrumentationTestRunner
* </code>
*/
@SmallTest
public class NameSplitterTest extends TestCase {
private NameSplitter mNameSplitter;
@Override
protected void setUp() throws Exception {
super.setUp();
createNameSplitter(Locale.US);
}
private void createNameSplitter(Locale locale) {
mNameSplitter = new NameSplitter("Mr, Ms, Mrs", "d', st, st., von", "Jr., M.D., MD, D.D.S.",
"&, AND", locale);
}
public void testNull() {
assertSplitName(null, null, null, null, null, null);
assertJoinedName(null, null, null, null, null, null);
}
public void testEmpty() {
assertSplitName("", null, null, null, null, null);
assertJoinedName(null, null, null, null, null, null);
}
public void testSpaces() {
assertSplitName(" ", null, null, null, null, null);
assertJoinedName(null, null, null, null, null, null);
}
public void testFamilyName() {
assertSplitName("Smith", null, "Smith", null, null, null);
assertJoinedName("Smith", null, "Smith", null, null, null);
}
public void testIgnoreSuffix() {
assertSplitName("Ms MD", "Ms", null, null, "MD", null);
assertJoinedName("Ms MD", "Ms", null, null, "MD", null);
}
public void testGivenFamilyName() {
assertSplitName("John Smith", null, "John", null, "Smith", null);
assertJoinedName("John Smith", null, "John", null, "Smith", null);
}
public void testGivenMiddleFamilyName() {
assertSplitName("John Edward Smith", null, "John", "Edward", "Smith", null);
assertJoinedName("John Edward Smith", null, "John", "Edward", "Smith", null);
}
public void testThreeNamesAndFamilyName() {
assertSplitName("John Edward Kevin Smith", null, "John Edward", "Kevin", "Smith", null);
assertJoinedName("John Edward Kevin Smith", null, "John Edward", "Kevin", "Smith", null);
}
public void testPrefixFivenFamilyName() {
assertSplitName("Mr. John Smith", "Mr.", "John", null, "Smith", null);
assertJoinedName("Mr John Smith", "Mr", "John", null, "Smith", null);
assertSplitName("Mr.John Smith", "Mr.", "John", null, "Smith", null);
assertJoinedName("Mr John Smith", "Mr", "John", null, "Smith", null);
}
public void testFivenFamilyNameSuffix() {
assertSplitName("John Smith Jr", null, "John", null, "Smith", "Jr");
assertJoinedName("John Smith, Jr.", null, "John", null, "Smith", "Jr");
}
public void testGivenFamilyNameSuffixWithDot() {
assertSplitName("John Smith M.D.", null, "John", null, "Smith", "M.D.");
assertJoinedName("John Smith, M.D.", null, "John", null, "Smith", "M.D.");
assertSplitName("John Smith D D S", null, "John", null, "Smith", "D D S");
assertJoinedName("John Smith, D D S", null, "John", null, "Smith", "D D S");
}
public void testGivenSuffixFamilyName() {
assertSplitName("John von Smith", null, "John", null, "von Smith", null);
assertJoinedName("John von Smith", null, "John", null, "von Smith", null);
}
public void testGivenSuffixFamilyNameWithDot() {
assertSplitName("John St.Smith", null, "John", null, "St. Smith", null);
assertJoinedName("John St. Smith", null, "John", null, "St. Smith", null);
}
public void testPrefixGivenMiddleFamily() {
assertSplitName("Mr. John Kevin Smith", "Mr.", "John", "Kevin", "Smith", null);
assertJoinedName("Mr John Kevin Smith", "Mr", "John", "Kevin", "Smith", null);
assertSplitName("Mr.John Kevin Smith", "Mr.", "John", "Kevin", "Smith", null);
assertJoinedName("Mr. John Kevin Smith", "Mr.", "John", "Kevin", "Smith", null);
}
public void testPrefixGivenMiddleFamilySuffix() {
assertSplitName("Mr. John Kevin Smith Jr.", "Mr.", "John", "Kevin", "Smith", "Jr.");
assertJoinedName("Mr John Kevin Smith, Jr.", "Mr", "John", "Kevin", "Smith", "Jr");
}
public void testPrefixGivenMiddlePrefixFamilySuffixWrongCapitalization() {
assertSplitName("MR. john keVin VON SmiTh JR.", "MR.", "john", "keVin", "VON SmiTh", "JR.");
assertJoinedName("MR john keVin VON SmiTh, JR.", "MR", "john", "keVin", "VON SmiTh", "JR");
}
public void testPrefixFamilySuffix() {
assertSplitName("von Smith Jr.", null, null, null, "von Smith", "Jr.");
assertJoinedName("von Smith, Jr.", null, null, null, "von Smith", "Jr");
}
public void testFamilyNameGiven() {
assertSplitName("Smith, John", null, "John", null, "Smith", null);
assertSplitName("Smith , John", null, "John", null, "Smith", null);
assertSplitName("Smith, John Kimble", null, "John", "Kimble", "Smith", null);
assertSplitName("Smith, John K.", null, "John", "K.", "Smith", null);
assertSplitName("Smith, John, Jr.", null, "John", null, "Smith", "Jr.");
assertSplitName("Smith, John Kimble, Jr.", null, "John", "Kimble", "Smith", "Jr.");
assertSplitName("von Braun, John, Jr.", null, "John", null, "von Braun", "Jr.");
assertSplitName("von Braun, John Kimble, Jr.", null, "John", "Kimble", "von Braun", "Jr.");
}
public void testTwoNamesAndFamilyNameWithAmpersand() {
assertSplitName("John & Edward Smith", null, "John & Edward", null, "Smith", null);
assertJoinedName("John & Edward Smith", null, "John & Edward", null, "Smith", null);
assertSplitName("John and Edward Smith", null, "John and Edward", null, "Smith", null);
assertSplitName("Smith, John and Edward", null, "John and Edward", null, "Smith", null);
assertJoinedName("John and Edward Smith", null, "John and Edward", null, "Smith", null);
}
public void testWithMiddleInitialAndNoDot() {
assertSplitName("John E. Smith", null, "John", "E.", "Smith", null);
assertJoinedName("John E Smith", null, "John", "E", "Smith", null);
}
public void testWithLongGivenNameAndDot() {
assertSplitName("John Ed. K. Smith", null, "John Ed.", "K.", "Smith", null);
assertJoinedName("John Ed. K Smith", null, "John Ed.", "K", "Smith", null);
}
public void testGuessFullNameStyleEmpty() {
assertFullNameStyle(FullNameStyle.UNDEFINED, null);
assertFullNameStyle(FullNameStyle.UNDEFINED, "");
}
public void testGuessFullNameStyleWestern() {
// Latin letters
assertFullNameStyle(FullNameStyle.WESTERN, "John Doe");
// Starts with a Latin letter, but contains Japanese letters
assertFullNameStyle(FullNameStyle.JAPANESE, "A\u3080\u308D\u306A\u307F\u3048");
// Starts with an Extended Latin letter "Latin Capital Ligature OE"
assertFullNameStyle(FullNameStyle.WESTERN, "\u0152uvre");
// Non-letters don't make a difference. This one starts with a vertical line
assertFullNameStyle(FullNameStyle.WESTERN, "\uFF5C.?+Smith");
}
public void testGuessFullNameStyleJapanese() {
createNameSplitter(Locale.JAPAN);
// Hiragana: always Japanese
assertFullNameStyle(FullNameStyle.JAPANESE, "\u3042\u3080\u308D\u306A\u307F\u3048");
// Katakana: always Japanese
assertFullNameStyle(FullNameStyle.JAPANESE, "\u30A2\u30E0\u30ED \u30CA\u30DF\u30A8");
// Half-width Katakana: always Japanese
assertFullNameStyle(FullNameStyle.JAPANESE, "\uFF71\uFF91\uFF9B \uFF85\uFF90\uFF74");
// Kanji: we cannot tell if this is Japanese, Chinese or Korean, but we are
// in Locale.JAPAN, so assume Japanese
assertFullNameStyle(FullNameStyle.JAPANESE, "\u5B89\u5BA4\u5948\u7F8E\u6075");
// TODO: mix
// Accompanied by a phonetic name in Hiragana, we can safely assume that the
// name is Japanese
assertFullNameStyle(FullNameStyle.JAPANESE, "\u5B89\u5BA4\u5948\u7F8E\u6075",
"\u3042\u3080\u308D", null, "\u306A\u307F\u3048");
// Starts with a latin letter - not Western
assertFullNameStyle(FullNameStyle.JAPANESE, "A\u3080\u308D\u306A\u307F\u3048");
}
public void testGuessFullNameStyleChinese() {
createNameSplitter(Locale.CHINA);
// Hanzi: we cannot tell if this is Chinese, Japanese or Korean,
// but we are in Locale.CHINA, so assume this is Chinese
assertFullNameStyle(FullNameStyle.CHINESE, "\u675C\u9D51");
// Accompanied by a phonetic name in Pinyin, we can safely assume that the
// name is Chinese
assertFullNameStyle(FullNameStyle.CHINESE, "\u675C\u9D51",
"du4", null, "juan1");
// Non-letters don't make a difference. This one starts with a vertical line
assertFullNameStyle(FullNameStyle.CHINESE, "\uFF5C--(\u675C\u9D51)");
}
public void testGuessPhoneticNameStyle() {
// Hiragana
assertPhoneticNameStyle(PhoneticNameStyle.JAPANESE, "\u3042\u3080\u308D", null, null);
assertPhoneticNameStyle(PhoneticNameStyle.JAPANESE, null, "\u3042\u3080\u308D", null);
assertPhoneticNameStyle(PhoneticNameStyle.JAPANESE, null, null, "\u306A\u307F\u3048");
assertPhoneticNameStyle(PhoneticNameStyle.JAPANESE, "\u3042\u3080\u308D", null,
"\u306A\u307F\u3048");
// Katakana
assertPhoneticNameStyle(PhoneticNameStyle.JAPANESE, "\u30A2\u30E0\u30ED", null,
"\u30CA\u30DF\u30A8");
// Half-width Katakana
assertPhoneticNameStyle(PhoneticNameStyle.JAPANESE, "\u30A2\u30E0\u30ED", null,
"\u30CA\u30DF\u30A8");
// Chinese
assertPhoneticNameStyle(PhoneticNameStyle.PINYIN, "du4", null, "juan1");
}
public void testSplitJapaneseName() {
createNameSplitter(Locale.JAPAN);
// One word is interpreted as given name only
assertSplitName("\u3042\u3080\u308D", null, "\u3042\u3080\u308D", null, null, null);
// Two words are interpreted as family + give name
assertSplitName("\u3042\u3080\u308D \u306A\u307F\u3048", null, "\u306A\u307F\u3048", null,
"\u3042\u3080\u308D", null);
// Multiple words are interpreted as "family - given names"
assertSplitName("\u3042\u3080\u308D \u3068\u304A\u308B \u306A\u307F\u3048", null,
"\u3068\u304A\u308B \u306A\u307F\u3048", null, "\u3042\u3080\u308D", null);
// Hanzi characters without spaces: lump them all in the given name
assertSplitName("\u6BB5\u5C0F\u6D9B", null, "\u6BB5\u5C0F\u6D9B", null, null, null);
}
public void testSplitChineseName() {
createNameSplitter(Locale.CHINA);
// Two Hanzi characters: familyName+givenName
assertSplitName("\u6BB5\u5C0F", null, "\u5C0F", null, "\u6BB5", null);
// Two Hanzi characters: familyName+middleName+givenName
assertSplitName("\u6BB5\u5C0F\u6D9B", null, "\u6D9B", "\u5C0F", "\u6BB5", null);
// Two Hanzi characters: familyName(2)+middleName+givenName
assertSplitName("\u6BB5\u5C0F\u6D9B\u6D9C", null, "\u6D9C", "\u6D9B", "\u6BB5\u5C0F", null);
}
public void testJoinJapaneseName() {
createNameSplitter(Locale.JAPAN);
assertJoinedName("\u3042\u3080\u308D", FullNameStyle.JAPANESE, null, "\u3042\u3080\u308D",
null, null, null, true);
// Given-name-first flag is ignored for CJK locales
assertJoinedName("\u3084\u307E\u3056\u304D \u3068\u304A\u308B", FullNameStyle.JAPANESE,
null, "\u3068\u304A\u308B", null, "\u3084\u307E\u3056\u304D", null, false);
assertJoinedName("\u3084\u307E\u3056\u304D \u3068\u304A\u308B \u3068\u304A\u308B",
FullNameStyle.JAPANESE, null, "\u3068\u304A\u308B", "\u3068\u304A\u308B",
"\u3084\u307E\u3056\u304D", null, false);
}
public void testJoinChineseName() {
createNameSplitter(Locale.CHINA);
// Given-name-first flag is ignored for CJK locales
assertJoinedName("\u6BB5\u5C0F\u6D9B", FullNameStyle.CHINESE, null,
"\u6D9B", "\u5C0F", "\u6BB5", null, true);
assertJoinedName("\u6BB5\u5C0F\u6D9B", FullNameStyle.CHINESE, null,
"\u6D9B", "\u5C0F", "\u6BB5", null, false);
}
private void assertSplitName(String fullName, String prefix, String givenNames,
String middleName, String familyName, String suffix) {
final Name name = new Name();
mNameSplitter.split(name, fullName);
assertEquals(prefix, name.getPrefix());
assertEquals(givenNames, name.getGivenNames());
assertEquals(middleName, name.getMiddleName());
assertEquals(familyName, name.getFamilyName());
assertEquals(suffix, name.getSuffix());
}
private void assertJoinedName(String expected, String prefix, String givenNames,
String middleName, String familyName, String suffix) {
assertJoinedName(expected, FullNameStyle.WESTERN, prefix, givenNames, middleName,
familyName, suffix, true);
}
private void assertJoinedName(String expected, int nameStyle, String prefix, String givenNames,
String middleName, String familyName, String suffix, boolean givenNameFirst) {
Name name = new Name();
name.fullNameStyle = nameStyle;
name.prefix = prefix;
name.givenNames = givenNames;
name.middleName = middleName;
name.familyName = familyName;
name.suffix = suffix;
String actual = mNameSplitter.join(name, givenNameFirst, true);
assertEquals(expected, actual);
}
private void assertFullNameStyle(int expectedFullNameStyle, String fullName) {
Name name = new Name();
mNameSplitter.split(name, fullName);
mNameSplitter.guessNameStyle(name);
assertEquals(expectedFullNameStyle, name.fullNameStyle);
}
private void assertFullNameStyle(int expectedFullNameStyle, String fullName,
String phoneticFamilyName, String phoneticMiddleName, String phoneticGivenName) {
Name name = new Name();
mNameSplitter.split(name, fullName);
name.phoneticFamilyName = phoneticFamilyName;
name.phoneticMiddleName = phoneticMiddleName;
name.phoneticGivenName = phoneticGivenName;
mNameSplitter.guessNameStyle(name);
assertEquals(expectedFullNameStyle, name.fullNameStyle);
}
private void assertPhoneticNameStyle(int expectedPhoneticNameStyle, String phoneticFamilyName,
String phoneticMiddleName, String phoneticGivenName) {
Name name = new Name();
name.phoneticFamilyName = phoneticFamilyName;
name.phoneticMiddleName = phoneticMiddleName;
name.phoneticGivenName = phoneticGivenName;
mNameSplitter.guessNameStyle(name);
assertEquals(expectedPhoneticNameStyle, name.phoneticNameStyle);
}
public void testSplitKoreanName() {
createNameSplitter(Locale.KOREA);
// Lee - Sang Il
assertSplitName("\uC774\uC0C1\uC77C", null, "\uC0C1\uC77C", null, "\uC774", null);
// Dok Go - Young Jae
assertSplitName("\uB3C5\uACE0\uC601\uC7AC",
null, "\uC601\uC7AC", null, "\uB3C5\uACE0", null);
}
}