Repository: python-babel/babel
Pull request #523 (2017-09-09 09:31:49)

modified normalize_locale and exists to handle various unexpected input
made normalize_locale and exists to handle various unexpected input such as list or None just like currency, and added test cases in test_localedata.py
resolves: #521

codecov-io: # [Codecov](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=h1) Report
> Merging [#523](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=desc) into [master](https://codecov.io/gh/python-babel/babel/commit/c7729ccbce85e5736a9a7de18321872dd1ed09d5?src=pr&el=desc) will **decrease** coverage by `1.35%`.
> The diff coverage is `100%`.

[![Impacted file tree graph](https://codecov.io/gh/python-babel/babel/pull/523/graphs/tree.svg?width=650&height=150&src=pr&token=lEYaWCjCnu)](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree)

```diff
@@            Coverage Diff             @@
##           master     #523      +/-   ##
==========================================
- Coverage   90.19%   88.84%   -1.36%     
==========================================
  Files          24       24              
  Lines        4020     4024       +4     
==========================================
- Hits         3626     3575      -51     
- Misses        394      449      +55
```


| [Impacted Files](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree) | Coverage Δ | |
|---|---|---|
| [babel/localedata.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvbG9jYWxlZGF0YS5weQ==) | `94.82% <100%> (-0.71%)` | :arrow_down: |
| [babel/\_compat.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvX2NvbXBhdC5weQ==) | `53.48% <0%> (-46.52%)` | :arrow_down: |
| [babel/localtime/\_unix.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvbG9jYWx0aW1lL191bml4LnB5) | `11.53% <0%> (-20.52%)` | :arrow_down: |
| [babel/localtime/\_win32.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvbG9jYWx0aW1lL193aW4zMi5weQ==) | `59.25% <0%> (-3.71%)` | :arrow_down: |
| [babel/localtime/\_\_init\_\_.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvbG9jYWx0aW1lL19faW5pdF9fLnB5) | `62.5% <0%> (-2.5%)` | :arrow_down: |
| [babel/messages/catalog.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvbWVzc2FnZXMvY2F0YWxvZy5weQ==) | `92.23% <0%> (-2.39%)` | :arrow_down: |
| [babel/util.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvdXRpbC5weQ==) | `90.78% <0%> (-1.32%)` | :arrow_down: |
| [babel/messages/extract.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvbWVzc2FnZXMvZXh0cmFjdC5weQ==) | `94.18% <0%> (-1.1%)` | :arrow_down: |
| [babel/support.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvc3VwcG9ydC5weQ==) | `82.28% <0%> (-0.4%)` | :arrow_down: |
| [babel/messages/pofile.py](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=tree#diff-YmFiZWwvbWVzc2FnZXMvcG9maWxlLnB5) | `96.38% <0%> (-0.37%)` | :arrow_down: |

------

[Continue to review full report at Codecov](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=continue).
> **Legend** - [Click here to learn more](https://docs.codecov.io/docs/codecov-delta)
> `Δ = absolute <relative> (impact)`, `ø = not affected`, `? = missing data`
> Powered by [Codecov](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=footer). Last update [c7729cc...0e53f2f](https://codecov.io/gh/python-babel/babel/pull/523?src=pr&el=lastupdated). Read the [comment docs](https://docs.codecov.io/docs/pull-request-comments).


Patch:
diff --git a/babel/localedata.py b/babel/localedata.py
index 4658221..ae21547 100644
--- a/babel/localedata.py
+++ b/babel/localedata.py
@@ -18,7 +18,7 @@ from collections import MutableMapping
 from itertools import chain
 import sys
 
-from babel._compat import pickle
+from babel._compat import pickle, string_types
 
 
 def get_base_dir():
@@ -41,6 +41,8 @@ def normalize_locale(name):
     Returns the normalized locale ID string or `None` if the ID is not
     recognized.
     """
+    if not name or not isinstance(name, string_types):
+        return None
     name = name.strip().lower()
     for locale_id in chain.from_iterable([_cache, locale_identifiers()]):
         if name == locale_id.lower():
@@ -54,6 +56,8 @@ def exists(name):
 
     :param name: the locale identifier string
     """
+    if not name or not isinstance(name, string_types):
+        return False
     if name in _cache:
         return True
     file_found = os.path.exists(os.path.join(_dirname, '%s.dat' % name))


Test patch:
diff --git a/tests/test_localedata.py b/tests/test_localedata.py
index 62ad93c..3599b21 100644
--- a/tests/test_localedata.py
+++ b/tests/test_localedata.py
@@ -16,8 +16,7 @@ import random
 from operator import methodcaller
 import sys
 
-from babel import localedata
-
+from babel import localedata, numbers
 
 class MergeResolveTestCase(unittest.TestCase):
 
@@ -80,7 +79,6 @@ def test_locale_identification():
     for l in localedata.locale_identifiers():
         assert localedata.exists(l)
 
-
 def test_unique_ids():
     # Check all locale IDs are uniques.
     all_ids = localedata.locale_identifiers()
@@ -106,3 +104,16 @@ def test_pi_support_frozen(monkeypatch):
 def test_pi_support_not_frozen():
     assert not getattr(sys, 'frozen', False)
     assert localedata.get_base_dir().endswith('babel')
+
+def test_locale_argument_acceptance():
+    # Testing None input.
+    normalized_locale = localedata.normalize_locale(None)
+    assert normalized_locale == None
+    locale_exist = localedata.exists(None)
+    assert locale_exist == False
+
+    # # Testing list input.
+    normalized_locale = localedata.normalize_locale(['en_us', None])
+    assert normalized_locale == None
+    locale_exist = localedata.exists(['en_us', None])
+    assert locale_exist == False