From 9357d810d8c7c55e0dc4cb03b3dfabbe50f4342f Mon Sep 17 00:00:00 2001 From: cassiobotaro Date: Sat, 2 May 2015 20:24:04 -0300 Subject: [PATCH] Fix List behaviour and added new feature --- gluon/storage.py | 49 +++++++++++++++++-------------------- gluon/tests/test_storage.py | 4 +++ 2 files changed, 27 insertions(+), 26 deletions(-) diff --git a/gluon/storage.py b/gluon/storage.py index 6996d805..cb0dae30 100644 --- a/gluon/storage.py +++ b/gluon/storage.py @@ -269,53 +269,50 @@ class FastStorage(dict): class List(list): + """ Like a regular python list but a[i] if i is out of bounds returns None - instead of `IndexOutOfBounds` + instead of `IndexOutOfBounds`. """ - def __call__(self, i, default=DEFAULT, cast=None, otherwise=None): + def __call__(self, i, default=None, cast=None, otherwise=None): """Allows to use a special syntax for fast-check of `request.args()` validity - Args: i: index default: use this value if arg not found cast: type cast otherwise: can be: - - None: results in a 404 - str: redirect to this address - callable: calls the function (nothing is passed) - Example: You can use:: - request.args(0,default=0,cast=int,otherwise='http://error_url') request.args(0,default=0,cast=int,otherwise=lambda:...) - """ + value = self[i] or default + try: + if cast: + value = cast(value) + if not value and otherwise: + raise ValueError('Otherwise will raised.') + except (ValueError, TypeError): + if otherwise is None: + raise HTTP(404) + elif isinstance(otherwise, str): + redirect(otherwise) + elif callable(otherwise): + return otherwise() + else: + raise RuntimeError("invalid otherwise") + return value + + def __getitem__(self, i): n = len(self) if 0 <= i < n or -n <= i < 0: - value = self[i] - elif default is DEFAULT: - value = None - else: - value, cast = default, False - if cast: - try: - value = cast(value) - except (ValueError, TypeError): - from http import HTTP, redirect - if otherwise is None: - raise HTTP(404) - elif isinstance(otherwise, str): - redirect(otherwise) - elif callable(otherwise): - return otherwise() - else: - raise RuntimeError("invalid otherwise") - return value + return super(List, self).__getitem__(i) + return None if __name__ == '__main__': diff --git a/gluon/tests/test_storage.py b/gluon/tests/test_storage.py index e046506b..804a3fb8 100644 --- a/gluon/tests/test_storage.py +++ b/gluon/tests/test_storage.py @@ -125,8 +125,12 @@ class TestList(unittest.TestCase): def test_listcall(self): a = List((1, 2, 3)) self.assertEqual(a(1), 2) + self.assertEqual(a[1], 2) + self.assertEqual(a(3), None) + self.assertEqual(a[3], None) self.assertEqual(a(-1), 3) self.assertEqual(a(-5), None) + self.assertEqual(a[-5], None) self.assertEqual(a(-5, default='x'), 'x') self.assertEqual(a(-3, cast=str), '1') a.append('1234')