summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGael Pasgrimaud <gael@gawel.org>2014-04-16 20:32:11 +0200
committerGael Pasgrimaud <gael@gawel.org>2014-04-16 20:34:04 +0200
commitb31cdebb5655b6e2fe0620d807c2d85f5b0f6c18 (patch)
treee84f68d9c8caaeb9db3f374b30bf49fc5c190480
parentbc5b86cc8c2feef77cd852efe65527148b241a14 (diff)
downloadwebtest-b31cdebb5655b6e2fe0620d807c2d85f5b0f6c18.tar.gz
add authorization property
-rw-r--r--CHANGELOG.rst2
-rw-r--r--docs/testapp.rst11
-rw-r--r--tests/test_authorisation.py41
-rw-r--r--webtest/app.py37
-rw-r--r--webtest/debugapp.py2
5 files changed, 92 insertions, 1 deletions
diff --git a/CHANGELOG.rst b/CHANGELOG.rst
index e8d8f04..54b85dd 100644
--- a/CHANGELOG.rst
+++ b/CHANGELOG.rst
@@ -6,6 +6,8 @@ News
- Fixed #107 Explicit error message when WSGIProxy2 is not installer
+- Fixed #103 Broken "Edit me on GitHub" links in documentation
+
2.0.14 (2014-01-23)
-------------------
diff --git a/docs/testapp.rst b/docs/testapp.rst
index 06bba54..fb7066e 100644
--- a/docs/testapp.rst
+++ b/docs/testapp.rst
@@ -96,6 +96,17 @@ If you want *all* your requests to have this key, do:
app = TestApp(my_app, extra_environ=dict(REMOTE_USER='bob'))
+If you have to use HTTP authorization you can use the ``.authorization``
+property to set the ``HTTP_AUTHORIZATION`` key of the extra_environ
+dictionnary:
+
+.. code-block:: python
+
+ app = TestApp(my_app)
+ app.authorization = ('Basic', ('user', 'password'))
+
+Only Basic auth is supported for now.
+
Testing a non wsgi application
------------------------------
diff --git a/tests/test_authorisation.py b/tests/test_authorisation.py
new file mode 100644
index 0000000..f1f03d9
--- /dev/null
+++ b/tests/test_authorisation.py
@@ -0,0 +1,41 @@
+# -*- coding: utf-8 -*-
+from __future__ import unicode_literals
+from webtest.debugapp import DebugApp
+from tests.compat import unittest
+from base64 import b64decode
+from webtest.compat import to_bytes
+
+import webtest
+
+
+class TestAuthorization(unittest.TestCase):
+
+ def callFUT(self):
+ return webtest.TestApp(DebugApp())
+
+ def test_basic_authorization(self):
+ app = self.callFUT()
+ authorization = ('Basic', ['gawel', 'passwd'])
+ app.authorization = authorization
+
+ self.assertIn('HTTP_AUTHORIZATION', app.extra_environ)
+ self.assertEquals(app.authorization, authorization)
+
+ resp = app.get('/')
+ resp.mustcontain('HTTP_AUTHORIZATION: Basic Z2F3ZWw6cGFzc3dk')
+ header = resp.request.environ['HTTP_AUTHORIZATION']
+ self.assertTrue(header.startswith('Basic '))
+ authtype, value = header.split(' ')
+ auth = (authtype,
+ b64decode(to_bytes(value)).decode('latin1').split(':'))
+ self.assertEquals(authorization, auth)
+
+ app.authorization = None
+ self.assertNotIn('HTTP_AUTHORIZATION', app.extra_environ)
+
+ def test_invalid(self):
+ app = self.callFUT()
+ self.assertRaises(ValueError, app.set_authorization, ())
+ self.assertRaises(ValueError, app.set_authorization, '')
+ self.assertRaises(ValueError, app.set_authorization, ('Basic', ''))
+ self.assertRaises(ValueError, app.set_authorization, ('Basic', ()))
diff --git a/webtest/app.py b/webtest/app.py
index 6acdde1..3a21643 100644
--- a/webtest/app.py
+++ b/webtest/app.py
@@ -17,6 +17,8 @@ import random
import re
import warnings
+from base64 import b64encode
+
from six import StringIO
from six import BytesIO
from six import string_types
@@ -146,6 +148,41 @@ class TestApp(object):
if parser_features:
self.RequestClass.ResponseClass.parser_features = parser_features
+ def get_authorization(self):
+ """Allow to set the HTTP_AUTHORIZATION environ key. Value should looks
+ like ``('Basic', ('user', 'password'))``
+
+ If value is None the the HTTP_AUTHORIZATION is removed
+ """
+ return self.authorization_value
+
+ def set_authorization(self, value):
+ self.authorization_value = value
+ if value is not None:
+ invalid_value = (
+ "You should use a value like ('Basic', ('user', 'password'))"
+ )
+ if isinstance(value, (list, tuple)) and len(value) == 2:
+ authtype, val = value
+ if authtype == 'Basic' and val and \
+ isinstance(val, (list, tuple)):
+ val = ':'.join(list(val))
+ val = b64encode(to_bytes(val)).strip()
+ val = val.decode('latin1')
+ else:
+ raise ValueError(invalid_value)
+ value = str('%s %s' % (authtype, val))
+ else:
+ raise ValueError(invalid_value)
+ self.extra_environ.update({
+ 'HTTP_AUTHORIZATION': value,
+ })
+ else:
+ if 'HTTP_AUTHORIZATION' in self.extra_environ:
+ del self.extra_environ['HTTP_AUTHORIZATION']
+
+ authorization = property(get_authorization, set_authorization)
+
@property
def cookies(self):
return dict([(cookie.name, cookie.value) for cookie in self.cookiejar])
diff --git a/webtest/debugapp.py b/webtest/debugapp.py
index 970f31c..60b4435 100644
--- a/webtest/debugapp.py
+++ b/webtest/debugapp.py
@@ -11,7 +11,7 @@ class DebugApp(object):
"""The WSGI application used for testing"""
def __init__(self, form=None, show_form=False):
- if os.path.isfile(form):
+ if form and os.path.isfile(form):
fd = open(form, 'rb')
self.form = fd.read()
fd.close()