Python module - phonenumbers 電話號碼格式驗證

Posted on  Sep 29, 2018  in  Python 模組/套件推薦  by  Amo Chen  ‐ 2 min read

如果 Java, C++, Javascript 開發者想驗證各個不同國家電話號碼的格式與正確性的話,可以利用 Google 所開源的 libphonenumber ,著實省去很多苦工。如果是使用 Python 的開發者則可以安裝模組 phonenumbers 做到一樣的事情,該 module 是由 daviddrysdale 佛心將 Google libphonenumbers 移植到 Python 供大家使用,我每次使用時都心懷感激!

本文將介紹:

  1. E.164 電話號碼格式
  2. 用 phonenumbers 驗證電話號碼
  3. 用 phonenumbers 擷取電話號碼資訊

本文環境

  • Python 3.6.5
  • phonenumbers 8.9.14

如何安裝 phonenumbers:

$ pip install phonenumbers

E.164 電話號碼格式

使用 phonenumbers 之前必須先認識 E.164 格式。

E.164 格式是由 ITU Telecommunication Standardization Sector (ITU-T) 所推崇的國際電話號碼標準,其格式至少分為 2 個部分 國碼(country code) + 用戶號碼(subscriber number) ,且必須為 + 加號開頭,所以一支 E.164 格式的電話號碼會像這樣:

+[國碼][用戶號碼]

這也就是為什麼打國際電話要輸入 + 加號的原因。

此外, E.164 也有提供 optional 的一些格式選項,譬如區碼(area code)。舉例來說,我們輸入台灣常見手機號碼時都會用 0 開頭,例如 0912000000 中的 0 是台灣專用的區碼,在播打國際電話時都不需要輸入,所以 0912000000 再加上國碼 886 的話,用 E.164 格式表示的話,以下 2 種都是正確的:

  • +886912000000
  • +8860912000000

以上就是簡單的 E.164 格式科普介紹。

用 phonenumbers 驗證電話號碼

如果要驗證一支電話號碼是否正確,可以先使用 phonenumbers.parse 函式,參數必須是 E.164 格式的電話號碼,如果電話號碼格式有錯的話,就會觸發 NumberParseException

>>> import phonenumbers
>>> phonenumbers.parse('+8860912000000')
PhoneNumber(country_code=886, national_number=912000000, extension=None, italian_leading_zero=None, number_of_leading_zeros=None, country_code_source=0, preferred_domestic_carrier_code=None)
>>>
>>>
>>> phonenumbers.parse('123456789')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "~/anaconda3/lib/python3.6/site-packages/phonenumbers/phonenumberutil.py", line 2807, in parse
    "Missing or invalid default region.")
phonenumbers.phonenumberutil.NumberParseException: (0) Missing or invalid default region.
>>>
>>>
>>> phonenumbers.parse('+88691')
PhoneNumber(country_code=886, national_number=91, extension=None, italian_leading_zero=None, number_of_leading_zeros=None, country_code_source=0, preferred_domestic_carrier_code=None)

上述範例可以發現 phonenumbers.parse 回傳的是一個 PhoneNumber 的 object ,裡面就儲存著電話號碼的相關資訊。同時還可以注意到 phonenumbers.parse('+88691') 竟然沒有觸發任何 NumberParseException 這是由於 phonenumbers.parse 僅先檢查電話格式、是否滿足最小與最大長度,以及電話號碼是否含有合法國碼、區碼等等資訊,如果要進一步驗證電話號碼是否合法,就必須搭配 phonenumbers.is_valid_number 檢查:

>>> p = phonenumbers.parse('+88691')
>>> phonenumbers.is_valid_number(p)
False
>>>
>>>
>>> p = phonenumbers.parse('+886912000000')
>>> phonenumbers.is_valid_number(p)
True

另外,要額外說明的是 phonenumbers.is_valid_number 僅檢查是否為合法的電話號碼,並不代表該電話號碼實際存在或可以撥打成功,請勿誤解。

用 phonenumbers 擷取電話號碼資訊

先前提到 phonenumbers.parse 回傳的是一個 PhoneNumber 的 object ,裡面就儲存著電話號碼的相關資訊,所以可以利用該 object 擷取裡面的資訊。以下提供各種常用的資訊取得法:

取得國碼:

>>> p = phonenumbers.parse('+886912000000')
>>> p.country_code
886

取得國碼名稱:

>>> from phonenumbers import geocoder
>>> geocoder.description_for_number(p, 'en')
Taiwan

取得電信業者名稱(電信資料有因為尚未更新而導致不準確的情況):

>>> from phonenumbers import carrier
>>> carrier.name_for_number(p, 'en')
'Chunghwa Telecom'

PhoneNumber object 以 E.164 格式輸出:

>>> phonenumbers.format_number(p, phonenumbers.PhoneNumberFormat.E164)
'+886912000000'

總結

以上就是 phonenumbers 的簡單介紹,如需要更詳細的使用方法,建議可以閱讀一下 官方文件 或者翻閱其原始碼。

References

https://github.com/googlei18n/libphonenumber

https://github.com/daviddrysdale/python-phonenumbers

對抗久坐職業傷害

研究指出每天增加 2 小時坐著的時間,會增加大腸癌、心臟疾病、肺癌的風險,也造成肩頸、腰背疼痛等常見問題。

然而對抗這些問題,卻只需要工作時定期休息跟伸展身體即可!

你想輕鬆改變現狀嗎?試試看我們的 PomodoRoll 番茄鐘吧! PomodoRoll 番茄鐘會根據你所設定的專注時間,定期建議你 1 項辦公族適用的伸展運動,幫助你打敗久坐所帶來的傷害!

贊助我們的創作

看完這篇文章了嗎? 休息一下,喝杯咖啡吧!

如果你覺得 MyApollo 有讓你獲得實用的資訊,希望能看到更多的技術分享,邀請你贊助我們一杯咖啡,讓我們有更多的動力與精力繼續提供高品質的文章,感謝你的支持!