1 // Copyright (C) 2009 The Libphonenumber Authors 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 // Author: Shaopeng Jia 16 // Open-sourced by: Philippe Liard 17 18 #include "phonenumbers/phonenumberutil.h" 19 20 #include <string.h> 21 #include <algorithm> 22 #include <cctype> 23 #include <fstream> 24 #include <iostream> 25 #include <iterator> 26 #include <map> 27 #include <sstream> 28 #include <utility> 29 #include <vector> 30 31 #include <google/protobuf/message_lite.h> 32 #include <unicode/uchar.h> 33 #include <unicode/utf8.h> 34 35 #include "phonenumbers/asyoutypeformatter.h" 36 #include "phonenumbers/base/basictypes.h" 37 #include "phonenumbers/base/logging.h" 38 #include "phonenumbers/base/memory/singleton.h" 39 #include "phonenumbers/default_logger.h" 40 #include "phonenumbers/encoding_utils.h" 41 #include "phonenumbers/metadata.h" 42 #include "phonenumbers/normalize_utf8.h" 43 #include "phonenumbers/phonemetadata.pb.h" 44 #include "phonenumbers/phonenumber.h" 45 #include "phonenumbers/phonenumber.pb.h" 46 #include "phonenumbers/regexp_adapter.h" 47 #include "phonenumbers/regexp_cache.h" 48 #include "phonenumbers/regexp_factory.h" 49 #include "phonenumbers/region_code.h" 50 #include "phonenumbers/stl_util.h" 51 #include "phonenumbers/stringutil.h" 52 #include "phonenumbers/utf/unicodetext.h" 53 #include "phonenumbers/utf/utf.h" 54 55 namespace i18n { 56 namespace phonenumbers { 57 58 using std::cerr; 59 using std::endl; 60 using std::ifstream; 61 using std::make_pair; 62 using std::sort; 63 using std::stringstream; 64 65 using google::protobuf::RepeatedPtrField; 66 67 // static 68 const char PhoneNumberUtil::kPlusChars[] = "+\xEF\xBC\x8B"; /* "+" */ 69 // To find out the unicode code-point of the characters below in vim, highlight 70 // the character and type 'ga'. Note that the - is used to express ranges of 71 // full-width punctuation below, as well as being present in the expression 72 // itself. In emacs, you can use M-x unicode-what to query information about the 73 // unicode character. 74 // static 75 const char PhoneNumberUtil::kValidPunctuation[] = 76 /* "-x-- <U+200B><U+2060>().\\[\\]/~" */ 77 "-x\xE2\x80\x90-\xE2\x80\x95\xE2\x88\x92\xE3\x83\xBC\xEF\xBC\x8D-\xEF\xBC" 78 "\x8F \xC2\xA0\xC2\xAD\xE2\x80\x8B\xE2\x81\xA0\xE3\x80\x80()\xEF\xBC\x88" 79 "\xEF\xBC\x89\xEF\xBC\xBB\xEF\xBC\xBD.\\[\\]/~\xE2\x81\x93\xE2\x88\xBC"; 80 81 // static 82 const char PhoneNumberUtil::kCaptureUpToSecondNumberStart[] = "(.*)[\\\\/] *x"; 83 84 // static 85 const char PhoneNumberUtil::kRegionCodeForNonGeoEntity[] = "001"; 86 87 namespace { 88 89 // The prefix that needs to be inserted in front of a Colombian landline 90 // number when dialed from a mobile phone in Colombia. 91 const char kColombiaMobileToFixedLinePrefix[] = "3"; 92 93 // The kPlusSign signifies the international prefix. 94 const char kPlusSign[] = "+"; 95 96 const char kStarSign[] = "*"; 97 98 const char kRfc3966ExtnPrefix[] = ";ext="; 99 const char kRfc3966Prefix[] = "tel:"; 100 const char kRfc3966PhoneContext[] = ";phone-context="; 101 const char kRfc3966IsdnSubaddress[] = ";isub="; 102 103 const char kDigits[] = "\\p{Nd}"; 104 // We accept alpha characters in phone numbers, ASCII only. We store lower-case 105 // here only since our regular expressions are case-insensitive. 106 const char kValidAlpha[] = "a-z"; 107 108 // Default extension prefix to use when formatting. This will be put in front of 109 // any extension component of the number, after the main national number is 110 // formatted. For example, if you wish the default extension formatting to be " 111 // extn: 3456", then you should specify " extn: " here as the default extension 112 // prefix. This can be overridden by region-specific preferences. 113 const char kDefaultExtnPrefix[] = " ext. "; 114 115 // One-character symbols that can be used to indicate an extension. 116 const char kSingleExtnSymbolsForMatching[] = 117 "x\xEF\xBD\x98#\xEF\xBC\x83~\xEF\xBD\x9E"; 118 119 bool LoadCompiledInMetadata(PhoneMetadataCollection* metadata) { 120 if (!metadata->ParseFromArray(metadata_get(), metadata_size())) { 121 cerr << "Could not parse binary data." << endl; 122 return false; 123 } 124 return true; 125 } 126 127 // Returns a pointer to the description inside the metadata of the appropriate 128 // type. 129 const PhoneNumberDesc* GetNumberDescByType( 130 const PhoneMetadata& metadata, 131 PhoneNumberUtil::PhoneNumberType type) { 132 switch (type) { 133 case PhoneNumberUtil::PREMIUM_RATE: 134 return &metadata.premium_rate(); 135 case PhoneNumberUtil::TOLL_FREE: 136 return &metadata.toll_free(); 137 case PhoneNumberUtil::MOBILE: 138 return &metadata.mobile(); 139 case PhoneNumberUtil::FIXED_LINE: 140 case PhoneNumberUtil::FIXED_LINE_OR_MOBILE: 141 return &metadata.fixed_line(); 142 case PhoneNumberUtil::SHARED_COST: 143 return &metadata.shared_cost(); 144 case PhoneNumberUtil::VOIP: 145 return &metadata.voip(); 146 case PhoneNumberUtil::PERSONAL_NUMBER: 147 return &metadata.personal_number(); 148 case PhoneNumberUtil::PAGER: 149 return &metadata.pager(); 150 case PhoneNumberUtil::UAN: 151 return &metadata.uan(); 152 case PhoneNumberUtil::VOICEMAIL: 153 return &metadata.voicemail(); 154 default: 155 return &metadata.general_desc(); 156 } 157 } 158 159 // A helper function that is used by Format and FormatByPattern. 160 void PrefixNumberWithCountryCallingCode( 161 int country_calling_code, 162 PhoneNumberUtil::PhoneNumberFormat number_format, 163 string* formatted_number) { 164 switch (number_format) { 165 case PhoneNumberUtil::E164: 166 formatted_number->insert(0, StrCat(kPlusSign, country_calling_code)); 167 return; 168 case PhoneNumberUtil::INTERNATIONAL: 169 formatted_number->insert(0, StrCat(kPlusSign, country_calling_code, " ")); 170 return; 171 case PhoneNumberUtil::RFC3966: 172 formatted_number->insert(0, StrCat(kRfc3966Prefix, kPlusSign, 173 country_calling_code, "-")); 174 return; 175 case PhoneNumberUtil::NATIONAL: 176 default: 177 // Do nothing. 178 return; 179 } 180 } 181 182 // Returns true when one national number is the suffix of the other or both are 183 // the same. 184 bool IsNationalNumberSuffixOfTheOther(const PhoneNumber& first_number, 185 const PhoneNumber& second_number) { 186 const string& first_number_national_number = 187 SimpleItoa(static_cast<uint64>(first_number.national_number())); 188 const string& second_number_national_number = 189 SimpleItoa(static_cast<uint64>(second_number.national_number())); 190 // Note that HasSuffixString returns true if the numbers are equal. 191 return HasSuffixString(first_number_national_number, 192 second_number_national_number) || 193 HasSuffixString(second_number_national_number, 194 first_number_national_number); 195 } 196 197 bool IsNumberMatchingDesc(const string& national_number, 198 const PhoneNumberDesc& number_desc, 199 RegExpCache* regexp_cache) { 200 return regexp_cache->GetRegExp(number_desc.possible_number_pattern()) 201 .FullMatch(national_number) && 202 regexp_cache->GetRegExp(number_desc.national_number_pattern()) 203 .FullMatch(national_number); 204 } 205 206 PhoneNumberUtil::PhoneNumberType GetNumberTypeHelper( 207 const string& national_number, const PhoneMetadata& metadata, 208 RegExpCache* regexp_cache) { 209 const PhoneNumberDesc& general_desc = metadata.general_desc(); 210 if (!general_desc.has_national_number_pattern() || 211 !IsNumberMatchingDesc(national_number, general_desc, regexp_cache)) { 212 VLOG(4) << "Number type unknown - doesn't match general national number" 213 << " pattern."; 214 return PhoneNumberUtil::UNKNOWN; 215 } 216 if (IsNumberMatchingDesc(national_number, metadata.premium_rate(), 217 regexp_cache)) { 218 VLOG(4) << "Number is a premium number."; 219 return PhoneNumberUtil::PREMIUM_RATE; 220 } 221 if (IsNumberMatchingDesc(national_number, metadata.toll_free(), 222 regexp_cache)) { 223 VLOG(4) << "Number is a toll-free number."; 224 return PhoneNumberUtil::TOLL_FREE; 225 } 226 if (IsNumberMatchingDesc(national_number, metadata.shared_cost(), 227 regexp_cache)) { 228 VLOG(4) << "Number is a shared cost number."; 229 return PhoneNumberUtil::SHARED_COST; 230 } 231 if (IsNumberMatchingDesc(national_number, metadata.voip(), regexp_cache)) { 232 VLOG(4) << "Number is a VOIP (Voice over IP) number."; 233 return PhoneNumberUtil::VOIP; 234 } 235 if (IsNumberMatchingDesc(national_number, metadata.personal_number(), 236 regexp_cache)) { 237 VLOG(4) << "Number is a personal number."; 238 return PhoneNumberUtil::PERSONAL_NUMBER; 239 } 240 if (IsNumberMatchingDesc(national_number, metadata.pager(), regexp_cache)) { 241 VLOG(4) << "Number is a pager number."; 242 return PhoneNumberUtil::PAGER; 243 } 244 if (IsNumberMatchingDesc(national_number, metadata.uan(), regexp_cache)) { 245 VLOG(4) << "Number is a UAN."; 246 return PhoneNumberUtil::UAN; 247 } 248 if (IsNumberMatchingDesc(national_number, metadata.voicemail(), 249 regexp_cache)) { 250 VLOG(4) << "Number is a voicemail number."; 251 return PhoneNumberUtil::VOICEMAIL; 252 } 253 254 bool is_fixed_line = 255 IsNumberMatchingDesc(national_number, metadata.fixed_line(), 256 regexp_cache); 257 if (is_fixed_line) { 258 if (metadata.same_mobile_and_fixed_line_pattern()) { 259 VLOG(4) << "Fixed-line and mobile patterns equal, number is fixed-line" 260 << " or mobile"; 261 return PhoneNumberUtil::FIXED_LINE_OR_MOBILE; 262 } else if (IsNumberMatchingDesc(national_number, metadata.mobile(), 263 regexp_cache)) { 264 VLOG(4) << "Fixed-line and mobile patterns differ, but number is " 265 << "still fixed-line or mobile"; 266 return PhoneNumberUtil::FIXED_LINE_OR_MOBILE; 267 } 268 VLOG(4) << "Number is a fixed line number."; 269 return PhoneNumberUtil::FIXED_LINE; 270 } 271 // Otherwise, test to see if the number is mobile. Only do this if certain 272 // that the patterns for mobile and fixed line aren't the same. 273 if (!metadata.same_mobile_and_fixed_line_pattern() && 274 IsNumberMatchingDesc(national_number, metadata.mobile(), regexp_cache)) { 275 VLOG(4) << "Number is a mobile number."; 276 return PhoneNumberUtil::MOBILE; 277 } 278 VLOG(4) << "Number type unknown - doesn\'t match any specific number type" 279 << " pattern."; 280 return PhoneNumberUtil::UNKNOWN; 281 } 282 283 char32 ToUnicodeCodepoint(const char* unicode_char) { 284 char32 codepoint; 285 EncodingUtils::DecodeUTF8Char(unicode_char, &codepoint); 286 return codepoint; 287 } 288 289 // Helper initialiser method to create the regular-expression pattern to match 290 // extensions, allowing the one-codepoint extension symbols provided by 291 // single_extn_symbols. 292 // Note that there are currently three capturing groups for the extension itself 293 // - if this number is changed, MaybeStripExtension needs to be updated. 294 string CreateExtnPattern(const string& single_extn_symbols) { 295 static const string capturing_extn_digits = StrCat("([", kDigits, "]{1,7})"); 296 // The first regular expression covers RFC 3966 format, where the extension is 297 // added using ";ext=". The second more generic one starts with optional white 298 // space and ends with an optional full stop (.), followed by zero or more 299 // spaces/tabs and then the numbers themselves. The third one covers the 300 // special case of American numbers where the extension is written with a hash 301 // at the end, such as "- 503#". 302 // Note that the only capturing groups should be around the digits that you 303 // want to capture as part of the extension, or else parsing will fail! 304 // Canonical-equivalence doesn't seem to be an option with RE2, so we allow 305 // two options for representing the - the character itself, and one in the 306 // unicode decomposed form with the combining acute accent. 307 return (StrCat( 308 kRfc3966ExtnPrefix, capturing_extn_digits, "|" 309 /* "[ \\t,]*(?:e?xt(?:ensi(?:o?|))?n?|??|single_extn_symbols|" 310 "int||anexo)" 311 "[:\\.]?[ \\t,-]*", capturing_extn_digits, "#?|" */ 312 "[ \xC2\xA0\\t,]*(?:e?xt(?:ensi(?:o\xCC\x81?|\xC3\xB3))?n?|" 313 "(?:\xEF\xBD\x85)?\xEF\xBD\x98\xEF\xBD\x94(?:\xEF\xBD\x8E)?|" 314 "[", single_extn_symbols, "]|int|" 315 "\xEF\xBD\x89\xEF\xBD\x8E\xEF\xBD\x94|anexo)" 316 "[:\\.\xEF\xBC\x8E]?[ \xC2\xA0\\t,-]*", capturing_extn_digits, 317 "#?|[- ]+([", kDigits, "]{1,5})#")); 318 } 319 320 // Normalizes a string of characters representing a phone number by replacing 321 // all characters found in the accompanying map with the values therein, and 322 // stripping all other characters if remove_non_matches is true. 323 // Parameters: 324 // number - a pointer to a string of characters representing a phone number to 325 // be normalized. 326 // normalization_replacements - a mapping of characters to what they should be 327 // replaced by in the normalized version of the phone number 328 // remove_non_matches - indicates whether characters that are not able to be 329 // replaced should be stripped from the number. If this is false, they will be 330 // left unchanged in the number. 331 void NormalizeHelper(const map<char32, char>& normalization_replacements, 332 bool remove_non_matches, 333 string* number) { 334 DCHECK(number); 335 UnicodeText number_as_unicode; 336 number_as_unicode.PointToUTF8(number->data(), number->size()); 337 string normalized_number; 338 char unicode_char[5]; 339 for (UnicodeText::const_iterator it = number_as_unicode.begin(); 340 it != number_as_unicode.end(); 341 ++it) { 342 map<char32, char>::const_iterator found_glyph_pair = 343 normalization_replacements.find(*it); 344 if (found_glyph_pair != normalization_replacements.end()) { 345 normalized_number.push_back(found_glyph_pair->second); 346 } else if (!remove_non_matches) { 347 // Find out how long this unicode char is so we can append it all. 348 int char_len = it.get_utf8(unicode_char); 349 normalized_number.append(unicode_char, char_len); 350 } 351 // If neither of the above are true, we remove this character. 352 } 353 number->assign(normalized_number); 354 } 355 356 PhoneNumberUtil::ValidationResult TestNumberLengthAgainstPattern( 357 const RegExp& number_pattern, const string& number) { 358 string extracted_number; 359 if (number_pattern.FullMatch(number, &extracted_number)) { 360 return PhoneNumberUtil::IS_POSSIBLE; 361 } 362 if (number_pattern.PartialMatch(number, &extracted_number)) { 363 return PhoneNumberUtil::TOO_LONG; 364 } else { 365 return PhoneNumberUtil::TOO_SHORT; 366 } 367 } 368 369 } // namespace 370 371 void PhoneNumberUtil::SetLogger(Logger* logger) { 372 logger_.reset(logger); 373 Logger::set_logger_impl(logger_.get()); 374 } 375 376 class PhoneNumberRegExpsAndMappings { 377 private: 378 void InitializeMapsAndSets() { 379 diallable_char_mappings_.insert(make_pair('+', '+')); 380 diallable_char_mappings_.insert(make_pair('*', '*')); 381 // Here we insert all punctuation symbols that we wish to respect when 382 // formatting alpha numbers, as they show the intended number groupings. 383 all_plus_number_grouping_symbols_.insert( 384 make_pair(ToUnicodeCodepoint("-"), '-')); 385 all_plus_number_grouping_symbols_.insert( 386 make_pair(ToUnicodeCodepoint("\xEF\xBC\x8D" /* "" */), '-')); 387 all_plus_number_grouping_symbols_.insert( 388 make_pair(ToUnicodeCodepoint("\xE2\x80\x90" /* "" */), '-')); 389 all_plus_number_grouping_symbols_.insert( 390 make_pair(ToUnicodeCodepoint("\xE2\x80\x91" /* "" */), '-')); 391 all_plus_number_grouping_symbols_.insert( 392 make_pair(ToUnicodeCodepoint("\xE2\x80\x92" /* "" */), '-')); 393 all_plus_number_grouping_symbols_.insert( 394 make_pair(ToUnicodeCodepoint("\xE2\x80\x93" /* "" */), '-')); 395 all_plus_number_grouping_symbols_.insert( 396 make_pair(ToUnicodeCodepoint("\xE2\x80\x94" /* "" */), '-')); 397 all_plus_number_grouping_symbols_.insert( 398 make_pair(ToUnicodeCodepoint("\xE2\x80\x95" /* "" */), '-')); 399 all_plus_number_grouping_symbols_.insert( 400 make_pair(ToUnicodeCodepoint("\xE2\x88\x92" /* "" */), '-')); 401 all_plus_number_grouping_symbols_.insert( 402 make_pair(ToUnicodeCodepoint("/"), '/')); 403 all_plus_number_grouping_symbols_.insert( 404 make_pair(ToUnicodeCodepoint("\xEF\xBC\x8F" /* "" */), '/')); 405 all_plus_number_grouping_symbols_.insert( 406 make_pair(ToUnicodeCodepoint(" "), ' ')); 407 all_plus_number_grouping_symbols_.insert( 408 make_pair(ToUnicodeCodepoint("\xE3\x80\x80" /* "" */), ' ')); 409 all_plus_number_grouping_symbols_.insert( 410 make_pair(ToUnicodeCodepoint("\xE2\x81\xA0"), ' ')); 411 all_plus_number_grouping_symbols_.insert( 412 make_pair(ToUnicodeCodepoint("."), '.')); 413 all_plus_number_grouping_symbols_.insert( 414 make_pair(ToUnicodeCodepoint("\xEF\xBC\x8E" /* "" */), '.')); 415 // Only the upper-case letters are added here - the lower-case versions are 416 // added programmatically. 417 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("A"), '2')); 418 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("B"), '2')); 419 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("C"), '2')); 420 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("D"), '3')); 421 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("E"), '3')); 422 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("F"), '3')); 423 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("G"), '4')); 424 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("H"), '4')); 425 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("I"), '4')); 426 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("J"), '5')); 427 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("K"), '5')); 428 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("L"), '5')); 429 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("M"), '6')); 430 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("N"), '6')); 431 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("O"), '6')); 432 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("P"), '7')); 433 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("Q"), '7')); 434 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("R"), '7')); 435 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("S"), '7')); 436 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("T"), '8')); 437 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("U"), '8')); 438 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("V"), '8')); 439 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("W"), '9')); 440 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("X"), '9')); 441 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("Y"), '9')); 442 alpha_mappings_.insert(make_pair(ToUnicodeCodepoint("Z"), '9')); 443 map<char32, char> lower_case_mappings; 444 map<char32, char> alpha_letters; 445 for (map<char32, char>::const_iterator it = alpha_mappings_.begin(); 446 it != alpha_mappings_.end(); 447 ++it) { 448 // Convert all the upper-case ASCII letters to lower-case. 449 if (it->first < 128) { 450 char letter_as_upper = static_cast<char>(it->first); 451 char32 letter_as_lower = static_cast<char32>(tolower(letter_as_upper)); 452 lower_case_mappings.insert(make_pair(letter_as_lower, it->second)); 453 // Add the letters in both variants to the alpha_letters map. This just 454 // pairs each letter with its upper-case representation so that it can 455 // be retained when normalising alpha numbers. 456 alpha_letters.insert(make_pair(letter_as_lower, letter_as_upper)); 457 alpha_letters.insert(make_pair(it->first, letter_as_upper)); 458 } 459 } 460 // In the Java version we don't insert the lower-case mappings in the map, 461 // because we convert to upper case on the fly. Doing this here would 462 // involve pulling in all of ICU, which we don't want to do if we don't have 463 // to. 464 alpha_mappings_.insert(lower_case_mappings.begin(), 465 lower_case_mappings.end()); 466 alpha_phone_mappings_.insert(alpha_mappings_.begin(), 467 alpha_mappings_.end()); 468 all_plus_number_grouping_symbols_.insert(alpha_letters.begin(), 469 alpha_letters.end()); 470 // Add the ASCII digits so that they don't get deleted by NormalizeHelper(). 471 for (char c = '0'; c <= '9'; ++c) { 472 diallable_char_mappings_.insert(make_pair(c, c)); 473 alpha_phone_mappings_.insert(make_pair(c, c)); 474 all_plus_number_grouping_symbols_.insert(make_pair(c, c)); 475 } 476 } 477 478 // Small string helpers since StrCat has a maximum number of arguments. These 479 // are both used to build valid_phone_number_. 480 const string punctuation_and_star_sign_; 481 const string min_length_phone_number_pattern_; 482 483 // Regular expression of viable phone numbers. This is location independent. 484 // Checks we have at least three leading digits, and only valid punctuation, 485 // alpha characters and digits in the phone number. Does not include extension 486 // data. The symbol 'x' is allowed here as valid punctuation since it is often 487 // used as a placeholder for carrier codes, for example in Brazilian phone 488 // numbers. We also allow multiple plus-signs at the start. 489 // Corresponds to the following: 490 // [digits]{minLengthNsn}| 491 // plus_sign*(([punctuation]|[star])*[digits]){3,} 492 // ([punctuation]|[star]|[digits]|[alpha])* 493 // 494 // The first reg-ex is to allow short numbers (two digits long) to be parsed 495 // if they are entered as "15" etc, but only if there is no punctuation in 496 // them. The second expression restricts the number of digits to three or 497 // more, but then allows them to be in international form, and to have 498 // alpha-characters and punctuation. 499 const string valid_phone_number_; 500 501 // Regexp of all possible ways to write extensions, for use when parsing. This 502 // will be run as a case-insensitive regexp match. Wide character versions are 503 // also provided after each ASCII version. 504 // For parsing, we are slightly more lenient in our interpretation than for 505 // matching. Here we allow a "comma" as a possible extension indicator. When 506 // matching, this is hardly ever used to indicate this. 507 const string extn_patterns_for_parsing_; 508 509 public: 510 scoped_ptr<const AbstractRegExpFactory> regexp_factory_; 511 scoped_ptr<RegExpCache> regexp_cache_; 512 513 // A map that contains characters that are essential when dialling. That means 514 // any of the characters in this map must not be removed from a number when 515 // dialing, otherwise the call will not reach the intended destination. 516 map<char32, char> diallable_char_mappings_; 517 // These mappings map a character (key) to a specific digit that should 518 // replace it for normalization purposes. 519 map<char32, char> alpha_mappings_; 520 // For performance reasons, store a map of combining alpha_mappings with ASCII 521 // digits. 522 map<char32, char> alpha_phone_mappings_; 523 524 // Separate map of all symbols that we wish to retain when formatting alpha 525 // numbers. This includes digits, ascii letters and number grouping symbols 526 // such as "-" and " ". 527 map<char32, char> all_plus_number_grouping_symbols_; 528 529 // Pattern that makes it easy to distinguish whether a region has a unique 530 // international dialing prefix or not. If a region has a unique international 531 // prefix (e.g. 011 in USA), it will be represented as a string that contains 532 // a sequence of ASCII digits. If there are multiple available international 533 // prefixes in a region, they will be represented as a regex string that 534 // always contains character(s) other than ASCII digits. 535 // Note this regex also includes tilde, which signals waiting for the tone. 536 scoped_ptr<const RegExp> unique_international_prefix_; 537 538 scoped_ptr<const RegExp> digits_pattern_; 539 scoped_ptr<const RegExp> capturing_digit_pattern_; 540 scoped_ptr<const RegExp> capturing_ascii_digits_pattern_; 541 542 // Regular expression of acceptable characters that may start a phone number 543 // for the purposes of parsing. This allows us to strip away meaningless 544 // prefixes to phone numbers that may be mistakenly given to us. This consists 545 // of digits, the plus symbol and arabic-indic digits. This does not contain 546 // alpha characters, although they may be used later in the number. It also 547 // does not include other punctuation, as this will be stripped later during 548 // parsing and is of no information value when parsing a number. The string 549 // starting with this valid character is captured. 550 // This corresponds to VALID_START_CHAR in the java version. 551 scoped_ptr<const RegExp> valid_start_char_pattern_; 552 553 // Regular expression of valid characters before a marker that might indicate 554 // a second number. 555 scoped_ptr<const RegExp> capture_up_to_second_number_start_pattern_; 556 557 // Regular expression of trailing characters that we want to remove. We remove 558 // all characters that are not alpha or numerical characters. The hash 559 // character is retained here, as it may signify the previous block was an 560 // extension. Note the capturing block at the start to capture the rest of the 561 // number if this was a match. 562 // This corresponds to UNWANTED_END_CHAR_PATTERN in the java version. 563 scoped_ptr<const RegExp> unwanted_end_char_pattern_; 564 565 // Regular expression of groups of valid punctuation characters. 566 scoped_ptr<const RegExp> separator_pattern_; 567 568 // Regexp of all possible ways to write extensions, for use when finding phone 569 // numbers in text. This will be run as a case-insensitive regexp match. Wide 570 // character versions are also provided after each ASCII version. 571 const string extn_patterns_for_matching_; 572 573 // Regexp of all known extension prefixes used by different regions followed 574 // by 1 or more valid digits, for use when parsing. 575 scoped_ptr<const RegExp> extn_pattern_; 576 577 // We append optionally the extension pattern to the end here, as a valid 578 // phone number may have an extension prefix appended, followed by 1 or more 579 // digits. 580 scoped_ptr<const RegExp> valid_phone_number_pattern_; 581 582 // We use this pattern to check if the phone number has at least three letters 583 // in it - if so, then we treat it as a number where some phone-number digits 584 // are represented by letters. 585 scoped_ptr<const RegExp> valid_alpha_phone_pattern_; 586 587 scoped_ptr<const RegExp> first_group_capturing_pattern_; 588 589 scoped_ptr<const RegExp> carrier_code_pattern_; 590 591 scoped_ptr<const RegExp> plus_chars_pattern_; 592 593 PhoneNumberRegExpsAndMappings() 594 : punctuation_and_star_sign_(StrCat(PhoneNumberUtil::kValidPunctuation, 595 kStarSign)), 596 min_length_phone_number_pattern_( 597 StrCat(kDigits, "{", PhoneNumberUtil::kMinLengthForNsn, "}")), 598 valid_phone_number_( 599 StrCat(min_length_phone_number_pattern_, "|[", 600 PhoneNumberUtil::kPlusChars, "]*(?:[", 601 punctuation_and_star_sign_, "]*", 602 kDigits, "){3,}[", kValidAlpha, 603 punctuation_and_star_sign_, kDigits, 604 "]*")), 605 extn_patterns_for_parsing_( 606 CreateExtnPattern(StrCat(",", kSingleExtnSymbolsForMatching))), 607 regexp_factory_(new RegExpFactory()), 608 regexp_cache_(new RegExpCache(*regexp_factory_.get(), 128)), 609 diallable_char_mappings_(), 610 alpha_mappings_(), 611 alpha_phone_mappings_(), 612 all_plus_number_grouping_symbols_(), 613 unique_international_prefix_(regexp_factory_->CreateRegExp( 614 /* "[\\d]+(?:[~][\\d]+)?" */ 615 "[\\d]+(?:[~\xE2\x81\x93\xE2\x88\xBC\xEF\xBD\x9E][\\d]+)?")), 616 digits_pattern_( 617 regexp_factory_->CreateRegExp(StrCat("[", kDigits, "]*"))), 618 capturing_digit_pattern_( 619 regexp_factory_->CreateRegExp(StrCat("([", kDigits, "])"))), 620 capturing_ascii_digits_pattern_( 621 regexp_factory_->CreateRegExp("(\\d+)")), 622 valid_start_char_pattern_(regexp_factory_->CreateRegExp( 623 StrCat("[", PhoneNumberUtil::kPlusChars, kDigits, "]"))), 624 capture_up_to_second_number_start_pattern_( 625 regexp_factory_->CreateRegExp( 626 PhoneNumberUtil::kCaptureUpToSecondNumberStart)), 627 unwanted_end_char_pattern_( 628 regexp_factory_->CreateRegExp("[^\\p{N}\\p{L}#]")), 629 separator_pattern_( 630 regexp_factory_->CreateRegExp( 631 StrCat("[", PhoneNumberUtil::kValidPunctuation, "]+"))), 632 extn_patterns_for_matching_( 633 CreateExtnPattern(kSingleExtnSymbolsForMatching)), 634 extn_pattern_(regexp_factory_->CreateRegExp( 635 StrCat("(?i)(?:", extn_patterns_for_parsing_, ")$"))), 636 valid_phone_number_pattern_(regexp_factory_->CreateRegExp( 637 StrCat("(?i)", valid_phone_number_, 638 "(?:", extn_patterns_for_parsing_, ")?"))), 639 valid_alpha_phone_pattern_(regexp_factory_->CreateRegExp( 640 StrCat("(?i)(?:.*?[", kValidAlpha, "]){3}"))), 641 // The first_group_capturing_pattern was originally set to $1 but there 642 // are some countries for which the first group is not used in the 643 // national pattern (e.g. Argentina) so the $1 group does not match 644 // correctly. Therefore, we use \d, so that the first group actually 645 // used in the pattern will be matched. 646 first_group_capturing_pattern_( 647 regexp_factory_->CreateRegExp("(\\$\\d)")), 648 carrier_code_pattern_(regexp_factory_->CreateRegExp("\\$CC")), 649 plus_chars_pattern_( 650 regexp_factory_->CreateRegExp( 651 StrCat("[", PhoneNumberUtil::kPlusChars, "]+"))) { 652 InitializeMapsAndSets(); 653 } 654 655 private: 656 DISALLOW_COPY_AND_ASSIGN(PhoneNumberRegExpsAndMappings); 657 }; 658 659 // Private constructor. Also takes care of initialisation. 660 PhoneNumberUtil::PhoneNumberUtil() 661 : logger_(Logger::set_logger_impl(new NullLogger())), 662 reg_exps_(new PhoneNumberRegExpsAndMappings), 663 country_calling_code_to_region_code_map_(new vector<IntRegionsPair>()), 664 nanpa_regions_(new set<string>()), 665 region_to_metadata_map_(new map<string, PhoneMetadata>()), 666 country_code_to_non_geographical_metadata_map_( 667 new map<int, PhoneMetadata>) { 668 Logger::set_logger_impl(logger_.get()); 669 // TODO: Update the java version to put the contents of the init 670 // method inside the constructor as well to keep both in sync. 671 PhoneMetadataCollection metadata_collection; 672 if (!LoadCompiledInMetadata(&metadata_collection)) { 673 LOG(DFATAL) << "Could not parse compiled-in metadata."; 674 return; 675 } 676 // Storing data in a temporary map to make it easier to find other regions 677 // that share a country calling code when inserting data. 678 map<int, list<string>* > country_calling_code_to_region_map; 679 for (RepeatedPtrField<PhoneMetadata>::const_iterator it = 680 metadata_collection.metadata().begin(); 681 it != metadata_collection.metadata().end(); 682 ++it) { 683 const string& region_code = it->id(); 684 if (region_code == RegionCode::GetUnknown()) { 685 continue; 686 } 687 688 int country_calling_code = it->country_code(); 689 if (kRegionCodeForNonGeoEntity == region_code) { 690 country_code_to_non_geographical_metadata_map_->insert( 691 make_pair(country_calling_code, *it)); 692 } else { 693 region_to_metadata_map_->insert(make_pair(region_code, *it)); 694 } 695 map<int, list<string>* >::iterator calling_code_in_map = 696 country_calling_code_to_region_map.find(country_calling_code); 697 if (calling_code_in_map != country_calling_code_to_region_map.end()) { 698 if (it->main_country_for_code()) { 699 calling_code_in_map->second->push_front(region_code); 700 } else { 701 calling_code_in_map->second->push_back(region_code); 702 } 703 } else { 704 // For most country calling codes, there will be only one region code. 705 list<string>* list_with_region_code = new list<string>(); 706 list_with_region_code->push_back(region_code); 707 country_calling_code_to_region_map.insert( 708 make_pair(country_calling_code, list_with_region_code)); 709 } 710 if (country_calling_code == kNanpaCountryCode) { 711 nanpa_regions_->insert(region_code); 712 } 713 } 714 715 country_calling_code_to_region_code_map_->insert( 716 country_calling_code_to_region_code_map_->begin(), 717 country_calling_code_to_region_map.begin(), 718 country_calling_code_to_region_map.end()); 719 // Sort all the pairs in ascending order according to country calling code. 720 sort(country_calling_code_to_region_code_map_->begin(), 721 country_calling_code_to_region_code_map_->end(), 722 OrderByFirst()); 723 } 724 725 PhoneNumberUtil::~PhoneNumberUtil() { 726 STLDeleteContainerPairSecondPointers( 727 country_calling_code_to_region_code_map_->begin(), 728 country_calling_code_to_region_code_map_->end()); 729 } 730 731 void PhoneNumberUtil::GetSupportedRegions(set<string>* regions) const { 732 DCHECK(regions); 733 for (map<string, PhoneMetadata>::const_iterator it = 734 region_to_metadata_map_->begin(); it != region_to_metadata_map_->end(); 735 ++it) { 736 regions->insert(it->first); 737 } 738 } 739 740 // Public wrapper function to get a PhoneNumberUtil instance with the default 741 // metadata file. 742 // static 743 PhoneNumberUtil* PhoneNumberUtil::GetInstance() { 744 return Singleton<PhoneNumberUtil>::GetInstance(); 745 } 746 747 const string& PhoneNumberUtil::GetExtnPatternsForMatching() const { 748 return reg_exps_->extn_patterns_for_matching_; 749 } 750 751 bool PhoneNumberUtil::StartsWithPlusCharsPattern(const string& number) 752 const { 753 const scoped_ptr<RegExpInput> number_string_piece( 754 reg_exps_->regexp_factory_->CreateInput(number)); 755 return reg_exps_->plus_chars_pattern_->Consume(number_string_piece.get()); 756 } 757 758 bool PhoneNumberUtil::ContainsOnlyValidDigits(const string& s) const { 759 return reg_exps_->digits_pattern_->FullMatch(s); 760 } 761 762 void PhoneNumberUtil::TrimUnwantedEndChars(string* number) const { 763 DCHECK(number); 764 UnicodeText number_as_unicode; 765 number_as_unicode.PointToUTF8(number->data(), number->size()); 766 char current_char[5]; 767 int len; 768 UnicodeText::const_reverse_iterator reverse_it(number_as_unicode.end()); 769 for (; reverse_it.base() != number_as_unicode.begin(); ++reverse_it) { 770 len = reverse_it.get_utf8(current_char); 771 current_char[len] = '\0'; 772 if (!reg_exps_->unwanted_end_char_pattern_->FullMatch(current_char)) { 773 break; 774 } 775 } 776 777 number->assign(UnicodeText::UTF8Substring(number_as_unicode.begin(), 778 reverse_it.base())); 779 } 780 781 bool PhoneNumberUtil::IsFormatEligibleForAsYouTypeFormatter( 782 const string& format) const { 783 // A pattern that is used to determine if a numberFormat under 784 // availableFormats is eligible to be used by the AYTF. It is eligible when 785 // the format element under numberFormat contains groups of the dollar sign 786 // followed by a single digit, separated by valid phone number punctuation. 787 // This prevents invalid punctuation (such as the star sign in Israeli star 788 // numbers) getting into the output of the AYTF. 789 const RegExp& eligible_format_pattern = reg_exps_->regexp_cache_->GetRegExp( 790 StrCat("[", kValidPunctuation, "]*", "(\\$\\d", "[", 791 kValidPunctuation, "]*)+")); 792 return eligible_format_pattern.FullMatch(format); 793 } 794 795 bool PhoneNumberUtil::FormattingRuleHasFirstGroupOnly( 796 const string& national_prefix_formatting_rule) const { 797 // A pattern that is used to determine if the national prefix formatting rule 798 // has the first group only, i.e., does not start with the national prefix. 799 // Note that the pattern explicitly allows for unbalanced parentheses. 800 const RegExp& first_group_only_prefix_pattern = 801 reg_exps_->regexp_cache_->GetRegExp("\\(?\\$1\\)?"); 802 return national_prefix_formatting_rule.empty() || 803 first_group_only_prefix_pattern.FullMatch( 804 national_prefix_formatting_rule); 805 } 806 807 void PhoneNumberUtil::GetNddPrefixForRegion(const string& region_code, 808 bool strip_non_digits, 809 string* national_prefix) const { 810 DCHECK(national_prefix); 811 const PhoneMetadata* metadata = GetMetadataForRegion(region_code); 812 if (!metadata) { 813 LOG(WARNING) << "Invalid or unknown region code (" << region_code 814 << ") provided."; 815 return; 816 } 817 national_prefix->assign(metadata->national_prefix()); 818 if (strip_non_digits) { 819 // Note: if any other non-numeric symbols are ever used in national 820 // prefixes, these would have to be removed here as well. 821 strrmm(national_prefix, "~"); 822 } 823 } 824 825 bool PhoneNumberUtil::IsValidRegionCode(const string& region_code) const { 826 return (region_to_metadata_map_->find(region_code) != 827 region_to_metadata_map_->end()); 828 } 829 830 bool PhoneNumberUtil::HasValidCountryCallingCode( 831 int country_calling_code) const { 832 // Create an IntRegionsPair with the country_code passed in, and use it to 833 // locate the pair with the same country_code in the sorted vector. 834 IntRegionsPair target_pair; 835 target_pair.first = country_calling_code; 836 return (binary_search(country_calling_code_to_region_code_map_->begin(), 837 country_calling_code_to_region_code_map_->end(), 838 target_pair, OrderByFirst())); 839 } 840 841 // Returns a pointer to the phone metadata for the appropriate region or NULL 842 // if the region code is invalid or unknown. 843 const PhoneMetadata* PhoneNumberUtil::GetMetadataForRegion( 844 const string& region_code) const { 845 map<string, PhoneMetadata>::const_iterator it = 846 region_to_metadata_map_->find(region_code); 847 if (it != region_to_metadata_map_->end()) { 848 return &it->second; 849 } 850 return NULL; 851 } 852 853 const PhoneMetadata* PhoneNumberUtil::GetMetadataForNonGeographicalRegion( 854 int country_calling_code) const { 855 map<int, PhoneMetadata>::const_iterator it = 856 country_code_to_non_geographical_metadata_map_->find( 857 country_calling_code); 858 if (it != country_code_to_non_geographical_metadata_map_->end()) { 859 return &it->second; 860 } 861 return NULL; 862 } 863 864 void PhoneNumberUtil::Format(const PhoneNumber& number, 865 PhoneNumberFormat number_format, 866 string* formatted_number) const { 867 DCHECK(formatted_number); 868 if (number.national_number() == 0) { 869 const string& raw_input = number.raw_input(); 870 if (!raw_input.empty()) { 871 // Unparseable numbers that kept their raw input just use that. 872 // This is the only case where a number can be formatted as E164 without a 873 // leading '+' symbol (but the original number wasn't parseable anyway). 874 // TODO: Consider removing the 'if' above so that unparseable 875 // strings without raw input format to the empty string instead of "+00". 876 formatted_number->assign(raw_input); 877 return; 878 } 879 } 880 int country_calling_code = number.country_code(); 881 string national_significant_number; 882 GetNationalSignificantNumber(number, &national_significant_number); 883 if (number_format == E164) { 884 // Early exit for E164 case (even if the country calling code is invalid) 885 // since no formatting of the national number needs to be applied. 886 // Extensions are not formatted. 887 formatted_number->assign(national_significant_number); 888 PrefixNumberWithCountryCallingCode(country_calling_code, E164, 889 formatted_number); 890 return; 891 } 892 if (!HasValidCountryCallingCode(country_calling_code)) { 893 formatted_number->assign(national_significant_number); 894 return; 895 } 896 // Note here that all NANPA formatting rules are contained by US, so we use 897 // that to format NANPA numbers. The same applies to Russian Fed regions - 898 // rules are contained by Russia. French Indian Ocean country rules are 899 // contained by Runion. 900 string region_code; 901 GetRegionCodeForCountryCode(country_calling_code, ®ion_code); 902 // Metadata cannot be NULL because the country calling code is valid (which 903 // means that the region code cannot be ZZ and must be one of our supported 904 // region codes). 905 const PhoneMetadata* metadata = 906 GetMetadataForRegionOrCallingCode(country_calling_code, region_code); 907 FormatNsn(national_significant_number, *metadata, number_format, 908 formatted_number); 909 MaybeAppendFormattedExtension(number, *metadata, number_format, 910 formatted_number); 911 PrefixNumberWithCountryCallingCode(country_calling_code, number_format, 912 formatted_number); 913 } 914 915 void PhoneNumberUtil::FormatByPattern( 916 const PhoneNumber& number, 917 PhoneNumberFormat number_format, 918 const RepeatedPtrField<NumberFormat>& user_defined_formats, 919 string* formatted_number) const { 920 DCHECK(formatted_number); 921 int country_calling_code = number.country_code(); 922 // Note GetRegionCodeForCountryCode() is used because formatting information 923 // for regions which share a country calling code is contained by only one 924 // region for performance reasons. For example, for NANPA regions it will be 925 // contained in the metadata for US. 926 string national_significant_number; 927 GetNationalSignificantNumber(number, &national_significant_number); 928 if (!HasValidCountryCallingCode(country_calling_code)) { 929 formatted_number->assign(national_significant_number); 930 return; 931 } 932 string region_code; 933 GetRegionCodeForCountryCode(country_calling_code, ®ion_code); 934 // Metadata cannot be NULL because the country calling code is valid. 935 const PhoneMetadata* metadata = 936 GetMetadataForRegionOrCallingCode(country_calling_code, region_code); 937 const NumberFormat* formatting_pattern = 938 ChooseFormattingPatternForNumber(user_defined_formats, 939 national_significant_number); 940 if (!formatting_pattern) { 941 // If no pattern above is matched, we format the number as a whole. 942 formatted_number->assign(national_significant_number); 943 } else { 944 NumberFormat num_format_copy; 945 // Before we do a replacement of the national prefix pattern $NP with the 946 // national prefix, we need to copy the rule so that subsequent replacements 947 // for different numbers have the appropriate national prefix. 948 num_format_copy.MergeFrom(*formatting_pattern); 949 string national_prefix_formatting_rule( 950 formatting_pattern->national_prefix_formatting_rule()); 951 if (!national_prefix_formatting_rule.empty()) { 952 const string& national_prefix = metadata->national_prefix(); 953 if (!national_prefix.empty()) { 954 // Replace $NP with national prefix and $FG with the first group ($1). 955 GlobalReplaceSubstring("$NP", national_prefix, 956 &national_prefix_formatting_rule); 957 GlobalReplaceSubstring("$FG", "$1", 958 &national_prefix_formatting_rule); 959 num_format_copy.set_national_prefix_formatting_rule( 960 national_prefix_formatting_rule); 961 } else { 962 // We don't want to have a rule for how to format the national prefix if 963 // there isn't one. 964 num_format_copy.clear_national_prefix_formatting_rule(); 965 } 966 } 967 FormatNsnUsingPattern(national_significant_number, num_format_copy, 968 number_format, formatted_number); 969 } 970 MaybeAppendFormattedExtension(number, *metadata, NATIONAL, formatted_number); 971 PrefixNumberWithCountryCallingCode(country_calling_code, number_format, 972 formatted_number); 973 } 974 975 void PhoneNumberUtil::FormatNationalNumberWithCarrierCode( 976 const PhoneNumber& number, 977 const string& carrier_code, 978 string* formatted_number) const { 979 int country_calling_code = number.country_code(); 980 string national_significant_number; 981 GetNationalSignificantNumber(number, &national_significant_number); 982 if (!HasValidCountryCallingCode(country_calling_code)) { 983 formatted_number->assign(national_significant_number); 984 return; 985 } 986 987 // Note GetRegionCodeForCountryCode() is used because formatting information 988 // for regions which share a country calling code is contained by only one 989 // region for performance reasons. For example, for NANPA regions it will be 990 // contained in the metadata for US. 991 string region_code; 992 GetRegionCodeForCountryCode(country_calling_code, ®ion_code); 993 // Metadata cannot be NULL because the country calling code is valid. 994 const PhoneMetadata* metadata = 995 GetMetadataForRegionOrCallingCode(country_calling_code, region_code); 996 FormatNsnWithCarrier(national_significant_number, *metadata, NATIONAL, 997 carrier_code, formatted_number); 998 MaybeAppendFormattedExtension(number, *metadata, NATIONAL, formatted_number); 999 PrefixNumberWithCountryCallingCode(country_calling_code, NATIONAL, 1000 formatted_number); 1001 } 1002 1003 const PhoneMetadata* PhoneNumberUtil::GetMetadataForRegionOrCallingCode( 1004 int country_calling_code, const string& region_code) const { 1005 return kRegionCodeForNonGeoEntity == region_code 1006 ? GetMetadataForNonGeographicalRegion(country_calling_code) 1007 : GetMetadataForRegion(region_code); 1008 } 1009 1010 void PhoneNumberUtil::FormatNationalNumberWithPreferredCarrierCode( 1011 const PhoneNumber& number, 1012 const string& fallback_carrier_code, 1013 string* formatted_number) const { 1014 FormatNationalNumberWithCarrierCode( 1015 number, 1016 number.has_preferred_domestic_carrier_code() 1017 ? number.preferred_domestic_carrier_code() 1018 : fallback_carrier_code, 1019 formatted_number); 1020 } 1021 1022 void PhoneNumberUtil::FormatNumberForMobileDialing( 1023 const PhoneNumber& number, 1024 const string& calling_from, 1025 bool with_formatting, 1026 string* formatted_number) const { 1027 int country_calling_code = number.country_code(); 1028 if (!HasValidCountryCallingCode(country_calling_code)) { 1029 formatted_number->assign(number.has_raw_input() ? number.raw_input() : ""); 1030 return; 1031 } 1032 1033 formatted_number->assign(""); 1034 // Clear the extension, as that part cannot normally be dialed together with 1035 // the main number. 1036 PhoneNumber number_no_extension(number); 1037 number_no_extension.clear_extension(); 1038 string region_code; 1039 GetRegionCodeForCountryCode(country_calling_code, ®ion_code); 1040 if (calling_from == region_code) { 1041 PhoneNumberType number_type = GetNumberType(number_no_extension); 1042 bool is_fixed_line_or_mobile = 1043 (number_type == FIXED_LINE) || (number_type == MOBILE) || 1044 (number_type == FIXED_LINE_OR_MOBILE); 1045 // Carrier codes may be needed in some countries. We handle this here. 1046 if ((region_code == "CO") && (number_type == FIXED_LINE)) { 1047 FormatNationalNumberWithCarrierCode( 1048 number_no_extension, kColombiaMobileToFixedLinePrefix, 1049 formatted_number); 1050 } else if ((region_code == "BR") && (is_fixed_line_or_mobile)) { 1051 if (number_no_extension.has_preferred_domestic_carrier_code()) { 1052 FormatNationalNumberWithPreferredCarrierCode(number_no_extension, "", 1053 formatted_number); 1054 } else { 1055 // Brazilian fixed line and mobile numbers need to be dialed with a 1056 // carrier code when called within Brazil. Without that, most of the 1057 // carriers won't connect the call. Because of that, we return an empty 1058 // string here. 1059 formatted_number->assign(""); 1060 } 1061 } else if (region_code == "HU") { 1062 // The national format for HU numbers doesn't contain the national prefix, 1063 // because that is how numbers are normally written down. However, the 1064 // national prefix is obligatory when dialing from a mobile phone. As a 1065 // result, we add it back here. 1066 Format(number_no_extension, NATIONAL, formatted_number); 1067 string hu_national_prefix; 1068 GetNddPrefixForRegion(region_code, true /* strip non-digits */, 1069 &hu_national_prefix); 1070 formatted_number->assign( 1071 StrCat(hu_national_prefix, " ", *formatted_number)); 1072 } else { 1073 // For NANPA countries, non-geographical countries, Mexican and Chilean 1074 // fixed line and mobile numbers, we output international format for 1075 // numbers that can be dialed internationally as that always works. 1076 if ((country_calling_code == kNanpaCountryCode || 1077 region_code == kRegionCodeForNonGeoEntity || 1078 // MX fixed line and mobile numbers should always be formatted in 1079 // international format, even when dialed within MX. For national 1080 // format to work, a carrier code needs to be used, and the correct 1081 // carrier code depends on if the caller and callee are from the same 1082 // local area. It is trickier to get that to work correctly than 1083 // using international format, which is tested to work fine on all 1084 // carriers. 1085 // CL fixed line numbers need the national prefix when dialing in the 1086 // national format, but don't have it when used for display. The 1087 // reverse is true for mobile numbers. As a result, we output them in 1088 // the international format to make it work. 1089 ((region_code == "MX" || region_code == "CL") && 1090 is_fixed_line_or_mobile)) && 1091 CanBeInternationallyDialled(number_no_extension)) { 1092 Format(number_no_extension, INTERNATIONAL, formatted_number); 1093 } else { 1094 Format(number_no_extension, NATIONAL, formatted_number); 1095 } 1096 1097 } 1098 } else if (CanBeInternationallyDialled(number_no_extension)) { 1099 with_formatting 1100 ? Format(number_no_extension, INTERNATIONAL, formatted_number) 1101 : Format(number_no_extension, E164, formatted_number); 1102 return; 1103 } 1104 if (!with_formatting) { 1105 NormalizeHelper(reg_exps_->diallable_char_mappings_, 1106 true /* remove non matches */, formatted_number); 1107 } 1108 } 1109 1110 void PhoneNumberUtil::FormatOutOfCountryCallingNumber( 1111 const PhoneNumber& number, 1112 const string& calling_from, 1113 string* formatted_number) const { 1114 DCHECK(formatted_number); 1115 if (!IsValidRegionCode(calling_from)) { 1116 LOG(WARNING) << "Trying to format number from invalid region " 1117 << calling_from 1118 << ". International formatting applied."; 1119 Format(number, INTERNATIONAL, formatted_number); 1120 return; 1121 } 1122 int country_code = number.country_code(); 1123 string national_significant_number; 1124 GetNationalSignificantNumber(number, &national_significant_number); 1125 if (!HasValidCountryCallingCode(country_code)) { 1126 formatted_number->assign(national_significant_number); 1127 return; 1128 } 1129 if (country_code == kNanpaCountryCode) { 1130 if (IsNANPACountry(calling_from)) { 1131 // For NANPA regions, return the national format for these regions but 1132 // prefix it with the country calling code. 1133 Format(number, NATIONAL, formatted_number); 1134 formatted_number->insert(0, StrCat(country_code, " ")); 1135 return; 1136 } 1137 } else if (country_code == GetCountryCodeForValidRegion(calling_from)) { 1138 // If neither region is a NANPA region, then we check to see if the 1139 // country calling code of the number and the country calling code of the 1140 // region we are calling from are the same. 1141 // For regions that share a country calling code, the country calling code 1142 // need not be dialled. This also applies when dialling within a region, so 1143 // this if clause covers both these cases. 1144 // Technically this is the case for dialling from la Runion to other 1145 // overseas departments of France (French Guiana, Martinique, Guadeloupe), 1146 // but not vice versa - so we don't cover this edge case for now and for 1147 // those cases return the version including country calling code. 1148 // Details here: 1149 // http://www.petitfute.com/voyage/225-info-pratiques-reunion 1150 Format(number, NATIONAL, formatted_number); 1151 return; 1152 } 1153 // Metadata cannot be NULL because we checked 'IsValidRegionCode()' above. 1154 const PhoneMetadata* metadata_calling_from = 1155 GetMetadataForRegion(calling_from); 1156 const string& international_prefix = 1157 metadata_calling_from->international_prefix(); 1158 1159 // For regions that have multiple international prefixes, the international 1160 // format of the number is returned, unless there is a preferred international 1161 // prefix. 1162 const string international_prefix_for_formatting( 1163 reg_exps_->unique_international_prefix_->FullMatch(international_prefix) 1164 ? international_prefix 1165 : metadata_calling_from->preferred_international_prefix()); 1166 1167 string region_code; 1168 GetRegionCodeForCountryCode(country_code, ®ion_code); 1169 // Metadata cannot be NULL because the country_code is valid. 1170 const PhoneMetadata* metadata_for_region = 1171 GetMetadataForRegionOrCallingCode(country_code, region_code); 1172 FormatNsn(national_significant_number, *metadata_for_region, INTERNATIONAL, 1173 formatted_number); 1174 MaybeAppendFormattedExtension(number, *metadata_for_region, INTERNATIONAL, 1175 formatted_number); 1176 if (!international_prefix_for_formatting.empty()) { 1177 formatted_number->insert( 1178 0, StrCat(international_prefix_for_formatting, " ", country_code, " ")); 1179 } else { 1180 PrefixNumberWithCountryCallingCode(country_code, INTERNATIONAL, 1181 formatted_number); 1182 } 1183 } 1184 1185 void PhoneNumberUtil::FormatInOriginalFormat(const PhoneNumber& number, 1186 const string& region_calling_from, 1187 string* formatted_number) const { 1188 DCHECK(formatted_number); 1189 1190 if (number.has_raw_input() && 1191 (HasUnexpectedItalianLeadingZero(number) || 1192 !HasFormattingPatternForNumber(number))) { 1193 // We check if we have the formatting pattern because without that, we might 1194 // format the number as a group without national prefix. 1195 formatted_number->assign(number.raw_input()); 1196 return; 1197 } 1198 if (!number.has_country_code_source()) { 1199 Format(number, NATIONAL, formatted_number); 1200 return; 1201 } 1202 switch (number.country_code_source()) { 1203 case PhoneNumber::FROM_NUMBER_WITH_PLUS_SIGN: 1204 Format(number, INTERNATIONAL, formatted_number); 1205 break; 1206 case PhoneNumber::FROM_NUMBER_WITH_IDD: 1207 FormatOutOfCountryCallingNumber(number, region_calling_from, 1208 formatted_number); 1209 break; 1210 case PhoneNumber::FROM_NUMBER_WITHOUT_PLUS_SIGN: 1211 Format(number, INTERNATIONAL, formatted_number); 1212 formatted_number->erase(formatted_number->begin()); 1213 break; 1214 case PhoneNumber::FROM_DEFAULT_COUNTRY: 1215 // Fall-through to default case. 1216 default: 1217 string region_code; 1218 GetRegionCodeForCountryCode(number.country_code(), ®ion_code); 1219 // We strip non-digits from the NDD here, and from the raw input later, so 1220 // that we can compare them easily. 1221 string national_prefix; 1222 GetNddPrefixForRegion(region_code, true /* strip non-digits */, 1223 &national_prefix); 1224 if (national_prefix.empty()) { 1225 // If the region doesn't have a national prefix at all, we can safely 1226 // return the national format without worrying about a national prefix 1227 // being added. 1228 Format(number, NATIONAL, formatted_number); 1229 break; 1230 } 1231 // Otherwise, we check if the original number was entered with a national 1232 // prefix. 1233 if (RawInputContainsNationalPrefix(number.raw_input(), national_prefix, 1234 region_code)) { 1235 // If so, we can safely return the national format. 1236 Format(number, NATIONAL, formatted_number); 1237 break; 1238 } 1239 // Metadata cannot be NULL here because GetNddPrefixForRegion() (above) 1240 // leaves the prefix empty if there is no metadata for the region. 1241 const PhoneMetadata* metadata = GetMetadataForRegion(region_code); 1242 string national_number; 1243 GetNationalSignificantNumber(number, &national_number); 1244 // This shouldn't be NULL, because we have checked that above with 1245 // HasFormattingPatternForNumber. 1246 const NumberFormat* format_rule = 1247 ChooseFormattingPatternForNumber(metadata->number_format(), 1248 national_number); 1249 // The format rule could still be NULL here if the national number was 0 1250 // and there was no raw input (this should not be possible for numbers 1251 // generated by the phonenumber library as they would also not have a 1252 // country calling code and we would have exited earlier). 1253 if (!format_rule) { 1254 Format(number, NATIONAL, formatted_number); 1255 break; 1256 } 1257 // When the format we apply to this number doesn't contain national 1258 // prefix, we can just return the national format. 1259 // TODO: Refactor the code below with the code in 1260 // IsNationalPrefixPresentIfRequired. 1261 string candidate_national_prefix_rule( 1262 format_rule->national_prefix_formatting_rule()); 1263 // We assume that the first-group symbol will never be _before_ the 1264 // national prefix. 1265 if (!candidate_national_prefix_rule.empty()) { 1266 candidate_national_prefix_rule.erase( 1267 candidate_national_prefix_rule.find("$1")); 1268 NormalizeDigitsOnly(&candidate_national_prefix_rule); 1269 } 1270 if (candidate_national_prefix_rule.empty()) { 1271 // National prefix not used when formatting this number. 1272 Format(number, NATIONAL, formatted_number); 1273 break; 1274 } 1275 // Otherwise, we need to remove the national prefix from our output. 1276 RepeatedPtrField<NumberFormat> number_formats; 1277 NumberFormat* number_format = number_formats.Add(); 1278 number_format->MergeFrom(*format_rule); 1279 number_format->clear_national_prefix_formatting_rule(); 1280 FormatByPattern(number, NATIONAL, number_formats, formatted_number); 1281 break; 1282 } 1283 // If no digit is inserted/removed/modified as a result of our formatting, we 1284 // return the formatted phone number; otherwise we return the raw input the 1285 // user entered. 1286 if (!formatted_number->empty() && !number.raw_input().empty()) { 1287 string normalized_formatted_number(*formatted_number); 1288 NormalizeHelper(reg_exps_->diallable_char_mappings_, 1289 true /* remove non matches */, 1290 &normalized_formatted_number); 1291 string normalized_raw_input(number.raw_input()); 1292 NormalizeHelper(reg_exps_->diallable_char_mappings_, 1293 true /* remove non matches */, &normalized_raw_input); 1294 if (normalized_formatted_number != normalized_raw_input) { 1295 formatted_number->assign(number.raw_input()); 1296 } 1297 } 1298 } 1299 1300 // Check if raw_input, which is assumed to be in the national format, has a 1301 // national prefix. The national prefix is assumed to be in digits-only form. 1302 bool PhoneNumberUtil::RawInputContainsNationalPrefix( 1303 const string& raw_input, 1304 const string& national_prefix, 1305 const string& region_code) const { 1306 string normalized_national_number(raw_input); 1307 NormalizeDigitsOnly(&normalized_national_number); 1308 if (HasPrefixString(normalized_national_number, national_prefix)) { 1309 // Some Japanese numbers (e.g. 00777123) might be mistaken to contain 1310 // the national prefix when written without it (e.g. 0777123) if we just 1311 // do prefix matching. To tackle that, we check the validity of the 1312 // number if the assumed national prefix is removed (777123 won't be 1313 // valid in Japan). 1314 PhoneNumber number_without_national_prefix; 1315 if (Parse(normalized_national_number.substr(national_prefix.length()), 1316 region_code, &number_without_national_prefix) 1317 == NO_PARSING_ERROR) { 1318 return IsValidNumber(number_without_national_prefix); 1319 } 1320 } 1321 return false; 1322 } 1323 1324 bool PhoneNumberUtil::HasUnexpectedItalianLeadingZero( 1325 const PhoneNumber& number) const { 1326 return number.has_italian_leading_zero() && 1327 !IsLeadingZeroPossible(number.country_code()); 1328 } 1329 1330 bool PhoneNumberUtil::HasFormattingPatternForNumber( 1331 const PhoneNumber& number) const { 1332 int country_calling_code = number.country_code(); 1333 string region_code; 1334 GetRegionCodeForCountryCode(country_calling_code, ®ion_code); 1335 const PhoneMetadata* metadata = 1336 GetMetadataForRegionOrCallingCode(country_calling_code, region_code); 1337 if (!metadata) { 1338 return false; 1339 } 1340 string national_number; 1341 GetNationalSignificantNumber(number, &national_number); 1342 const NumberFormat* format_rule = 1343 ChooseFormattingPatternForNumber(metadata->number_format(), 1344 national_number); 1345 return format_rule; 1346 } 1347 1348 void PhoneNumberUtil::FormatOutOfCountryKeepingAlphaChars( 1349 const PhoneNumber& number, 1350 const string& calling_from, 1351 string* formatted_number) const { 1352 // If there is no raw input, then we can't keep alpha characters because there 1353 // aren't any. In this case, we return FormatOutOfCountryCallingNumber. 1354 if (number.raw_input().empty()) { 1355 FormatOutOfCountryCallingNumber(number, calling_from, formatted_number); 1356 return; 1357 } 1358 int country_code = number.country_code(); 1359 if (!HasValidCountryCallingCode(country_code)) { 1360 formatted_number->assign(number.raw_input()); 1361 return; 1362 } 1363 // Strip any prefix such as country calling code, IDD, that was present. We do 1364 // this by comparing the number in raw_input with the parsed number. 1365 string raw_input_copy(number.raw_input()); 1366 // Normalize punctuation. We retain number grouping symbols such as " " only. 1367 NormalizeHelper(reg_exps_->all_plus_number_grouping_symbols_, true, 1368 &raw_input_copy); 1369 // Now we trim everything before the first three digits in the parsed number. 1370 // We choose three because all valid alpha numbers have 3 digits at the start 1371 // - if it does not, then we don't trim anything at all. Similarly, if the 1372 // national number was less than three digits, we don't trim anything at all. 1373 string national_number; 1374 GetNationalSignificantNumber(number, &national_number); 1375 if (national_number.length() > 3) { 1376 size_t first_national_number_digit = 1377 raw_input_copy.find(national_number.substr(0, 3)); 1378 if (first_national_number_digit != string::npos) { 1379 raw_input_copy = raw_input_copy.substr(first_national_number_digit); 1380 } 1381 } 1382 const PhoneMetadata* metadata = GetMetadataForRegion(calling_from); 1383 if (country_code == kNanpaCountryCode) { 1384 if (IsNANPACountry(calling_from)) { 1385 StrAppend(formatted_number, country_code, " ", raw_input_copy); 1386 return; 1387 } 1388 } else if (metadata && 1389 country_code == GetCountryCodeForValidRegion(calling_from)) { 1390 const NumberFormat* formatting_pattern = 1391 ChooseFormattingPatternForNumber(metadata->number_format(), 1392 national_number); 1393 if (!formatting_pattern) { 1394 // If no pattern above is matched, we format the original input. 1395 formatted_number->assign(raw_input_copy); 1396 return; 1397 } 1398 NumberFormat new_format; 1399 new_format.MergeFrom(*formatting_pattern); 1400 // The first group is the first group of digits that the user wrote 1401 // together. 1402 new_format.set_pattern("(\\d+)(.*)"); 1403 // Here we just concatenate them back together after the national prefix 1404 // has been fixed. 1405 new_format.set_format("$1$2"); 1406 // Now we format using this pattern instead of the default pattern, but 1407 // with the national prefix prefixed if necessary. 1408 // This will not work in the cases where the pattern (and not the 1409 // leading digits) decide whether a national prefix needs to be used, since 1410 // we have overridden the pattern to match anything, but that is not the 1411 // case in the metadata to date. 1412 FormatNsnUsingPattern(raw_input_copy, new_format, NATIONAL, 1413 formatted_number); 1414 return; 1415 } 1416 1417 string international_prefix_for_formatting; 1418 // If an unsupported region-calling-from is entered, or a country with 1419 // multiple international prefixes, the international format of the number is 1420 // returned, unless there is a preferred international prefix. 1421 if (metadata) { 1422 const string& international_prefix = metadata->international_prefix(); 1423 international_prefix_for_formatting = 1424 reg_exps_->unique_international_prefix_->FullMatch(international_prefix) 1425 ? international_prefix 1426 : metadata->preferred_international_prefix(); 1427 } 1428 if (!international_prefix_for_formatting.empty()) { 1429 StrAppend(formatted_number, international_prefix_for_formatting, " ", 1430 country_code, " ", raw_input_copy); 1431 } else { 1432 // Invalid region entered as country-calling-from (so no metadata was found 1433 // for it) or the region chosen has multiple international dialling 1434 // prefixes. 1435 LOG(WARNING) << "Trying to format number from invalid region " 1436 << calling_from 1437 << ". International formatting applied."; 1438 formatted_number->assign(raw_input_copy); 1439 PrefixNumberWithCountryCallingCode(country_code, INTERNATIONAL, 1440 formatted_number); 1441 } 1442 } 1443 1444 const NumberFormat* PhoneNumberUtil::ChooseFormattingPatternForNumber( 1445 const RepeatedPtrField<NumberFormat>& available_formats, 1446 const string& national_number) const { 1447 for (RepeatedPtrField<NumberFormat>::const_iterator 1448 it = available_formats.begin(); it != available_formats.end(); ++it) { 1449 int size = it->leading_digits_pattern_size(); 1450 if (size > 0) { 1451 const scoped_ptr<RegExpInput> number_copy( 1452 reg_exps_->regexp_factory_->CreateInput(national_number)); 1453 // We always use the last leading_digits_pattern, as it is the most 1454 // detailed. 1455 if (!reg_exps_->regexp_cache_->GetRegExp( 1456 it->leading_digits_pattern(size - 1)).Consume( 1457 number_copy.get())) { 1458 continue; 1459 } 1460 } 1461 const RegExp& pattern_to_match( 1462 reg_exps_->regexp_cache_->GetRegExp(it->pattern())); 1463 if (pattern_to_match.FullMatch(national_number)) { 1464 return &(*it); 1465 } 1466 } 1467 return NULL; 1468 } 1469 1470 // Note that carrier_code is optional - if an empty string, no carrier code 1471 // replacement will take place. 1472 void PhoneNumberUtil::FormatNsnUsingPatternWithCarrier( 1473 const string& national_number, 1474 const NumberFormat& formatting_pattern, 1475 PhoneNumberUtil::PhoneNumberFormat number_format, 1476 const string& carrier_code, 1477 string* formatted_number) const { 1478 DCHECK(formatted_number); 1479 string number_format_rule(formatting_pattern.format()); 1480 if (number_format == PhoneNumberUtil::NATIONAL && 1481 carrier_code.length() > 0 && 1482 formatting_pattern.domestic_carrier_code_formatting_rule().length() > 0) { 1483 // Replace the $CC in the formatting rule with the desired carrier code. 1484 string carrier_code_formatting_rule = 1485 formatting_pattern.domestic_carrier_code_formatting_rule(); 1486 reg_exps_->carrier_code_pattern_->Replace(&carrier_code_formatting_rule, 1487 carrier_code); 1488 reg_exps_->first_group_capturing_pattern_-> 1489 Replace(&number_format_rule, carrier_code_formatting_rule); 1490 } else { 1491 // Use the national prefix formatting rule instead. 1492 string national_prefix_formatting_rule = 1493 formatting_pattern.national_prefix_formatting_rule(); 1494 if (number_format == PhoneNumberUtil::NATIONAL && 1495 national_prefix_formatting_rule.length() > 0) { 1496 // Apply the national_prefix_formatting_rule as the formatting_pattern 1497 // contains only information on how the national significant number 1498 // should be formatted at this point. 1499 reg_exps_->first_group_capturing_pattern_->Replace( 1500 &number_format_rule, national_prefix_formatting_rule); 1501 } 1502 } 1503 formatted_number->assign(national_number); 1504 1505 const RegExp& pattern_to_match( 1506 reg_exps_->regexp_cache_->GetRegExp(formatting_pattern.pattern())); 1507 pattern_to_match.GlobalReplace(formatted_number, number_format_rule); 1508 1509 if (number_format == RFC3966) { 1510 // First consume any leading punctuation, if any was present. 1511 const scoped_ptr<RegExpInput> number( 1512 reg_exps_->regexp_factory_->CreateInput(*formatted_number)); 1513 if (reg_exps_->separator_pattern_->Consume(number.get())) { 1514 formatted_number->assign(number->ToString()); 1515 } 1516 // Then replace all separators with a "-". 1517 reg_exps_->separator_pattern_->GlobalReplace(formatted_number, "-"); 1518 } 1519 } 1520 1521 // Simple wrapper of FormatNsnUsingPatternWithCarrier for the common case of 1522 // no carrier code. 1523 void PhoneNumberUtil::FormatNsnUsingPattern( 1524 const string& national_number, 1525 const NumberFormat& formatting_pattern, 1526 PhoneNumberUtil::PhoneNumberFormat number_format, 1527 string* formatted_number) const { 1528 DCHECK(formatted_number); 1529 FormatNsnUsingPatternWithCarrier(national_number, formatting_pattern, 1530 number_format, "", formatted_number); 1531 } 1532 1533 void PhoneNumberUtil::FormatNsn(const string& number, 1534 const PhoneMetadata& metadata, 1535 PhoneNumberFormat number_format, 1536 string* formatted_number) const { 1537 DCHECK(formatted_number); 1538 FormatNsnWithCarrier(number, metadata, number_format, "", formatted_number); 1539 } 1540 1541 // Note in some regions, the national number can be written in two completely 1542 // different ways depending on whether it forms part of the NATIONAL format or 1543 // INTERNATIONAL format. The number_format parameter here is used to specify 1544 // which format to use for those cases. If a carrier_code is specified, this 1545 // will be inserted into the formatted string to replace $CC. 1546 void PhoneNumberUtil::FormatNsnWithCarrier(const string& number, 1547 const PhoneMetadata& metadata, 1548 PhoneNumberFormat number_format, 1549 const string& carrier_code, 1550 string* formatted_number) const { 1551 DCHECK(formatted_number); 1552 // When the intl_number_formats exists, we use that to format national number 1553 // for the INTERNATIONAL format instead of using the number_formats. 1554 const RepeatedPtrField<NumberFormat> available_formats = 1555 (metadata.intl_number_format_size() == 0 || number_format == NATIONAL) 1556 ? metadata.number_format() 1557 : metadata.intl_number_format(); 1558 const NumberFormat* formatting_pattern = 1559 ChooseFormattingPatternForNumber(available_formats, number); 1560 if (!formatting_pattern) { 1561 formatted_number->assign(number); 1562 } else { 1563 FormatNsnUsingPatternWithCarrier(number, *formatting_pattern, number_format, 1564 carrier_code, formatted_number); 1565 } 1566 } 1567 1568 // Appends the formatted extension of a phone number, if the phone number had an 1569 // extension specified. 1570 void PhoneNumberUtil::MaybeAppendFormattedExtension( 1571 const PhoneNumber& number, 1572 const PhoneMetadata& metadata, 1573 PhoneNumberFormat number_format, 1574 string* formatted_number) const { 1575 DCHECK(formatted_number); 1576 if (number.has_extension() && number.extension().length() > 0) { 1577 if (number_format == RFC3966) { 1578 StrAppend(formatted_number, kRfc3966ExtnPrefix, number.extension()); 1579 } else { 1580 if (metadata.has_preferred_extn_prefix()) { 1581 StrAppend(formatted_number, metadata.preferred_extn_prefix(), 1582 number.extension()); 1583 } else { 1584 StrAppend(formatted_number, kDefaultExtnPrefix, number.extension()); 1585 } 1586 } 1587 } 1588 } 1589 1590 bool PhoneNumberUtil::IsNANPACountry(const string& region_code) const { 1591 return nanpa_regions_->find(region_code) != nanpa_regions_->end(); 1592 } 1593 1594 // Returns the region codes that matches the specific country calling code. In 1595 // the case of no region code being found, region_codes will be left empty. 1596 void PhoneNumberUtil::GetRegionCodesForCountryCallingCode( 1597 int country_calling_code, 1598 list<string>* region_codes) const { 1599 DCHECK(region_codes); 1600 // Create a IntRegionsPair with the country_code passed in, and use it to 1601 // locate the pair with the same country_code in the sorted vector. 1602 IntRegionsPair target_pair; 1603 target_pair.first = country_calling_code; 1604 typedef vector<IntRegionsPair>::const_iterator ConstIterator; 1605 pair<ConstIterator, ConstIterator> range = equal_range( 1606 country_calling_code_to_region_code_map_->begin(), 1607 country_calling_code_to_region_code_map_->end(), 1608 target_pair, OrderByFirst()); 1609 if (range.first != range.second) { 1610 region_codes->insert(region_codes->begin(), 1611 range.first->second->begin(), 1612 range.first->second->end()); 1613 } 1614 } 1615 1616 // Returns the region code that matches the specific country calling code. In 1617 // the case of no region code being found, the unknown region code will be 1618 // returned. 1619 void PhoneNumberUtil::GetRegionCodeForCountryCode( 1620 int country_calling_code, 1621 string* region_code) const { 1622 DCHECK(region_code); 1623 list<string> region_codes; 1624 1625 GetRegionCodesForCountryCallingCode(country_calling_code, ®ion_codes); 1626 *region_code = (region_codes.size() > 0) ? 1627 region_codes.front() : RegionCode::GetUnknown(); 1628 } 1629 1630 void PhoneNumberUtil::GetRegionCodeForNumber(const PhoneNumber& number, 1631 string* region_code) const { 1632 DCHECK(region_code); 1633 int country_calling_code = number.country_code(); 1634 list<string> region_codes; 1635 GetRegionCodesForCountryCallingCode(country_calling_code, ®ion_codes); 1636 if (region_codes.size() == 0) { 1637 string number_string; 1638 GetNationalSignificantNumber(number, &number_string); 1639 LOG(WARNING) << "Missing/invalid country calling code (" 1640 << country_calling_code 1641 << ") for number " << number_string; 1642 *region_code = RegionCode::GetUnknown(); 1643 return; 1644 } 1645 if (region_codes.size() == 1) { 1646 *region_code = region_codes.front(); 1647 } else { 1648 GetRegionCodeForNumberFromRegionList(number, region_codes, region_code); 1649 } 1650 } 1651 1652 void PhoneNumberUtil::GetRegionCodeForNumberFromRegionList( 1653 const PhoneNumber& number, const list<string>& region_codes, 1654 string* region_code) const { 1655 DCHECK(region_code); 1656 string national_number; 1657 GetNationalSignificantNumber(number, &national_number); 1658 for (list<string>::const_iterator it = region_codes.begin(); 1659 it != region_codes.end(); ++it) { 1660 // Metadata cannot be NULL because the region codes come from the country 1661 // calling code map. 1662 const PhoneMetadata* metadata = GetMetadataForRegion(*it); 1663 if (metadata->has_leading_digits()) { 1664 const scoped_ptr<RegExpInput> number( 1665 reg_exps_->regexp_factory_->CreateInput(national_number)); 1666 if (reg_exps_->regexp_cache_-> 1667 GetRegExp(metadata->leading_digits()).Consume(number.get())) { 1668 *region_code = *it; 1669 return; 1670 } 1671 } else if (GetNumberTypeHelper(national_number, *metadata, 1672 reg_exps_->regexp_cache_.get()) != UNKNOWN) { 1673 *region_code = *it; 1674 return; 1675 } 1676 } 1677 *region_code = RegionCode::GetUnknown(); 1678 } 1679 1680 int PhoneNumberUtil::GetCountryCodeForRegion(const string& region_code) const { 1681 if (!IsValidRegionCode(region_code)) { 1682 LOG(WARNING) << "Invalid or unknown region code (" << region_code 1683 << ") provided."; 1684 return 0; 1685 } 1686 return GetCountryCodeForValidRegion(region_code); 1687 } 1688 1689 int PhoneNumberUtil::GetCountryCodeForValidRegion( 1690 const string& region_code) const { 1691 const PhoneMetadata* metadata = GetMetadataForRegion(region_code); 1692 return metadata->country_code(); 1693 } 1694 1695 // Gets a valid fixed-line number for the specified region_code. Returns false 1696 // if the region was unknown or 001 (representing non-geographical regions), or 1697 // if no number exists. 1698 bool PhoneNumberUtil::GetExampleNumber(const string& region_code, 1699 PhoneNumber* number) const { 1700 DCHECK(number); 1701 return GetExampleNumberForType(region_code, FIXED_LINE, number); 1702 } 1703 1704 // Gets a valid number for the specified region_code and type. Returns false if 1705 // the country was unknown or 001 (representing non-geographical regions), or if 1706 // no number exists. 1707 bool PhoneNumberUtil::GetExampleNumberForType( 1708 const string& region_code, 1709 PhoneNumberUtil::PhoneNumberType type, 1710 PhoneNumber* number) const { 1711 DCHECK(number); 1712 if (!IsValidRegionCode(region_code)) { 1713 LOG(WARNING) << "Invalid or unknown region code (" << region_code 1714 << ") provided."; 1715 return false; 1716 } 1717 const PhoneMetadata* region_metadata = GetMetadataForRegion(region_code); 1718 const PhoneNumberDesc* desc = GetNumberDescByType(*region_metadata, type); 1719 if (desc && desc->has_example_number()) { 1720 ErrorType success = Parse(desc->example_number(), region_code, number); 1721 if (success == NO_PARSING_ERROR) { 1722 return true; 1723 } else { 1724 LOG(ERROR) << "Error parsing example number (" 1725 << static_cast<int>(success) << ")"; 1726 } 1727 } 1728 return false; 1729 } 1730 1731 bool PhoneNumberUtil::GetExampleNumberForNonGeoEntity( 1732 int country_calling_code, PhoneNumber* number) const { 1733 DCHECK(number); 1734 const PhoneMetadata* metadata = 1735 GetMetadataForNonGeographicalRegion(country_calling_code); 1736 if (metadata) { 1737 const PhoneNumberDesc& desc = metadata->general_desc(); 1738 if (desc.has_example_number()) { 1739 ErrorType success = Parse(StrCat(kPlusSign, 1740 SimpleItoa(country_calling_code), 1741 desc.example_number()), 1742 RegionCode::ZZ(), number); 1743 if (success == NO_PARSING_ERROR) { 1744 return true; 1745 } else { 1746 LOG(ERROR) << "Error parsing example number (" 1747 << static_cast<int>(success) << ")"; 1748 } 1749 } 1750 } else { 1751 LOG(WARNING) << "Invalid or unknown country calling code provided: " 1752 << country_calling_code; 1753 } 1754 return false; 1755 } 1756 1757 PhoneNumberUtil::ErrorType PhoneNumberUtil::Parse(const string& number_to_parse, 1758 const string& default_region, 1759 PhoneNumber* number) const { 1760 DCHECK(number); 1761 return ParseHelper(number_to_parse, default_region, false, true, number); 1762 } 1763 1764 PhoneNumberUtil::ErrorType PhoneNumberUtil::ParseAndKeepRawInput( 1765 const string& number_to_parse, 1766 const string& default_region, 1767 PhoneNumber* number) const { 1768 DCHECK(number); 1769 return ParseHelper(number_to_parse, default_region, true, true, number); 1770 } 1771 1772 // Checks to see that the region code used is valid, or if it is not valid, that 1773 // the number to parse starts with a + symbol so that we can attempt to infer 1774 // the country from the number. Returns false if it cannot use the region 1775 // provided and the region cannot be inferred. 1776 bool PhoneNumberUtil::CheckRegionForParsing( 1777 const string& number_to_parse, 1778 const string& default_region) const { 1779 if (!IsValidRegionCode(default_region) && !number_to_parse.empty()) { 1780 const scoped_ptr<RegExpInput> number( 1781 reg_exps_->regexp_factory_->CreateInput(number_to_parse)); 1782 if (!reg_exps_->plus_chars_pattern_->Consume(number.get())) { 1783 return false; 1784 } 1785 } 1786 return true; 1787 } 1788 1789 // Converts number_to_parse to a form that we can parse and write it to 1790 // national_number if it is written in RFC3966; otherwise extract a possible 1791 // number out of it and write to national_number. 1792 void PhoneNumberUtil::BuildNationalNumberForParsing( 1793 const string& number_to_parse, string* national_number) const { 1794 size_t index_of_phone_context = number_to_parse.find(kRfc3966PhoneContext); 1795 if (index_of_phone_context != string::npos) { 1796 int phone_context_start = 1797 index_of_phone_context + strlen(kRfc3966PhoneContext); 1798 // If the phone context contains a phone number prefix, we need to capture 1799 // it, whereas domains will be ignored. 1800 if (number_to_parse.at(phone_context_start) == kPlusSign[0]) { 1801 // Additional parameters might follow the phone context. If so, we will 1802 // remove them here because the parameters after phone context are not 1803 // important for parsing the phone number. 1804 size_t phone_context_end = number_to_parse.find(';', phone_context_start); 1805 if (phone_context_end != string::npos) { 1806 StrAppend( 1807 national_number, number_to_parse.substr( 1808 phone_context_start, phone_context_end - phone_context_start)); 1809 } else { 1810 StrAppend(national_number, number_to_parse.substr(phone_context_start)); 1811 } 1812 } 1813 1814 // Now append everything between the "tel:" prefix and the phone-context. 1815 // This should include the national number, an optional extension or 1816 // isdn-subaddress component. 1817 int end_of_rfc_prefix = 1818 number_to_parse.find(kRfc3966Prefix) + strlen(kRfc3966Prefix); 1819 StrAppend( 1820 national_number, 1821 number_to_parse.substr(end_of_rfc_prefix, 1822 index_of_phone_context - end_of_rfc_prefix)); 1823 } else { 1824 // Extract a possible number from the string passed in (this strips leading 1825 // characters that could not be the start of a phone number.) 1826 ExtractPossibleNumber(number_to_parse, national_number); 1827 } 1828 1829 // Delete the isdn-subaddress and everything after it if it is present. Note 1830 // extension won't appear at the same time with isdn-subaddress according to 1831 // paragraph 5.3 of the RFC3966 spec. 1832 size_t index_of_isdn = national_number->find(kRfc3966IsdnSubaddress); 1833 if (index_of_isdn != string::npos) { 1834 national_number->erase(index_of_isdn); 1835 } 1836 // If both phone context and isdn-subaddress are absent but other parameters 1837 // are present, the parameters are left in nationalNumber. This is because 1838 // we are concerned about deleting content from a potential number string 1839 // when there is no strong evidence that the number is actually written in 1840 // RFC3966. 1841 } 1842 1843 PhoneNumberUtil::ErrorType PhoneNumberUtil::ParseHelper( 1844 const string& number_to_parse, 1845 const string& default_region, 1846 bool keep_raw_input, 1847 bool check_region, 1848 PhoneNumber* phone_number) const { 1849 DCHECK(phone_number); 1850 1851 string national_number; 1852 BuildNationalNumberForParsing(number_to_parse, &national_number); 1853 1854 if (!IsViablePhoneNumber(national_number)) { 1855 VLOG(2) << "The string supplied did not seem to be a phone number."; 1856 return NOT_A_NUMBER; 1857 } 1858 1859 if (check_region && 1860 !CheckRegionForParsing(national_number, default_region)) { 1861 VLOG(1) << "Missing or invalid default country."; 1862 return INVALID_COUNTRY_CODE_ERROR; 1863 } 1864 PhoneNumber temp_number; 1865 if (keep_raw_input) { 1866 temp_number.set_raw_input(number_to_parse); 1867 } 1868 // Attempt to parse extension first, since it doesn't require country-specific 1869 // data and we want to have the non-normalised number here. 1870 string extension; 1871 MaybeStripExtension(&national_number, &extension); 1872 if (!extension.empty()) { 1873 temp_number.set_extension(extension); 1874 } 1875 const PhoneMetadata* country_metadata = GetMetadataForRegion(default_region); 1876 // Check to see if the number is given in international format so we know 1877 // whether this number is from the default country or not. 1878 string normalized_national_number(national_number); 1879 ErrorType country_code_error = 1880 MaybeExtractCountryCode(country_metadata, keep_raw_input, 1881 &normalized_national_number, &temp_number); 1882 if (country_code_error != NO_PARSING_ERROR) { 1883 const scoped_ptr<RegExpInput> number_string_piece( 1884 reg_exps_->regexp_factory_->CreateInput(national_number)); 1885 if ((country_code_error == INVALID_COUNTRY_CODE_ERROR) && 1886 (reg_exps_->plus_chars_pattern_->Consume(number_string_piece.get()))) { 1887 normalized_national_number.assign(number_string_piece->ToString()); 1888 // Strip the plus-char, and try again. 1889 MaybeExtractCountryCode(country_metadata, 1890 keep_raw_input, 1891 &normalized_national_number, 1892 &temp_number); 1893 if (temp_number.country_code() == 0) { 1894 return INVALID_COUNTRY_CODE_ERROR; 1895 } 1896 } else { 1897 return country_code_error; 1898 } 1899 } 1900 int country_code = temp_number.country_code(); 1901 if (country_code != 0) { 1902 string phone_number_region; 1903 GetRegionCodeForCountryCode(country_code, &phone_number_region); 1904 if (phone_number_region != default_region) { 1905 country_metadata = 1906 GetMetadataForRegionOrCallingCode(country_code, phone_number_region); 1907 } 1908 } else if (country_metadata) { 1909 // If no extracted country calling code, use the region supplied instead. 1910 // Note that the national number was already normalized by 1911 // MaybeExtractCountryCode. 1912 country_code = country_metadata->country_code(); 1913 } 1914 if (normalized_national_number.length() < kMinLengthForNsn) { 1915 VLOG(2) << "The string supplied is too short to be a phone number."; 1916 return TOO_SHORT_NSN; 1917 } 1918 if (country_metadata) { 1919 string* carrier_code = keep_raw_input ? 1920 temp_number.mutable_preferred_domestic_carrier_code() : NULL; 1921 MaybeStripNationalPrefixAndCarrierCode(*country_metadata, 1922 &normalized_national_number, 1923 carrier_code); 1924 } 1925 size_t normalized_national_number_length = 1926 normalized_national_number.length(); 1927 if (normalized_national_number_length < kMinLengthForNsn) { 1928 VLOG(2) << "The string supplied is too short to be a phone number."; 1929 return TOO_SHORT_NSN; 1930 } 1931 if (normalized_national_number_length > kMaxLengthForNsn) { 1932 VLOG(2) << "The string supplied is too long to be a phone number."; 1933 return TOO_LONG_NSN; 1934 } 1935 temp_number.set_country_code(country_code); 1936 if (normalized_national_number[0] == '0') { 1937 temp_number.set_italian_leading_zero(true); 1938 } 1939 uint64 number_as_int; 1940 safe_strtou64(normalized_national_number, &number_as_int); 1941 temp_number.set_national_number(number_as_int); 1942 phone_number->MergeFrom(temp_number); 1943 return NO_PARSING_ERROR; 1944 } 1945 1946 // Attempts to extract a possible number from the string passed in. This 1947 // currently strips all leading characters that could not be used to start a 1948 // phone number. Characters that can be used to start a phone number are 1949 // defined in the valid_start_char_pattern. If none of these characters are 1950 // found in the number passed in, an empty string is returned. This function 1951 // also attempts to strip off any alternative extensions or endings if two or 1952 // more are present, such as in the case of: (530) 583-6985 x302/x2303. The 1953 // second extension here makes this actually two phone numbers, (530) 583-6985 1954 // x302 and (530) 583-6985 x2303. We remove the second extension so that the 1955 // first number is parsed correctly. 1956 void PhoneNumberUtil::ExtractPossibleNumber(const string& number, 1957 string* extracted_number) const { 1958 DCHECK(extracted_number); 1959 1960 UnicodeText number_as_unicode; 1961 number_as_unicode.PointToUTF8(number.data(), number.size()); 1962 char current_char[5]; 1963 int len; 1964 UnicodeText::const_iterator it; 1965 for (it = number_as_unicode.begin(); it != number_as_unicode.end(); ++it) { 1966 len = it.get_utf8(current_char); 1967 current_char[len] = '\0'; 1968 if (reg_exps_->valid_start_char_pattern_->FullMatch(current_char)) { 1969 break; 1970 } 1971 } 1972 1973 if (it == number_as_unicode.end()) { 1974 // No valid start character was found. extracted_number should be set to 1975 // empty string. 1976 extracted_number->assign(""); 1977 return; 1978 } 1979 1980 extracted_number->assign( 1981 UnicodeText::UTF8Substring(it, number_as_unicode.end())); 1982 TrimUnwantedEndChars(extracted_number); 1983 if (extracted_number->length() == 0) { 1984 return; 1985 } 1986 1987 VLOG(3) << "After stripping starting and trailing characters, left with: " 1988 << *extracted_number; 1989 1990 // Now remove any extra numbers at the end. 1991 reg_exps_->capture_up_to_second_number_start_pattern_-> 1992 PartialMatch(*extracted_number, extracted_number); 1993 } 1994 1995 bool PhoneNumberUtil::IsPossibleNumber(const PhoneNumber& number) const { 1996 return IsPossibleNumberWithReason(number) == IS_POSSIBLE; 1997 } 1998 1999 bool PhoneNumberUtil::IsPossibleNumberForString( 2000 const string& number, 2001 const string& region_dialing_from) const { 2002 PhoneNumber number_proto; 2003 if (Parse(number, region_dialing_from, &number_proto) == NO_PARSING_ERROR) { 2004 return IsPossibleNumber(number_proto); 2005 } else { 2006 return false; 2007 } 2008 } 2009 2010 PhoneNumberUtil::ValidationResult PhoneNumberUtil::IsPossibleNumberWithReason( 2011 const PhoneNumber& number) const { 2012 string national_number; 2013 GetNationalSignificantNumber(number, &national_number); 2014 int country_code = number.country_code(); 2015 // Note: For Russian Fed and NANPA numbers, we just use the rules from the 2016 // default region (US or Russia) since the GetRegionCodeForNumber will not 2017 // work if the number is possible but not valid. This would need to be 2018 // revisited if the possible number pattern ever differed between various 2019 // regions within those plans. 2020 if (!HasValidCountryCallingCode(country_code)) { 2021 return INVALID_COUNTRY_CODE; 2022 } 2023 string region_code; 2024 GetRegionCodeForCountryCode(country_code, ®ion_code); 2025 // Metadata cannot be NULL because the country calling code is valid. 2026 const PhoneMetadata* metadata = 2027 GetMetadataForRegionOrCallingCode(country_code, region_code); 2028 const PhoneNumberDesc& general_num_desc = metadata->general_desc(); 2029 // Handling case of numbers with no metadata. 2030 if (!general_num_desc.has_national_number_pattern()) { 2031 size_t number_length = national_number.length(); 2032 if (number_length < kMinLengthForNsn) { 2033 return TOO_SHORT; 2034 } else if (number_length > kMaxLengthForNsn) { 2035 return TOO_LONG; 2036 } else { 2037 return IS_POSSIBLE; 2038 } 2039 } 2040 const RegExp& possible_number_pattern = reg_exps_->regexp_cache_->GetRegExp( 2041 StrCat("(", general_num_desc.possible_number_pattern(), ")")); 2042 return TestNumberLengthAgainstPattern(possible_number_pattern, 2043 national_number); 2044 } 2045 2046 bool PhoneNumberUtil::TruncateTooLongNumber(PhoneNumber* number) const { 2047 if (IsValidNumber(*number)) { 2048 return true; 2049 } 2050 PhoneNumber number_copy(*number); 2051 uint64 national_number = number->national_number(); 2052 do { 2053 national_number /= 10; 2054 number_copy.set_national_number(national_number); 2055 if (IsPossibleNumberWithReason(number_copy) == TOO_SHORT || 2056 national_number == 0) { 2057 return false; 2058 } 2059 } while (!IsValidNumber(number_copy)); 2060 number->set_national_number(national_number); 2061 return true; 2062 } 2063 2064 PhoneNumberUtil::PhoneNumberType PhoneNumberUtil::GetNumberType( 2065 const PhoneNumber& number) const { 2066 string region_code; 2067 GetRegionCodeForNumber(number, ®ion_code); 2068 const PhoneMetadata* metadata = 2069 GetMetadataForRegionOrCallingCode(number.country_code(), region_code); 2070 if (!metadata) { 2071 return UNKNOWN; 2072 } 2073 string national_significant_number; 2074 GetNationalSignificantNumber(number, &national_significant_number); 2075 return GetNumberTypeHelper(national_significant_number, 2076 *metadata, 2077 reg_exps_->regexp_cache_.get()); 2078 } 2079 2080 bool PhoneNumberUtil::IsValidNumber(const PhoneNumber& number) const { 2081 string region_code; 2082 GetRegionCodeForNumber(number, ®ion_code); 2083 return IsValidNumberForRegion(number, region_code); 2084 } 2085 2086 bool PhoneNumberUtil::IsValidNumberForRegion(const PhoneNumber& number, 2087 const string& region_code) const { 2088 int country_code = number.country_code(); 2089 const PhoneMetadata* metadata = 2090 GetMetadataForRegionOrCallingCode(country_code, region_code); 2091 if (!metadata || 2092 ((kRegionCodeForNonGeoEntity != region_code) && 2093 country_code != GetCountryCodeForValidRegion(region_code))) { 2094 // Either the region code was invalid, or the country calling code for this 2095 // number does not match that of the region code. 2096 return false; 2097 } 2098 const PhoneNumberDesc& general_desc = metadata->general_desc(); 2099 string national_number; 2100 GetNationalSignificantNumber(number, &national_number); 2101 2102 // For regions where we don't have metadata for PhoneNumberDesc, we treat 2103 // any number passed in as a valid number if its national significant number 2104 // is between the minimum and maximum lengths defined by ITU for a national 2105 // significant number. 2106 if (!general_desc.has_national_number_pattern()) { 2107 VLOG(3) << "Validating number with incomplete metadata."; 2108 size_t number_length = national_number.length(); 2109 return number_length > kMinLengthForNsn && 2110 number_length <= kMaxLengthForNsn; 2111 } 2112 return GetNumberTypeHelper(national_number, *metadata, 2113 reg_exps_->regexp_cache_.get()) != UNKNOWN; 2114 } 2115 2116 bool PhoneNumberUtil::IsNumberGeographical( 2117 const PhoneNumber& phone_number) const { 2118 PhoneNumberType number_type = GetNumberType(phone_number); 2119 // TODO: Include mobile phone numbers from countries like 2120 // Indonesia, which has some mobile numbers that are geographical. 2121 return number_type == PhoneNumberUtil::FIXED_LINE || 2122 number_type == PhoneNumberUtil::FIXED_LINE_OR_MOBILE; 2123 } 2124 2125 bool PhoneNumberUtil::IsLeadingZeroPossible(int country_calling_code) const { 2126 string region_code; 2127 GetRegionCodeForCountryCode(country_calling_code, ®ion_code); 2128 const PhoneMetadata* main_metadata_for_calling_code = 2129 GetMetadataForRegionOrCallingCode(country_calling_code, region_code); 2130 if (!main_metadata_for_calling_code) return false; 2131 return main_metadata_for_calling_code->leading_zero_possible(); 2132 } 2133 2134 void PhoneNumberUtil::GetNationalSignificantNumber( 2135 const PhoneNumber& number, 2136 string* national_number) const { 2137 DCHECK(national_number); 2138 // If a leading zero has been set, we prefix this now. Note this is not a 2139 // national prefix. 2140 StrAppend(national_number, number.italian_leading_zero() ? "0" : ""); 2141 StrAppend(national_number, number.national_number()); 2142 } 2143 2144 int PhoneNumberUtil::GetLengthOfGeographicalAreaCode( 2145 const PhoneNumber& number) const { 2146 string region_code; 2147 GetRegionCodeForNumber(number, ®ion_code); 2148 const PhoneMetadata* metadata = GetMetadataForRegion(region_code); 2149 if (!metadata) { 2150 return 0; 2151 } 2152 // If a country doesn't use a national prefix, and this number doesn't have an 2153 // Italian leading zero, we assume it is a closed dialling plan with no area 2154 // codes. 2155 if (!metadata->has_national_prefix() && !number.italian_leading_zero()) { 2156 return 0; 2157 } 2158 2159 if (!IsNumberGeographical(number)) { 2160 return 0; 2161 } 2162 2163 return GetLengthOfNationalDestinationCode(number); 2164 } 2165 2166 int PhoneNumberUtil::GetLengthOfNationalDestinationCode( 2167 const PhoneNumber& number) const { 2168 PhoneNumber copied_proto(number); 2169 if (number.has_extension()) { 2170 // Clear the extension so it's not included when formatting. 2171 copied_proto.clear_extension(); 2172 } 2173 2174 string formatted_number; 2175 Format(copied_proto, INTERNATIONAL, &formatted_number); 2176 const scoped_ptr<RegExpInput> i18n_number( 2177 reg_exps_->regexp_factory_->CreateInput(formatted_number)); 2178 string digit_group; 2179 string ndc; 2180 string third_group; 2181 for (int i = 0; i < 3; ++i) { 2182 if (!reg_exps_->capturing_ascii_digits_pattern_->FindAndConsume( 2183 i18n_number.get(), &digit_group)) { 2184 // We should find at least three groups. 2185 return 0; 2186 } 2187 if (i == 1) { 2188 ndc = digit_group; 2189 } else if (i == 2) { 2190 third_group = digit_group; 2191 } 2192 } 2193 string region_code; 2194 GetRegionCodeForCountryCode(number.country_code(), ®ion_code); 2195 if (region_code == "AR" && 2196 GetNumberType(number) == MOBILE) { 2197 // Argentinian mobile numbers, when formatted in the international format, 2198 // are in the form of +54 9 NDC XXXX.... As a result, we take the length of 2199 // the third group (NDC) and add 1 for the digit 9, which also forms part of 2200 // the national significant number. 2201 return third_group.size() + 1; 2202 } 2203 return ndc.size(); 2204 } 2205 2206 void PhoneNumberUtil::NormalizeDigitsOnly(string* number) const { 2207 DCHECK(number); 2208 const RegExp& non_digits_pattern = reg_exps_->regexp_cache_->GetRegExp( 2209 StrCat("[^", kDigits, "]")); 2210 // Delete everything that isn't valid digits. 2211 non_digits_pattern.GlobalReplace(number, ""); 2212 // Normalize all decimal digits to ASCII digits. 2213 number->assign(NormalizeUTF8::NormalizeDecimalDigits(*number)); 2214 } 2215 2216 bool PhoneNumberUtil::IsAlphaNumber(const string& number) const { 2217 if (!IsViablePhoneNumber(number)) { 2218 // Number is too short, or doesn't match the basic phone number pattern. 2219 return false; 2220 } 2221 // Copy the number, since we are going to try and strip the extension from it. 2222 string number_copy(number); 2223 string extension; 2224 MaybeStripExtension(&number_copy, &extension); 2225 return reg_exps_->valid_alpha_phone_pattern_->FullMatch(number_copy); 2226 } 2227 2228 void PhoneNumberUtil::ConvertAlphaCharactersInNumber(string* number) const { 2229 DCHECK(number); 2230 NormalizeHelper(reg_exps_->alpha_phone_mappings_, false, number); 2231 } 2232 2233 // Normalizes a string of characters representing a phone number. This performs 2234 // the following conversions: 2235 // - Punctuation is stripped. 2236 // For ALPHA/VANITY numbers: 2237 // - Letters are converted to their numeric representation on a telephone 2238 // keypad. The keypad used here is the one defined in ITU Recommendation 2239 // E.161. This is only done if there are 3 or more letters in the number, to 2240 // lessen the risk that such letters are typos. 2241 // For other numbers: 2242 // - Wide-ascii digits are converted to normal ASCII (European) digits. 2243 // - Arabic-Indic numerals are converted to European numerals. 2244 // - Spurious alpha characters are stripped. 2245 void PhoneNumberUtil::Normalize(string* number) const { 2246 DCHECK(number); 2247 if (reg_exps_->valid_alpha_phone_pattern_->PartialMatch(*number)) { 2248 NormalizeHelper(reg_exps_->alpha_phone_mappings_, true, number); 2249 } 2250 NormalizeDigitsOnly(number); 2251 } 2252 2253 // Checks to see if the string of characters could possibly be a phone number at 2254 // all. At the moment, checks to see that the string begins with at least 3 2255 // digits, ignoring any punctuation commonly found in phone numbers. This 2256 // method does not require the number to be normalized in advance - but does 2257 // assume that leading non-number symbols have been removed, such as by the 2258 // method ExtractPossibleNumber. 2259 bool PhoneNumberUtil::IsViablePhoneNumber(const string& number) const { 2260 if (number.length() < kMinLengthForNsn) { 2261 VLOG(2) << "Number too short to be viable:" << number; 2262 return false; 2263 } 2264 return reg_exps_->valid_phone_number_pattern_->FullMatch(number); 2265 } 2266 2267 // Strips the IDD from the start of the number if present. Helper function used 2268 // by MaybeStripInternationalPrefixAndNormalize. 2269 bool PhoneNumberUtil::ParsePrefixAsIdd(const RegExp& idd_pattern, 2270 string* number) const { 2271 DCHECK(number); 2272 const scoped_ptr<RegExpInput> number_copy( 2273 reg_exps_->regexp_factory_->CreateInput(*number)); 2274 // First attempt to strip the idd_pattern at the start, if present. We make a 2275 // copy so that we can revert to the original string if necessary. 2276 if (idd_pattern.Consume(number_copy.get())) { 2277 // Only strip this if the first digit after the match is not a 0, since 2278 // country calling codes cannot begin with 0. 2279 string extracted_digit; 2280 if (reg_exps_->capturing_digit_pattern_->PartialMatch( 2281 number_copy->ToString(), &extracted_digit)) { 2282 NormalizeDigitsOnly(&extracted_digit); 2283 if (extracted_digit == "0") { 2284 return false; 2285 } 2286 } 2287 number->assign(number_copy->ToString()); 2288 return true; 2289 } 2290 return false; 2291 } 2292 2293 // Strips any international prefix (such as +, 00, 011) present in the number 2294 // provided, normalizes the resulting number, and indicates if an international 2295 // prefix was present. 2296 // 2297 // possible_idd_prefix represents the international direct dialing prefix from 2298 // the region we think this number may be dialed in. 2299 // Returns true if an international dialing prefix could be removed from the 2300 // number, otherwise false if the number did not seem to be in international 2301 // format. 2302 PhoneNumber::CountryCodeSource 2303 PhoneNumberUtil::MaybeStripInternationalPrefixAndNormalize( 2304 const string& possible_idd_prefix, 2305 string* number) const { 2306 DCHECK(number); 2307 if (number->empty()) { 2308 return PhoneNumber::FROM_DEFAULT_COUNTRY; 2309 } 2310 const scoped_ptr<RegExpInput> number_string_piece( 2311 reg_exps_->regexp_factory_->CreateInput(*number)); 2312 if (reg_exps_->plus_chars_pattern_->Consume(number_string_piece.get())) { 2313 number->assign(number_string_piece->ToString()); 2314 // Can now normalize the rest of the number since we've consumed the "+" 2315 // sign at the start. 2316 Normalize(number); 2317 return PhoneNumber::FROM_NUMBER_WITH_PLUS_SIGN; 2318 } 2319 // Attempt to parse the first digits as an international prefix. 2320 const RegExp& idd_pattern = 2321 reg_exps_->regexp_cache_->GetRegExp(possible_idd_prefix); 2322 Normalize(number); 2323 return ParsePrefixAsIdd(idd_pattern, number) 2324 ? PhoneNumber::FROM_NUMBER_WITH_IDD 2325 : PhoneNumber::FROM_DEFAULT_COUNTRY; 2326 } 2327 2328 // Strips any national prefix (such as 0, 1) present in the number provided. 2329 // The number passed in should be the normalized telephone number that we wish 2330 // to strip any national dialing prefix from. The metadata should be for the 2331 // region that we think this number is from. Returns true if a national prefix 2332 // and/or carrier code was stripped. 2333 bool PhoneNumberUtil::MaybeStripNationalPrefixAndCarrierCode( 2334 const PhoneMetadata& metadata, 2335 string* number, 2336 string* carrier_code) const { 2337 DCHECK(number); 2338 string carrier_code_temp; 2339 const string& possible_national_prefix = 2340 metadata.national_prefix_for_parsing(); 2341 if (number->empty() || possible_national_prefix.empty()) { 2342 // Early return for numbers of zero length or with no national prefix 2343 // possible. 2344 return false; 2345 } 2346 // We use two copies here since Consume modifies the phone number, and if the 2347 // first if-clause fails the number will already be changed. 2348 const scoped_ptr<RegExpInput> number_copy( 2349 reg_exps_->regexp_factory_->CreateInput(*number)); 2350 const scoped_ptr<RegExpInput> number_copy_without_transform( 2351 reg_exps_->regexp_factory_->CreateInput(*number)); 2352 string number_string_copy(*number); 2353 string captured_part_of_prefix; 2354 const RegExp& national_number_rule = reg_exps_->regexp_cache_->GetRegExp( 2355 metadata.general_desc().national_number_pattern()); 2356 // Check if the original number is viable. 2357 bool is_viable_original_number = national_number_rule.FullMatch(*number); 2358 // Attempt to parse the first digits as a national prefix. We make a 2359 // copy so that we can revert to the original string if necessary. 2360 const string& transform_rule = metadata.national_prefix_transform_rule(); 2361 const RegExp& possible_national_prefix_pattern = 2362 reg_exps_->regexp_cache_->GetRegExp(possible_national_prefix); 2363 if (!transform_rule.empty() && 2364 (possible_national_prefix_pattern.Consume( 2365 number_copy.get(), &carrier_code_temp, &captured_part_of_prefix) || 2366 possible_national_prefix_pattern.Consume( 2367 number_copy.get(), &captured_part_of_prefix)) && 2368 !captured_part_of_prefix.empty()) { 2369 // If this succeeded, then we must have had a transform rule and there must 2370 // have been some part of the prefix that we captured. 2371 // We make the transformation and check that the resultant number is still 2372 // viable. If so, replace the number and return. 2373 possible_national_prefix_pattern.Replace(&number_string_copy, 2374 transform_rule); 2375 if (is_viable_original_number && 2376 !national_number_rule.FullMatch(number_string_copy)) { 2377 return false; 2378 } 2379 number->assign(number_string_copy); 2380 if (carrier_code) { 2381 carrier_code->assign(carrier_code_temp); 2382 } 2383 } else if (possible_national_prefix_pattern.Consume( 2384 number_copy_without_transform.get(), &carrier_code_temp) || 2385 possible_national_prefix_pattern.Consume( 2386 number_copy_without_transform.get())) { 2387 VLOG(4) << "Parsed the first digits as a national prefix."; 2388 // If captured_part_of_prefix is empty, this implies nothing was captured by 2389 // the capturing groups in possible_national_prefix; therefore, no 2390 // transformation is necessary, and we just remove the national prefix. 2391 const string number_copy_as_string = 2392 number_copy_without_transform->ToString(); 2393 if (is_viable_original_number && 2394 !national_number_rule.FullMatch(number_copy_as_string)) { 2395 return false; 2396 } 2397 number->assign(number_copy_as_string); 2398 if (carrier_code) { 2399 carrier_code->assign(carrier_code_temp); 2400 } 2401 } else { 2402 return false; 2403 VLOG(4) << "The first digits did not match the national prefix."; 2404 } 2405 return true; 2406 } 2407 2408 // Strips any extension (as in, the part of the number dialled after the call is 2409 // connected, usually indicated with extn, ext, x or similar) from the end of 2410 // the number, and returns it. The number passed in should be non-normalized. 2411 bool PhoneNumberUtil::MaybeStripExtension(string* number, string* extension) 2412 const { 2413 DCHECK(number); 2414 DCHECK(extension); 2415 // There are three extension capturing groups in the regular expression. 2416 string possible_extension_one; 2417 string possible_extension_two; 2418 string possible_extension_three; 2419 string number_copy(*number); 2420 const scoped_ptr<RegExpInput> number_copy_as_regexp_input( 2421 reg_exps_->regexp_factory_->CreateInput(number_copy)); 2422 if (reg_exps_->extn_pattern_->Consume(number_copy_as_regexp_input.get(), 2423 false, 2424 &possible_extension_one, 2425 &possible_extension_two, 2426 &possible_extension_three)) { 2427 // Replace the extensions in the original string here. 2428 reg_exps_->extn_pattern_->Replace(&number_copy, ""); 2429 VLOG(4) << "Found an extension. Possible extension one: " 2430 << possible_extension_one 2431 << ". Possible extension two: " << possible_extension_two 2432 << ". Possible extension three: " << possible_extension_three 2433 << ". Remaining number: " << number_copy; 2434 // If we find a potential extension, and the number preceding this is a 2435 // viable number, we assume it is an extension. 2436 if ((!possible_extension_one.empty() || !possible_extension_two.empty() || 2437 !possible_extension_three.empty()) && 2438 IsViablePhoneNumber(number_copy)) { 2439 number->assign(number_copy); 2440 if (!possible_extension_one.empty()) { 2441 extension->assign(possible_extension_one); 2442 } else if (!possible_extension_two.empty()) { 2443 extension->assign(possible_extension_two); 2444 } else if (!possible_extension_three.empty()) { 2445 extension->assign(possible_extension_three); 2446 } 2447 return true; 2448 } 2449 } 2450 return false; 2451 } 2452 2453 // Extracts country calling code from national_number, and returns it. It 2454 // assumes that the leading plus sign or IDD has already been removed. Returns 0 2455 // if national_number doesn't start with a valid country calling code, and 2456 // leaves national_number unmodified. Assumes the national_number is at least 3 2457 // characters long. 2458 int PhoneNumberUtil::ExtractCountryCode(string* national_number) const { 2459 int potential_country_code; 2460 if (national_number->empty() || (national_number->at(0) == '0')) { 2461 // Country codes do not begin with a '0'. 2462 return 0; 2463 } 2464 for (size_t i = 1; i <= kMaxLengthCountryCode; ++i) { 2465 safe_strto32(national_number->substr(0, i), &potential_country_code); 2466 string region_code; 2467 GetRegionCodeForCountryCode(potential_country_code, ®ion_code); 2468 if (region_code != RegionCode::GetUnknown()) { 2469 national_number->erase(0, i); 2470 return potential_country_code; 2471 } 2472 } 2473 return 0; 2474 } 2475 2476 // Tries to extract a country calling code from a number. Country calling codes 2477 // are extracted in the following ways: 2478 // - by stripping the international dialing prefix of the region the person 2479 // is dialing from, if this is present in the number, and looking at the next 2480 // digits 2481 // - by stripping the '+' sign if present and then looking at the next digits 2482 // - by comparing the start of the number and the country calling code of the 2483 // default region. If the number is not considered possible for the numbering 2484 // plan of the default region initially, but starts with the country calling 2485 // code of this region, validation will be reattempted after stripping this 2486 // country calling code. If this number is considered a possible number, then 2487 // the first digits will be considered the country calling code and removed as 2488 // such. 2489 // 2490 // Returns NO_PARSING_ERROR if a country calling code was successfully 2491 // extracted or none was present, or the appropriate error otherwise, such as 2492 // if a + was present but it was not followed by a valid country calling code. 2493 // If NO_PARSING_ERROR is returned, the national_number without the country 2494 // calling code is populated, and the country_code of the phone_number passed 2495 // in is set to the country calling code if found, otherwise to 0. 2496 PhoneNumberUtil::ErrorType PhoneNumberUtil::MaybeExtractCountryCode( 2497 const PhoneMetadata* default_region_metadata, 2498 bool keep_raw_input, 2499 string* national_number, 2500 PhoneNumber* phone_number) const { 2501 DCHECK(national_number); 2502 DCHECK(phone_number); 2503 // Set the default prefix to be something that will never match if there is no 2504 // default region. 2505 string possible_country_idd_prefix = default_region_metadata 2506 ? default_region_metadata->international_prefix() 2507 : "NonMatch"; 2508 PhoneNumber::CountryCodeSource country_code_source = 2509 MaybeStripInternationalPrefixAndNormalize(possible_country_idd_prefix, 2510 national_number); 2511 if (keep_raw_input) { 2512 phone_number->set_country_code_source(country_code_source); 2513 } 2514 if (country_code_source != PhoneNumber::FROM_DEFAULT_COUNTRY) { 2515 if (national_number->length() <= kMinLengthForNsn) { 2516 VLOG(2) << "Phone number had an IDD, but after this was not " 2517 << "long enough to be a viable phone number."; 2518 return TOO_SHORT_AFTER_IDD; 2519 } 2520 int potential_country_code = ExtractCountryCode(national_number); 2521 if (potential_country_code != 0) { 2522 phone_number->set_country_code(potential_country_code); 2523 return NO_PARSING_ERROR; 2524 } 2525 // If this fails, they must be using a strange country calling code that we 2526 // don't recognize, or that doesn't exist. 2527 return INVALID_COUNTRY_CODE_ERROR; 2528 } else if (default_region_metadata) { 2529 // Check to see if the number starts with the country calling code for the 2530 // default region. If so, we remove the country calling code, and do some 2531 // checks on the validity of the number before and after. 2532 int default_country_code = default_region_metadata->country_code(); 2533 string default_country_code_string(SimpleItoa(default_country_code)); 2534 VLOG(4) << "Possible country calling code: " << default_country_code_string; 2535 string potential_national_number; 2536 if (TryStripPrefixString(*national_number, 2537 default_country_code_string, 2538 &potential_national_number)) { 2539 const PhoneNumberDesc& general_num_desc = 2540 default_region_metadata->general_desc(); 2541 const RegExp& valid_number_pattern = 2542 reg_exps_->regexp_cache_->GetRegExp( 2543 general_num_desc.national_number_pattern()); 2544 MaybeStripNationalPrefixAndCarrierCode(*default_region_metadata, 2545 &potential_national_number, 2546 NULL); 2547 VLOG(4) << "Number without country calling code prefix: " 2548 << potential_national_number; 2549 const RegExp& possible_number_pattern = 2550 reg_exps_->regexp_cache_->GetRegExp( 2551 StrCat("(", general_num_desc.possible_number_pattern(), ")")); 2552 // If the number was not valid before but is valid now, or if it was too 2553 // long before, we consider the number with the country code stripped to 2554 // be a better result and keep that instead. 2555 if ((!valid_number_pattern.FullMatch(*national_number) && 2556 valid_number_pattern.FullMatch(potential_national_number)) || 2557 TestNumberLengthAgainstPattern(possible_number_pattern, 2558 *national_number) == TOO_LONG) { 2559 national_number->assign(potential_national_number); 2560 if (keep_raw_input) { 2561 phone_number->set_country_code_source( 2562 PhoneNumber::FROM_NUMBER_WITHOUT_PLUS_SIGN); 2563 } 2564 phone_number->set_country_code(default_country_code); 2565 return NO_PARSING_ERROR; 2566 } 2567 } 2568 } 2569 // No country calling code present. Set the country_code to 0. 2570 phone_number->set_country_code(0); 2571 return NO_PARSING_ERROR; 2572 } 2573 2574 PhoneNumberUtil::MatchType PhoneNumberUtil::IsNumberMatch( 2575 const PhoneNumber& first_number_in, 2576 const PhoneNumber& second_number_in) const { 2577 // Make copies of the phone number so that the numbers passed in are not 2578 // edited. 2579 PhoneNumber first_number(first_number_in); 2580 PhoneNumber second_number(second_number_in); 2581 // First clear raw_input and country_code_source and 2582 // preferred_domestic_carrier_code fields and any empty-string extensions so 2583 // that we can use the proto-buffer equality method. 2584 first_number.clear_raw_input(); 2585 first_number.clear_country_code_source(); 2586 first_number.clear_preferred_domestic_carrier_code(); 2587 second_number.clear_raw_input(); 2588 second_number.clear_country_code_source(); 2589 second_number.clear_preferred_domestic_carrier_code(); 2590 if (first_number.extension().empty()) { 2591 first_number.clear_extension(); 2592 } 2593 if (second_number.extension().empty()) { 2594 second_number.clear_extension(); 2595 } 2596 // Early exit if both had extensions and these are different. 2597 if (first_number.has_extension() && second_number.has_extension() && 2598 first_number.extension() != second_number.extension()) { 2599 return NO_MATCH; 2600 } 2601 int first_number_country_code = first_number.country_code(); 2602 int second_number_country_code = second_number.country_code(); 2603 // Both had country calling code specified. 2604 if (first_number_country_code != 0 && second_number_country_code != 0) { 2605 if (ExactlySameAs(first_number, second_number)) { 2606 return EXACT_MATCH; 2607 } else if (first_number_country_code == second_number_country_code && 2608 IsNationalNumberSuffixOfTheOther(first_number, second_number)) { 2609 // A SHORT_NSN_MATCH occurs if there is a difference because of the 2610 // presence or absence of an 'Italian leading zero', the presence or 2611 // absence of an extension, or one NSN being a shorter variant of the 2612 // other. 2613 return SHORT_NSN_MATCH; 2614 } 2615 // This is not a match. 2616 return NO_MATCH; 2617 } 2618 // Checks cases where one or both country calling codes were not specified. To 2619 // make equality checks easier, we first set the country_code fields to be 2620 // equal. 2621 first_number.set_country_code(second_number_country_code); 2622 // If all else was the same, then this is an NSN_MATCH. 2623 if (ExactlySameAs(first_number, second_number)) { 2624 return NSN_MATCH; 2625 } 2626 if (IsNationalNumberSuffixOfTheOther(first_number, second_number)) { 2627 return SHORT_NSN_MATCH; 2628 } 2629 return NO_MATCH; 2630 } 2631 2632 PhoneNumberUtil::MatchType PhoneNumberUtil::IsNumberMatchWithTwoStrings( 2633 const string& first_number, 2634 const string& second_number) const { 2635 PhoneNumber first_number_as_proto; 2636 ErrorType error_type = 2637 Parse(first_number, RegionCode::GetUnknown(), &first_number_as_proto); 2638 if (error_type == NO_PARSING_ERROR) { 2639 return IsNumberMatchWithOneString(first_number_as_proto, second_number); 2640 } 2641 if (error_type == INVALID_COUNTRY_CODE_ERROR) { 2642 PhoneNumber second_number_as_proto; 2643 ErrorType error_type = Parse(second_number, RegionCode::GetUnknown(), 2644 &second_number_as_proto); 2645 if (error_type == NO_PARSING_ERROR) { 2646 return IsNumberMatchWithOneString(second_number_as_proto, first_number); 2647 } 2648 if (error_type == INVALID_COUNTRY_CODE_ERROR) { 2649 error_type = ParseHelper(first_number, RegionCode::GetUnknown(), false, 2650 false, &first_number_as_proto); 2651 if (error_type == NO_PARSING_ERROR) { 2652 error_type = ParseHelper(second_number, RegionCode::GetUnknown(), false, 2653 false, &second_number_as_proto); 2654 if (error_type == NO_PARSING_ERROR) { 2655 return IsNumberMatch(first_number_as_proto, second_number_as_proto); 2656 } 2657 } 2658 } 2659 } 2660 // One or more of the phone numbers we are trying to match is not a viable 2661 // phone number. 2662 return INVALID_NUMBER; 2663 } 2664 2665 PhoneNumberUtil::MatchType PhoneNumberUtil::IsNumberMatchWithOneString( 2666 const PhoneNumber& first_number, 2667 const string& second_number) const { 2668 // First see if the second number has an implicit country calling code, by 2669 // attempting to parse it. 2670 PhoneNumber second_number_as_proto; 2671 ErrorType error_type = 2672 Parse(second_number, RegionCode::GetUnknown(), &second_number_as_proto); 2673 if (error_type == NO_PARSING_ERROR) { 2674 return IsNumberMatch(first_number, second_number_as_proto); 2675 } 2676 if (error_type == INVALID_COUNTRY_CODE_ERROR) { 2677 // The second number has no country calling code. EXACT_MATCH is no longer 2678 // possible. We parse it as if the region was the same as that for the 2679 // first number, and if EXACT_MATCH is returned, we replace this with 2680 // NSN_MATCH. 2681 string first_number_region; 2682 GetRegionCodeForCountryCode(first_number.country_code(), 2683 &first_number_region); 2684 if (first_number_region != RegionCode::GetUnknown()) { 2685 PhoneNumber second_number_with_first_number_region; 2686 Parse(second_number, first_number_region, 2687 &second_number_with_first_number_region); 2688 MatchType match = IsNumberMatch(first_number, 2689 second_number_with_first_number_region); 2690 if (match == EXACT_MATCH) { 2691 return NSN_MATCH; 2692 } 2693 return match; 2694 } else { 2695 // If the first number didn't have a valid country calling code, then we 2696 // parse the second number without one as well. 2697 error_type = ParseHelper(second_number, RegionCode::GetUnknown(), false, 2698 false, &second_number_as_proto); 2699 if (error_type == NO_PARSING_ERROR) { 2700 return IsNumberMatch(first_number, second_number_as_proto); 2701 } 2702 } 2703 } 2704 // One or more of the phone numbers we are trying to match is not a viable 2705 // phone number. 2706 return INVALID_NUMBER; 2707 } 2708 2709 AsYouTypeFormatter* PhoneNumberUtil::GetAsYouTypeFormatter( 2710 const string& region_code) const { 2711 return new AsYouTypeFormatter(region_code); 2712 } 2713 2714 bool PhoneNumberUtil::CanBeInternationallyDialled( 2715 const PhoneNumber& number) const { 2716 string region_code; 2717 GetRegionCodeForNumber(number, ®ion_code); 2718 const PhoneMetadata* metadata = GetMetadataForRegion(region_code); 2719 if (!metadata) { 2720 // Note numbers belonging to non-geographical entities (e.g. +800 numbers) 2721 // are always internationally diallable, and will be caught here. 2722 return true; 2723 } 2724 string national_significant_number; 2725 GetNationalSignificantNumber(number, &national_significant_number); 2726 return !IsNumberMatchingDesc( 2727 national_significant_number, metadata->no_international_dialling(), 2728 reg_exps_->regexp_cache_.get()); 2729 } 2730 2731 } // namespace phonenumbers 2732 } // namespace i18n 2733