I have a list of international phone numbers and a List of Country calling codes.
I would like to identify the Country from the numbers but I can't find a fast and elegant way to do it.
Any idea? The only I got is to have an hardcoded check (Eg. "look at the first number, look at the second number: if it's X then check for the third number. If the second number is Y then the Country is Foo", etc.).
I'm using PHP and a DB (MySQL) for the lists, but I think that any pseudocode will help.
Alternatively, you could use a tool like Twilio Lookup.
The CountryCode
property is always returned when you make an API request with Lookup.
https://www.twilio.com/docs/api/lookups#lookups-instance-properties
[Disclosure: I work for Twilio]
i was after something similar to this, but i also wanted to determine the region/state - if available. in the end i hacked up something based on a tree of the digits leading digits (spurred on by the description at wikipedia)
my implementation is available as a gist.
I'm currently using an implementation of Google's libphonenumber in Node, which works fairly well. I suppose you could try a PHP implementation, e.g. libphonenumber-for-php.
The hard-coded check can be turned into a decision tree generated automatically from the list of calling codes. Each node of the tree defines the 'current' character, the list of possible following characters (tree nodes) or a country in case it's a terminal node. The root node will be for the leading '+' sign.
The challenge here is that some countries share the same phone country code. E.g. both Canada and the US have phone numbers starting with +1.
I'm using https://github.com/giggsey/libphonenumber-for-php as following:
/**
* Get country
* @param string $phone
* @param string $defaultCountry
* @return string Country code, e.g. 'CA', 'US', 'DE', ...
*/
public static function getCountry($phone, $defaultCountry) {
try {
$PhoneNumberUtil = \libphonenumber\PhoneNumberUtil::getInstance();
$PhoneNumber = $PhoneNumberUtil->parse($phone, $defaultCountry);
$country = $PhoneNumberUtil->getRegionCodeForNumber($PhoneNumber);
return $country;
} catch (\libphonenumber\NumberParseException $e) {
}
return $defaultCountry;
}
You can easily do a simple lookup starting with the first number, then the second, and so on until you find it. This will work correctly because no calling code is a prefix of another code, i.e. the international calling codes form a "prefix code" (the phone system relies on this property).
I'm not good any good at PHP so here is a simple python implementation; hopefully it is easy to follow:
>>> phone_numbers = ["+12345", "+23456", "+34567", "+45678"]
>>> country_codes = { "+1": "USA", "+234": "Nigeria", "+34" : "Spain" }
>>> for number in phone_numbers:
... for i in [2, 3, 4]:
... if number[:i] in country_codes:
... print country_codes[number[:i]]
... break
... else:
... print "Unknown"
...
USA
Nigeria
Spain
Unknown
Essentially you have an associative array between prefixes and countries (which I assume you can easily generate from that Wikipedia article. You try looking up the first digit of the phone number in the associative array. If it's not in the array you try the first two digits, then the first three. If there is no match after three digits then this number doesn't start with a valid international calling code.