37 from logilab.common.umessage import message_from_string |
37 from logilab.common.umessage import message_from_string |
38 from logilab.common.decorators import cached, classproperty, clear_cache, iclassmethod |
38 from logilab.common.decorators import cached, classproperty, clear_cache, iclassmethod |
39 from logilab.common.deprecation import deprecated, class_deprecated |
39 from logilab.common.deprecation import deprecated, class_deprecated |
40 from logilab.common.shellutils import getlogin |
40 from logilab.common.shellutils import getlogin |
41 |
41 |
42 from cubicweb import ValidationError, NoSelectableObject, AuthenticationError |
42 from cubicweb import (ValidationError, NoSelectableObject, AuthenticationError, |
43 from cubicweb import cwconfig, dbapi, devtools, web, server, repoapi |
43 ProgrammingError) |
|
44 from cubicweb import cwconfig, devtools, web, server, repoapi |
44 from cubicweb.utils import json |
45 from cubicweb.utils import json |
45 from cubicweb.sobjects import notification |
46 from cubicweb.sobjects import notification |
46 from cubicweb.web import Redirect, application |
47 from cubicweb.web import Redirect, application |
47 from cubicweb.server.hook import SendMailOp |
48 from cubicweb.server.hook import SendMailOp |
48 from cubicweb.server.session import Session |
49 from cubicweb.server.session import Session |
154 |
155 |
155 cwconfig.SMTP = MockSMTP |
156 cwconfig.SMTP = MockSMTP |
156 |
157 |
157 |
158 |
158 class TestCaseConnectionProxy(object): |
159 class TestCaseConnectionProxy(object): |
159 """thin wrapper around `cubicweb.dbapi.Connection` context-manager |
160 """thin wrapper around `cubicweb.repoapi.ClientConnection` context-manager |
160 used in CubicWebTC (cf. `cubicweb.devtools.testlib.CubicWebTC.login` method) |
161 used in CubicWebTC (cf. `cubicweb.devtools.testlib.CubicWebTC.login` method) |
161 |
162 |
162 It just proxies to the default connection context manager but |
163 It just proxies to the default connection context manager but |
163 restores the original connection on exit. |
164 restores the original connection on exit. |
164 """ |
165 """ |
258 attributes: |
259 attributes: |
259 |
260 |
260 * `vreg`, the vregistry |
261 * `vreg`, the vregistry |
261 * `schema`, self.vreg.schema |
262 * `schema`, self.vreg.schema |
262 * `config`, cubicweb configuration |
263 * `config`, cubicweb configuration |
263 * `cnx`, dbapi connection to the repository using an admin user |
264 * `cnx`, repoapi connection to the repository using an admin user |
264 * `session`, server side session associated to `cnx` |
265 * `session`, server side session associated to `cnx` |
265 * `app`, the cubicweb publisher (for web testing) |
266 * `app`, the cubicweb publisher (for web testing) |
266 * `repo`, the repository object |
267 * `repo`, the repository object |
267 * `admlogin`, login of the admin user |
268 * `admlogin`, login of the admin user |
268 * `admpassword`, password of the admin user |
269 * `admpassword`, password of the admin user |
434 @nocoverage |
435 @nocoverage |
435 @deprecated('[3.19] explicitly use RepoAccess object in test instead') |
436 @deprecated('[3.19] explicitly use RepoAccess object in test instead') |
436 def rollback(self): |
437 def rollback(self): |
437 try: |
438 try: |
438 self.cnx.rollback() |
439 self.cnx.rollback() |
439 except dbapi.ProgrammingError: |
440 except ProgrammingError: |
440 pass # connection closed |
441 pass # connection closed |
441 finally: |
442 finally: |
442 self.session.set_cnxset() # ensure cnxset still set after commit |
443 self.session.set_cnxset() # ensure cnxset still set after commit |
443 |
444 |
444 @deprecated('[3.19] explicitly use RepoAccess object in test instead') |
445 @deprecated('[3.19] explicitly use RepoAccess object in test instead') |
665 |
666 |
666 * using named argument(s): |
667 * using named argument(s): |
667 |
668 |
668 .. sourcecode:: python |
669 .. sourcecode:: python |
669 |
670 |
670 rdef = self.schema['CWUser'].rdef('login') |
|
671 with self.temporary_permissions(CWUser={'read': ()}): |
671 with self.temporary_permissions(CWUser={'read': ()}): |
672 ... |
672 ... |
673 |
673 |
674 Usually the former will be prefered to override permissions on a |
674 Usually the former will be preferred to override permissions on a |
675 relation definition, while the latter is well suited for entity types. |
675 relation definition, while the latter is well suited for entity types. |
676 |
676 |
677 The allowed keys in the permission dictionary depends on the schema type |
677 The allowed keys in the permission dictionary depend on the schema type |
678 (entity type / relation definition). Resulting permissions will be |
678 (entity type / relation definition). Resulting permissions will be |
679 similar to `orig_permissions.update(partial_perms)`. |
679 similar to `orig_permissions.update(partial_perms)`. |
680 """ |
680 """ |
681 torestore = [] |
681 torestore = [] |
682 for erschema, etypeperms in chain(perm_overrides, perm_kwoverrides.iteritems()): |
682 for erschema, etypeperms in chain(perm_overrides, perm_kwoverrides.iteritems()): |