libphonenumber归属地

一、简述
libphonenumber\src\com\google\i18n\phonenumbers\data\PhoneNumberMetadataProto_CN
保存着中国手机号码和国家号码的一些规范,比如
国际前缀“0|(1(?:[12]\\d|79|9[0235-7])\\d\\d)”
国际直拨号码前缀“!00|1(?:[12]\\d|79|9[02367])\\d\\d00”
手机号码分割成344格式的“1[3-9]”前缀
libphonenumber/src/com/google/i18n/phonenumbers/AsYouTypeFormatter.java
号码显示格式相关
internal/prefixmapper/src/com/google/i18n/phonenumbers/prefixmapper/PhonePrefixMap.java
归属地二分法查询
 
二、关于libphonenumber和libphonenumber-platform
 include $(CLEAR_VARS)
 LOCAL_MODULE := libphonenumber-platform
 LOCAL_MODULE_TAGS := optional
 LOCAL_SRC_FILES := $(libphonenumber_platform_src_files)
 LOCAL_JAVA_RESOURCE_DIRS := $(libphonenumber_platform_resource_dirs)
 LOCAL_JARJAR_RULES := $(LOCAL_PATH)/jarjar-rules.txt
 LOCAL_ADDITIONAL_DEPENDENCIES := $(LOCAL_PATH)/Android.mk
 LOCAL_NO_STANDARD_LIBRARIES := true
 LOCAL_JAVA_LIBRARIES := core-oj core-libart
 LOCAL_JAVA_LANGUAGE_VERSION := 1.7
 include $(BUILD_STATIC_JAVA_LIBRARY)
 
 # For unbundled use, supports gingerbread and up.
 include $(CLEAR_VARS)
 LOCAL_MODULE := libphonenumber
 LOCAL_MODULE_TAGS := optional
 LOCAL_SRC_FILES := $(libphonenumber_src_files)
 LOCAL_JAVA_RESOURCE_DIRS := $(libphonenumber_resource_dirs)
 LOCAL_ADDITIONAL_DEPENDENCIES := $(LOCAL_PATH)/Android.mk
 LOCAL_SDK_VERSION := 9
 LOCAL_JAVA_LANGUAGE_VERSION := 1.7
 include $(BUILD_STATIC_JAVA_LIBRARY)

external/libphonenumber/Android.mk中可以看出libphonenumber-platform和libphonenumber是同一份代码

不过libphonenumber-platform使用了LOCAL_JARJAR_RULES := $(LOCAL_PATH)/jarjar-rules.txt

jarjar-rules.txt                                                                                                                                                           
 rule com.google.** com.android.@1

将原来com.google的包名改成com.android开头的包名

 

1、libphonenumber-platform:com.android

被ext.jar引用

frameworks/base/Android.mk

include $(CLEAR_VARS)
 
 LOCAL_SRC_FILES := $(ext_src_files)
 ...
 LOCAL_STATIC_JAVA_LIBRARIES := libphonenumber-platform
 LOCAL_MODULE_TAGS := optional
 LOCAL_MODULE := ext
 ...
 LOCAL_DX_FLAGS := --core-library
 
 include $(BUILD_JAVA_LIBRARY)
拨号盘中用到的格式化号码
PhoneNumberFormatter.setPhoneNumberFormattingTextWatcher(getActivity(), mDigits);
frameworks\base\telephony\java\android\telephony\PhoneNumberFormattingTextWatcher.java引用libphonenumber-platform的AsYouTypeFormatter和PhoneNumberUtil
import com.android.i18n.phonenumbers.AsYouTypeFormatter;
import com.android.i18n.phonenumbers.PhoneNumberUtil;
修改调试验证:
调试拨号盘号码显示格式不对的问题,需要新建包com.android.i18n.phonenumbers,将AsYouTypeFormatter拷贝到此包中,才能debug
编译:
修改验证,需重编make -j32刷机
 

2、libphonenumber:com.google

Dialer模块引用

packages/apps/Dialer/Android.mk

LOCAL_STATIC_JAVA_LIBRARIES := \
     com.android.vcard \
..
     libphonenumber \
     ims-ext-common \

packages/apps/Dialer/src/com/android/dialer/util/PhoneNumberUtil.java

import com.google.i18n.phonenumbers.NumberParseException;
import com.google.i18n.phonenumbers.Phonenumber;
import com.google.i18n.phonenumbers.geocoding.PhoneNumberOfflineGeocoder;

