web/test/unittest_web.py
changeset 11057 0b59724cb3f2
parent 11052 058bb3dc685f
child 11058 23eb30449fe5
equal deleted inserted replaced
11052:058bb3dc685f 11057:0b59724cb3f2
     1 # copyright 2003-2014 LOGILAB S.A. (Paris, FRANCE), all rights reserved.
       
     2 # contact http://www.logilab.fr/ -- mailto:contact@logilab.fr
       
     3 #
       
     4 # This file is part of CubicWeb.
       
     5 #
       
     6 # CubicWeb is free software: you can redistribute it and/or modify it under the
       
     7 # terms of the GNU Lesser General Public License as published by the Free
       
     8 # Software Foundation, either version 2.1 of the License, or (at your option)
       
     9 # any later version.
       
    10 #
       
    11 # CubicWeb is distributed in the hope that it will be useful, but WITHOUT
       
    12 # ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
       
    13 # FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more
       
    14 # details.
       
    15 #
       
    16 # You should have received a copy of the GNU Lesser General Public License along
       
    17 # with CubicWeb.  If not, see <http://www.gnu.org/licenses/>.
       
    18 
       
    19 from json import loads
       
    20 from os.path import join
       
    21 import tempfile
       
    22 
       
    23 try:
       
    24     import requests
       
    25     assert [int(n) for n in requests.__version__.split('.', 2)][:2] >= [1, 2]
       
    26 except (ImportError, AssertionError):
       
    27     requests = None
       
    28 
       
    29 from logilab.common.testlib import TestCase, unittest_main
       
    30 from cubicweb.devtools.httptest import CubicWebServerTC
       
    31 from cubicweb.devtools.fake import FakeRequest
       
    32 
       
    33 class AjaxReplaceUrlTC(TestCase):
       
    34 
       
    35     def test_ajax_replace_url_1(self):
       
    36         self._test_arurl("fname=view&rql=Person%20P&vid=list",
       
    37                          rql='Person P', vid='list')
       
    38 
       
    39     def test_ajax_replace_url_2(self):
       
    40         self._test_arurl("age=12&fname=view&name=bar&rql=Person%20P&vid=oneline",
       
    41                          rql='Person P', vid='oneline', name='bar', age=12)
       
    42 
       
    43     def _test_arurl(self, qs, **kwargs):
       
    44         req = FakeRequest()
       
    45         arurl = req.ajax_replace_url
       
    46         # NOTE: for the simplest use cases, we could use doctest
       
    47         url = arurl('foo', **kwargs)
       
    48         self.assertTrue(url.startswith('javascript:'))
       
    49         self.assertTrue(url.endswith('()'))
       
    50         cbname = url.split()[1][:-2]
       
    51         self.assertMultiLineEqual(
       
    52             'function %s() { $("#foo").loadxhtml("http://testing.fr/cubicweb/ajax?%s",'
       
    53             '{pageid: "%s"},"get","replace"); }' %
       
    54             (cbname, qs, req.pageid),
       
    55             req.html_headers.post_inlined_scripts[0])
       
    56 
       
    57 
       
    58 class FileUploadTC(CubicWebServerTC):
       
    59 
       
    60     def setUp(self):
       
    61         "Skip whole test class if a suitable requests module is not available"
       
    62         if requests is None:
       
    63             self.skipTest('Python ``requests`` module is not available')
       
    64         super(FileUploadTC, self).setUp()
       
    65 
       
    66     @property
       
    67     def _post_url(self):
       
    68         with self.admin_access.web_request() as req:
       
    69             return req.build_url('ajax', fname='fileupload')
       
    70 
       
    71     def _fobject(self, fname):
       
    72         return open(join(self.datadir, fname), 'rb')
       
    73 
       
    74     def _fcontent(self, fname):
       
    75         return self._fobject(fname).read()
       
    76 
       
    77     def test_single_file_upload(self):
       
    78         files = {'file': ('schema.py', self._fobject('schema.py'))}
       
    79         webreq = requests.post(self._post_url, files=files)
       
    80         # check backward compat : a single uploaded file leads to a single
       
    81         # 2-uple in the request form
       
    82         expect = {'fname': u'fileupload',
       
    83                   'file': ['schema.py', self._fcontent('schema.py')]}
       
    84         self.assertEqual(webreq.status_code, 200)
       
    85         self.assertDictEqual(expect, loads(webreq.content))
       
    86 
       
    87     def test_multiple_file_upload(self):
       
    88         files = [('files', ('schema.py', self._fobject('schema.py'))),
       
    89                  ('files', ('views.py',  self._fobject('views.py')))]
       
    90         webreq = requests.post(self._post_url, files=files,)
       
    91         expect = {'fname': u'fileupload',
       
    92                   'files': [['schema.py', self._fcontent('schema.py')],
       
    93                             ['views.py', self._fcontent('views.py')]],}
       
    94         self.assertEqual(webreq.status_code, 200)
       
    95         self.assertDictEqual(expect, loads(webreq.content))
       
    96 
       
    97 
       
    98 class LanguageTC(CubicWebServerTC):
       
    99 
       
   100     def test_language_neg(self):
       
   101         headers = {'Accept-Language': 'fr'}
       
   102         webreq = self.web_request(headers=headers)
       
   103         self.assertIn('lang="fr"', webreq.read())
       
   104         vary = [h.lower().strip() for h in webreq.getheader('Vary').split(',')]
       
   105         self.assertIn('accept-language', vary)
       
   106         headers = {'Accept-Language': 'en'}
       
   107         webreq = self.web_request(headers=headers)
       
   108         self.assertIn('lang="en"', webreq.read())
       
   109         vary = [h.lower().strip() for h in webreq.getheader('Vary').split(',')]
       
   110         self.assertIn('accept-language', vary)
       
   111 
       
   112     def test_response_codes(self):
       
   113         with self.admin_access.client_cnx() as cnx:
       
   114             admin_eid = cnx.user.eid
       
   115         # guest can't see admin
       
   116         webreq = self.web_request('/%d' % admin_eid)
       
   117         self.assertEqual(webreq.status, 403)
       
   118 
       
   119         # but admin can
       
   120         self.web_login()
       
   121         webreq = self.web_request('/%d' % admin_eid)
       
   122         self.assertEqual(webreq.status, 200)
       
   123 
       
   124     def test_session_cookie_httponly(self):
       
   125         webreq = self.web_request()
       
   126         self.assertIn('HttpOnly', webreq.getheader('set-cookie'))
       
   127 
       
   128 
       
   129 class MiscOptionsTC(CubicWebServerTC):
       
   130     @classmethod
       
   131     def setUpClass(cls):
       
   132         super(MiscOptionsTC, cls).setUpClass()
       
   133         cls.logfile = tempfile.NamedTemporaryFile()
       
   134 
       
   135     def setUp(self):
       
   136         super(MiscOptionsTC, self).setUp()
       
   137         self.config.global_set_option('query-log-file', self.logfile.name)
       
   138         self.config.global_set_option('datadir-url', '//static.testing.fr/')
       
   139         # call load_configuration again to let the config reset its datadir_url
       
   140         self.config.load_configuration()
       
   141 
       
   142     def test_log_queries(self):
       
   143         self.web_request()
       
   144         self.assertTrue(self.logfile.read())
       
   145 
       
   146     def test_datadir_url(self):
       
   147         webreq = self.web_request()
       
   148         self.assertNotIn('/data/', webreq.read())
       
   149 
       
   150     @classmethod
       
   151     def tearDownClass(cls):
       
   152         super(MiscOptionsTC, cls).tearDownClass()
       
   153         cls.logfile.close()
       
   154 
       
   155 
       
   156 if __name__ == '__main__':
       
   157     unittest_main()