| // Copyright (C) 2011 The Libphonenumber Authors |
| // |
| // Licensed under the Apache License, Version 2.0 (the "License"); |
| // you may not use this file except in compliance with the License. |
| // You may obtain a copy of the License at |
| // |
| // http://www.apache.org/licenses/LICENSE-2.0 |
| // |
| // Unless required by applicable law or agreed to in writing, software |
| // distributed under the License is distributed on an "AS IS" BASIS, |
| // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| // See the License for the specific language governing permissions and |
| // limitations under the License. |
| // |
| // Author: Lara Rennie |
| // Author: Tao Huang |
| // |
| // This is a direct port from PhoneNumberMatcher.java. |
| // Changes to this class should also happen to the Java version, whenever it |
| // makes sense. |
| |
| #ifndef I18N_PHONENUMBERS_PHONENUMBERMATCHER_H_ |
| #define I18N_PHONENUMBERS_PHONENUMBERMATCHER_H_ |
| |
| #include <string> |
| #include <vector> |
| |
| #include "base/basictypes.h" |
| #include "base/memory/scoped_ptr.h" |
| #include "phonenumbers/callback.h" |
| #include "phonenumbers/regexp_adapter.h" |
| |
| namespace i18n { |
| namespace phonenumbers { |
| |
| template <class R, class A1, class A2, class A3, class A4> |
| class ResultCallback4; |
| |
| using std::string; |
| using std::vector; |
| |
| class NumberFormat; |
| class PhoneNumber; |
| class PhoneNumberMatch; |
| class PhoneNumberMatcherRegExps; |
| class PhoneNumberUtil; |
| |
| class PhoneNumberMatcher { |
| friend class PhoneNumberMatcherTest; |
| public: |
| // Leniency when finding potential phone numbers in text segments. The levels |
| // here are ordered in increasing strictness. |
| enum Leniency { |
| // Phone numbers accepted are possible, but not necessarily valid. |
| POSSIBLE, |
| // Phone numbers accepted are possible and valid. |
| VALID, |
| // Phone numbers accepted are valid and are grouped in a possible way for |
| // this locale. For example, a US number written as "65 02 53 00 00" is not |
| // accepted at this leniency level, whereas "650 253 0000" or "6502530000" |
| // are. Numbers with more than one '/' symbol are also dropped at this |
| // level. |
| // Warning: The next two levels might result in lower coverage especially |
| // for regions outside of country code "+1". If you are not sure about which |
| // level to use, you can send an e-mail to the discussion group |
| // http://groups.google.com/group/libphonenumber-discuss/ |
| STRICT_GROUPING, |
| // Phone numbers accepted are valid and are grouped in the same way that we |
| // would have formatted it, or as a single block. For example, a US number |
| // written as "650 2530000" is not accepted at this leniency level, whereas |
| // "650 253 0000" or "6502530000" are. |
| EXACT_GROUPING, |
| }; |
| |
| // Constructs a phone number matcher. |
| PhoneNumberMatcher(const PhoneNumberUtil& util, |
| const string& text, |
| const string& region_code, |
| Leniency leniency, |
| int max_tries); |
| |
| // Wrapper to construct a phone number matcher, with no limitation on the |
| // number of retries and VALID Leniency. |
| PhoneNumberMatcher(const string& text, |
| const string& region_code); |
| |
| ~PhoneNumberMatcher(); |
| |
| // Returns true if the text sequence has another match. |
| bool HasNext(); |
| |
| // Gets next match from text sequence. |
| bool Next(PhoneNumberMatch* match); |
| |
| private: |
| // The potential states of a PhoneNumberMatcher. |
| enum State { |
| NOT_READY, |
| READY, |
| DONE, |
| }; |
| |
| // Attempts to extract a match from a candidate string. Returns true if a |
| // match is found, otherwise returns false. The value "offset" refers to the |
| // start index of the candidate string within the overall text. |
| bool Find(int index, PhoneNumberMatch* match); |
| |
| // Checks a number was formatted with a national prefix, if the number was |
| // found in national format, and a national prefix is required for that |
| // number. Returns false if the number needed to have a national prefix and |
| // none was found. |
| bool IsNationalPrefixPresentIfRequired(const PhoneNumber& number) const; |
| |
| // Attempts to extract a match from candidate. Returns true if the match was |
| // found, otherwise returns false. |
| bool ExtractMatch(const string& candidate, int offset, |
| PhoneNumberMatch* match); |
| |
| // Attempts to extract a match from a candidate string if the whole candidate |
| // does not qualify as a match. Returns true if a match is found, otherwise |
| // returns false. |
| bool ExtractInnerMatch(const string& candidate, int offset, |
| PhoneNumberMatch* match); |
| |
| // Parses a phone number from the candidate using PhoneNumberUtil::Parse() and |
| // verifies it matches the requested leniency. If parsing and verification |
| // succeed, returns true, otherwise this method returns false; |
| bool ParseAndVerify(const string& candidate, int offset, |
| PhoneNumberMatch* match); |
| |
| bool CheckNumberGroupingIsValid( |
| const PhoneNumber& phone_number, |
| const string& candidate, |
| ResultCallback4<bool, const PhoneNumberUtil&, const PhoneNumber&, |
| const string&, const vector<string>&>* checker) const; |
| |
| void GetNationalNumberGroups( |
| const PhoneNumber& number, |
| const NumberFormat* formatting_pattern, |
| vector<string>* digit_blocks) const; |
| |
| bool AllNumberGroupsAreExactlyPresent( |
| const PhoneNumberUtil& util, |
| const PhoneNumber& phone_number, |
| const string& normalized_candidate, |
| const vector<string>& formatted_number_groups) const; |
| |
| bool VerifyAccordingToLeniency(Leniency leniency, const PhoneNumber& number, |
| const string& candidate) const; |
| |
| // Helper method to determine if a character is a Latin-script letter or not. |
| // For our purposes, combining marks should also return true since we assume |
| // they have been added to a preceding Latin character. |
| static bool IsLatinLetter(char32 letter); |
| |
| // Helper class holding useful regular expressions. |
| const PhoneNumberMatcherRegExps* reg_exps_; |
| |
| // The phone number utility; |
| const PhoneNumberUtil& phone_util_; |
| |
| // The text searched for phone numbers; |
| const string text_; |
| |
| // The region(country) to assume for phone numbers without an international |
| // prefix. |
| const string preferred_region_; |
| |
| // The degree of validation requested. |
| Leniency leniency_; |
| |
| // The maximum number of retries after matching an invalid number. |
| int max_tries_; |
| |
| // The iteration tristate. |
| State state_; |
| |
| // The last successful match, NULL unless in State.READY. |
| scoped_ptr<PhoneNumberMatch> last_match_; |
| |
| // The next index to start searching at. Undefined in State.DONE. |
| int search_index_; |
| |
| DISALLOW_COPY_AND_ASSIGN(PhoneNumberMatcher); |
| }; |
| |
| } // namespace phonenumbers |
| } // namespace i18n |
| |
| #endif // I18N_PHONENUMBERS_PHONENUMBERMATCHER_H_ |