修改调试验证:

将libphonenumber源码导入AS即可调试

编译:

packages/apps/Dialer$ mma -B -j32

 

三、修改点:

1、number去掉86之后匹配,同时去掉86_zh里号段前面的86,修改后可对8位号段支持

--- a/internal/prefixmapper/src/com/google/i18n/phonenumbers/prefixmapper/PhonePrefixMap.java
+++ b/internal/prefixmapper/src/com/google/i18n/phonenumbers/prefixmapper/PhonePrefixMap.java
@@ -178,8 +178,16 @@ public class PhonePrefixMap implements Externalizable {
    * @return  the description corresponding to the prefix that best matches this phone number
    */
   public String lookup(PhoneNumber number) {
-    long phonePrefix =
-        Long.parseLong(number.getCountryCode() + phoneUtil.getNationalSignificantNumber(number));
+    long phonePrefix = 0;
+    if (number.getCountryCode() == 86) {
+      phonePrefix =
+              Long.parseLong(phoneUtil.getNationalSignificantNumber(number));
+    } else {
+      phonePrefix =
+              Long.parseLong(number.getCountryCode() + phoneUtil.getNationalSignificantNumber(number));
+    }

2、修改问题 “拨号盘输入12位号码,部分号码会出现错误归属地”,错误识别国际号码前缀,提取的号码错误

    如198041312345,提取后用1312345来查找归属地

--- a/libphonenumber/src/com/google/i18n/phonenumbers/PhoneNumberUtil.java
+++ b/libphonenumber/src/com/google/i18n/phonenumbers/PhoneNumberUtil.java
@@ -2568,7 +2568,14 @@ public class PhoneNumberUtil {
   boolean maybeStripNationalPrefixAndCarrierCode(
       StringBuilder number, PhoneMetadata metadata, StringBuilder carrierCode) {
     int numberLength = number.length();
-    String possibleNationalPrefix = metadata.getNationalPrefixForParsing();
+    String possibleNationalPrefix;
+    if ("CN".equals(metadata.getId())) {
+        possibleNationalPrefix = "0|(1(?:[12]\\d|79|9[0235-7])\\d\\d)";
+    } else {
+        possibleNationalPrefix = metadata.getNationalPrefixForParsing();
+    }
     if (numberLength == 0 || possibleNationalPrefix.length() == 0) {
       // Early return for numbers of zero length.

3、修改个别号段如1999600被识别为IDD的问题,更新最新的idd prefix

--- a/libphonenumber/src/com/google/i18n/phonenumbers/PhoneNumberUtil.java
+++ b/libphonenumber/src/com/google/i18n/phonenumbers/PhoneNumberUtil.java
@@ -2427,7 +2427,15 @@ public class PhoneNumberUtil {
     // Set the default prefix to be something that will never match.
     String possibleCountryIddPrefix = "NonMatch";
     if (defaultRegionMetadata != null) {
-      possibleCountryIddPrefix = defaultRegionMetadata.getInternationalPrefix();
+      int defaultCountryCode = defaultRegionMetadata.getCountryCode();
+      if (defaultCountryCode == 86) {
+        // from https://github.com/googlei18n/libphonenumber/tree/master/java/libphonenumber/src/com/google/i18n/phonenumbers/data/PhoneNumberMetadataProto_CN
+        possibleCountryIddPrefix = "1(?:[12]\\d|79|9[0235-7])\\d\\d00";
+      } else {
+        possibleCountryIddPrefix = defaultRegionMetadata.getInternationalPrefix();
+      }
     }
 
     CountryCodeSource countryCodeSource =

4、修改“拨号盘输入191、198、199开头的11位号码,号码格式出错(非默认344)

     如19103 12123 4,应该显示为191 0312 1234

--- a/libphonenumber/src/com/google/i18n/phonenumbers/AsYouTypeFormatter.java
+++ b/libphonenumber/src/com/google/i18n/phonenumbers/AsYouTypeFormatter.java
@@ -206,8 +206,19 @@ public class AsYouTypeFormatter {
       }
       int lastLeadingDigitsPattern =
           Math.min(indexOfLeadingDigitsPattern, format.leadingDigitsPatternSize() - 1);
-      Pattern leadingDigitsPattern = regexCache.getPatternForRegex(
-          format.getLeadingDigitsPattern(lastLeadingDigitsPattern));
+      Pattern leadingDigitsPattern;
+      if (currentMetadata.getCountryCode() == 86) {
+        String leadingDigitsString = format.getLeadingDigitsPattern(lastLeadingDigitsPattern);
+        if ("1[3-578]".equals(leadingDigitsString)) {
+          leadingDigitsString = "1[3-9]";
+        }
+        leadingDigitsPattern = regexCache.getPatternForRegex(leadingDigitsString);
+      } else {
+        leadingDigitsPattern = regexCache.getPatternForRegex(
+                format.getLeadingDigitsPattern(lastLeadingDigitsPattern));
+      }
       Matcher m = leadingDigitsPattern.matcher(leadingDigits);
       if (!m.lookingAt()) {
         it.remove();
@@ -538,8 +549,16 @@ public class AsYouTypeFormatter {
       prefixBeforeNationalNumber.append('1').append(SEPARATOR_BEFORE_NATIONAL_NUMBER);
       isCompleteNumber = true;
     } else if (currentMetadata.hasNationalPrefixForParsing()) {
-      Pattern nationalPrefixForParsing =
-          regexCache.getPatternForRegex(currentMetadata.getNationalPrefixForParsing());
+      Pattern nationalPrefixForParsing;
+      if (currentMetadata.getCountryCode() == 86) {
+        nationalPrefixForParsing =
+                regexCache.getPatternForRegex("0|(1(?:[12]\\d|79|9[0235-7])\\d\\d)");
+      } else {
+        nationalPrefixForParsing =
+                regexCache.getPatternForRegex(currentMetadata.getNationalPrefixForParsing());
+      }
       Matcher m = nationalPrefixForParsing.matcher(nationalNumber);
       // Since some national prefix patterns are entirely optional, check that a national prefix
       // could actually be extracted.
@@ -565,9 +584,18 @@ public class AsYouTypeFormatter {
    *     defaultCountry.
    */
   private boolean attemptToExtractIdd() {
-    Pattern internationalPrefix =
-        regexCache.getPatternForRegex("\\" + PhoneNumberUtil.PLUS_SIGN + "|" +
-            currentMetadata.getInternationalPrefix());
+    Pattern internationalPrefix;
+    if (currentMetadata.getCountryCode() == 86) {
+      internationalPrefix =
+              regexCache.getPatternForRegex("\\" + PhoneNumberUtil.PLUS_SIGN + "|" +
+                      "!00|1(?:[12]\\d|79|9[02367])\\d\\d00");
+    } else {
+      internationalPrefix =
+              regexCache.getPatternForRegex("\\" + PhoneNumberUtil.PLUS_SIGN + "|" +
+                      currentMetadata.getInternationalPrefix());
+    }
     Matcher iddMatcher = internationalPrefix.matcher(accruedInputWithoutFormatting);
     if (iddMatcher.lookingAt()) {
       isCompleteNumber = true;

四、加入log

--- a/geocoder/src/com/google/i18n/phonenumbers/geocoding/PhoneNumberOfflineGeocoder.java
+++ b/geocoder/src/com/google/i18n/phonenumbers/geocoding/PhoneNumberOfflineGeocoder.java
@@ -24,6 +24,8 @@ import com.google.i18n.phonenumbers.prefixmapper.PrefixFileReader;
 
 import java.util.List;
 import java.util.Locale;
+import java.util.logging.Logger;
+import java.util.logging.Level;
 
@@ -38,6 +40,8 @@ public class PhoneNumberOfflineGeocoder {
 
   private final PhoneNumberUtil phoneUtil = PhoneNumberUtil.getInstance();
 
+  private final Logger logger = Logger.getLogger(PhoneNumberOfflineGeocoder.class.getName());
+
   // @VisibleForTesting
   PhoneNumberOfflineGeocoder(String phonePrefixDataDirectory) {
     prefixFileReader = new PrefixFileReader(phonePrefixDataDirectory);
@@ -206,6 +210,7 @@ public class PhoneNumberOfflineGeocoder {
   public String getDescriptionForNumber(PhoneNumber number, Locale languageCode, boolean isRawNumberStartWithZero) {
     final PhoneNumberType numberType = phoneUtil.getNumberType(number);
     final String numberString = String.valueOf(number.getNationalNumber());
+    logger.info("getDescriptionForNumber " + number);
     if (number.getCountryCode() == 86) {
       if (numberString.length() < 11) {
         //for posiblle mobile

输出如下:

 
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值