author | Rémi Cardona <remi.cardona@logilab.fr> |
Tue, 22 Sep 2015 15:24:58 +0200 | |
changeset 10730 | 874ac29b515d |
parent 10548 | 2b398e58ea73 |
child 10907 | 9ae707db5265 |
permissions | -rw-r--r-- |
9981
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
1 |
# copyright 2003-2014 LOGILAB S.A. (Paris, FRANCE), all rights reserved. |
5421
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
2 |
# contact http://www.logilab.fr/ -- mailto:contact@logilab.fr |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
3 |
# |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
4 |
# This file is part of CubicWeb. |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
5 |
# |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
6 |
# CubicWeb is free software: you can redistribute it and/or modify it under the |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
7 |
# terms of the GNU Lesser General Public License as published by the Free |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
8 |
# Software Foundation, either version 2.1 of the License, or (at your option) |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
9 |
# any later version. |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
10 |
# |
5424
8ecbcbff9777
replace logilab-common by CubicWeb in disclaimer
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
5421
diff
changeset
|
11 |
# CubicWeb is distributed in the hope that it will be useful, but WITHOUT |
5421
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
12 |
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
13 |
# FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
14 |
# details. |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
15 |
# |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
16 |
# You should have received a copy of the GNU Lesser General Public License along |
8167de96c523
proper licensing information (LGPL-2.1). Hope I get it right this time.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4999
diff
changeset
|
17 |
# with CubicWeb. If not, see <http://www.gnu.org/licenses/>. |
0 | 18 |
"""Security hooks: check permissions to add/delete/update entities according to |
9612
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
19 |
the connected user |
5813
0b250d72fcfa
[transaction w/ separated web/repo processes] the dbapi should explicitly specify a transaction id to avoid confusion when web server / repository run in separated processes
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
5670
diff
changeset
|
20 |
""" |
0 | 21 |
|
22 |
__docformat__ = "restructuredtext en" |
|
9395
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
23 |
from warnings import warn |
0 | 24 |
|
8190
2a3c1b787688
[vreg] move base registry implementation to logilab.common. Closes #1916014
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6426
diff
changeset
|
25 |
from logilab.common.registry import objectify_predicate |
2a3c1b787688
[vreg] move base registry implementation to logilab.common. Closes #1916014
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6426
diff
changeset
|
26 |
|
9129
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
27 |
from yams import buildobjs |
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
28 |
|
0 | 29 |
from cubicweb import Unauthorized |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
30 |
from cubicweb.server import BEFORE_ADD_RELATIONS, ON_COMMIT_ADD_RELATIONS, hook |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
31 |
|
0 | 32 |
|
9395
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
33 |
|
9612
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
34 |
def check_entity_attributes(cnx, entity, action, editedattrs=None): |
0 | 35 |
eid = entity.eid |
36 |
eschema = entity.e_schema |
|
9981
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
37 |
if action == 'delete': |
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
38 |
eschema.check_perm(session, action, eid=eid) |
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
39 |
return |
5557
1a534c596bff
[entity] continue cleanup of Entity/AnyEntity namespace
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
5449
diff
changeset
|
40 |
# ._cw_skip_security_attributes is there to bypass security for attributes |
8238
087bb529035c
[spelling] fix dictionnary -> dictionary typo
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6426
diff
changeset
|
41 |
# set by hooks by modifying the entity's dictionary |
4577
049d92fc8614
[security] we should save back edited_attributes in case of multiple modification of an entity during the same transaction
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4570
diff
changeset
|
42 |
if editedattrs is None: |
6142
8bc6eac1fac1
[session] cleanup hook / operation / entity edition api
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
5849
diff
changeset
|
43 |
editedattrs = entity.cw_edited |
8bc6eac1fac1
[session] cleanup hook / operation / entity edition api
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
5849
diff
changeset
|
44 |
dontcheck = editedattrs.skip_security |
9981
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
45 |
etypechecked = False |
2647
b0a2e779845c
enable server side entity caching, 25% speedup on codenaf insertion. ALL CW TESTS OK
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
1977
diff
changeset
|
46 |
for attr in editedattrs: |
4999
221f76e14eea
don't update dontcheck until everything went fine:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4970
diff
changeset
|
47 |
if attr in dontcheck: |
0 | 48 |
continue |
9521
9eb810333b0f
[hooks/security, devtools/fill] silence yams 0.38.0 warnings
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9129
diff
changeset
|
49 |
rdef = eschema.rdef(attr, takefirst=True) |
9129
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
50 |
if rdef.final: # non final relation are checked by standard hooks |
9395
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
51 |
perms = rdef.permissions.get(action) |
9129
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
52 |
# comparison below works because the default update perm is: |
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
53 |
# |
9395
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
54 |
# ('managers', ERQLExpression(Any X WHERE U has_update_permission X, |
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
55 |
# X eid %(x)s, U eid %(u)s)) |
9129
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
56 |
# |
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
57 |
# is deserialized in this order (groups first), and ERQLExpression |
9395
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
58 |
# implements comparison by rql expression. |
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
59 |
if perms == buildobjs.DEFAULT_ATTRPERMS[action]: |
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
60 |
# The default rule is to delegate to the entity |
9981
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
61 |
# rule. This needs to be checked only once. |
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
62 |
if not etypechecked: |
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
63 |
entity.cw_check_perm(action) |
7099bbd685aa
[hooks/security] allow edition of attributes with permissive permissions
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9536
diff
changeset
|
64 |
etypechecked = True |
9129
6c4ae3a06619
[hooks/security] Streamline attributes default permission check.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
8239
diff
changeset
|
65 |
continue |
9395
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
66 |
if perms == (): |
9412
8aa6c923d6c0
[security] Add comment to check_entity_attributes shortcut
Julien Cristau <julien.cristau@logilab.fr>
parents:
9395
diff
changeset
|
67 |
# That means an immutable attribute; as an optimization, avoid |
8aa6c923d6c0
[security] Add comment to check_entity_attributes shortcut
Julien Cristau <julien.cristau@logilab.fr>
parents:
9395
diff
changeset
|
68 |
# going through check_perm. |
9395
96dba2efd16d
[hooks/security] provide attribute "add" permission
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9254
diff
changeset
|
69 |
raise Unauthorized(action, str(rdef)) |
9612
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
70 |
rdef.check_perm(cnx, action, eid=eid) |
1802
d628defebc17
delete-trailing-whitespace + some copyright update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
479
diff
changeset
|
71 |
|
10153
85cbf16fbb57
[security] Test case and fix for an INSERT security hole
Julien Cristau <julien.cristau@logilab.fr>
parents:
9981
diff
changeset
|
72 |
if action == 'add' and not etypechecked: |
85cbf16fbb57
[security] Test case and fix for an INSERT security hole
Julien Cristau <julien.cristau@logilab.fr>
parents:
9981
diff
changeset
|
73 |
# think about cnx.create_entity('Foo') |
85cbf16fbb57
[security] Test case and fix for an INSERT security hole
Julien Cristau <julien.cristau@logilab.fr>
parents:
9981
diff
changeset
|
74 |
# the standard metadata were inserted by a hook |
85cbf16fbb57
[security] Test case and fix for an INSERT security hole
Julien Cristau <julien.cristau@logilab.fr>
parents:
9981
diff
changeset
|
75 |
# with a bypass ... we conceptually need to check |
85cbf16fbb57
[security] Test case and fix for an INSERT security hole
Julien Cristau <julien.cristau@logilab.fr>
parents:
9981
diff
changeset
|
76 |
# the eid attribute at *creation* time |
85cbf16fbb57
[security] Test case and fix for an INSERT security hole
Julien Cristau <julien.cristau@logilab.fr>
parents:
9981
diff
changeset
|
77 |
entity.cw_check_perm(action) |
1802
d628defebc17
delete-trailing-whitespace + some copyright update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
479
diff
changeset
|
78 |
|
d628defebc17
delete-trailing-whitespace + some copyright update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
479
diff
changeset
|
79 |
|
6426
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
80 |
class CheckEntityPermissionOp(hook.DataOperationMixIn, hook.LateOperation): |
0 | 81 |
def precommit_event(self): |
9612
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
82 |
cnx = self.cnx |
6426
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
83 |
for eid, action, edited in self.get_data(): |
9612
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
84 |
entity = cnx.entity_from_eid(eid) |
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
85 |
check_entity_attributes(cnx, entity, action, edited) |
1802
d628defebc17
delete-trailing-whitespace + some copyright update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
479
diff
changeset
|
86 |
|
d628defebc17
delete-trailing-whitespace + some copyright update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
479
diff
changeset
|
87 |
|
6426
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
88 |
class CheckRelationPermissionOp(hook.DataOperationMixIn, hook.LateOperation): |
0 | 89 |
def precommit_event(self): |
9612
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
90 |
cnx = self.cnx |
6426
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
91 |
for action, rschema, eidfrom, eidto in self.get_data(): |
9612
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
92 |
rdef = rschema.rdef(cnx.entity_metas(eidfrom)['type'], |
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
93 |
cnx.entity_metas(eidto)['type']) |
24460d4d64bf
[hooks/security] let's use a connection, not a session
Julien Cristau <julien.cristau@logilab.fr>
parents:
9543
diff
changeset
|
94 |
rdef.check_perm(cnx, action, fromeid=eidfrom, toeid=eidto) |
1802
d628defebc17
delete-trailing-whitespace + some copyright update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
479
diff
changeset
|
95 |
|
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
96 |
|
8190
2a3c1b787688
[vreg] move base registry implementation to logilab.common. Closes #1916014
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6426
diff
changeset
|
97 |
@objectify_predicate |
4835
13b0b96d7982
[repo] enhanced security handling: deprecates unsafe_execute, in favor of explicit read/write security control using the `enabled_security` context manager. Also code executed on the repository side is now unsafe by default.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4577
diff
changeset
|
98 |
def write_security_enabled(cls, req, **kwargs): |
13b0b96d7982
[repo] enhanced security handling: deprecates unsafe_execute, in favor of explicit read/write security control using the `enabled_security` context manager. Also code executed on the repository side is now unsafe by default.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4577
diff
changeset
|
99 |
if req is None or not req.write_security: |
13b0b96d7982
[repo] enhanced security handling: deprecates unsafe_execute, in favor of explicit read/write security control using the `enabled_security` context manager. Also code executed on the repository side is now unsafe by default.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4577
diff
changeset
|
100 |
return 0 |
13b0b96d7982
[repo] enhanced security handling: deprecates unsafe_execute, in favor of explicit read/write security control using the `enabled_security` context manager. Also code executed on the repository side is now unsafe by default.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4577
diff
changeset
|
101 |
return 1 |
13b0b96d7982
[repo] enhanced security handling: deprecates unsafe_execute, in favor of explicit read/write security control using the `enabled_security` context manager. Also code executed on the repository side is now unsafe by default.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4577
diff
changeset
|
102 |
|
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
103 |
class SecurityHook(hook.Hook): |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
104 |
__abstract__ = True |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
105 |
category = 'security' |
4835
13b0b96d7982
[repo] enhanced security handling: deprecates unsafe_execute, in favor of explicit read/write security control using the `enabled_security` context manager. Also code executed on the repository side is now unsafe by default.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4577
diff
changeset
|
106 |
__select__ = hook.Hook.__select__ & write_security_enabled() |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
107 |
|
0 | 108 |
|
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
109 |
class AfterAddEntitySecurityHook(SecurityHook): |
3376
f5c69485381f
[appobjects] use __regid__ instead of __id__, more explicit
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2968
diff
changeset
|
110 |
__regid__ = 'securityafteraddentity' |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
111 |
events = ('after_add_entity',) |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
112 |
|
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
113 |
def __call__(self): |
6426
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
114 |
CheckEntityPermissionOp.get_instance(self._cw).add_data( |
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
115 |
(self.entity.eid, 'add', self.entity.cw_edited) ) |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
116 |
|
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
117 |
|
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
118 |
class AfterUpdateEntitySecurityHook(SecurityHook): |
3376
f5c69485381f
[appobjects] use __regid__ instead of __id__, more explicit
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2968
diff
changeset
|
119 |
__regid__ = 'securityafterupdateentity' |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
120 |
events = ('after_update_entity',) |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
121 |
|
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
122 |
def __call__(self): |
9254
e1369f2dba79
[hooks/security] Defer entity permission checks to an Operation.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9129
diff
changeset
|
123 |
# save back editedattrs in case the entity is reedited later in the |
e1369f2dba79
[hooks/security] Defer entity permission checks to an Operation.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9129
diff
changeset
|
124 |
# same transaction, which will lead to cw_edited being |
e1369f2dba79
[hooks/security] Defer entity permission checks to an Operation.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9129
diff
changeset
|
125 |
# overwritten |
10114
6f4b4567b77d
[security] check attributes: dispatch on the "add" action if entity was just created
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9984
diff
changeset
|
126 |
action = 'add' if self._cw.added_in_transaction(self.entity.eid) else 'update' |
9254
e1369f2dba79
[hooks/security] Defer entity permission checks to an Operation.
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9129
diff
changeset
|
127 |
CheckEntityPermissionOp.get_instance(self._cw).add_data( |
10114
6f4b4567b77d
[security] check attributes: dispatch on the "add" action if entity was just created
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
9984
diff
changeset
|
128 |
(self.entity.eid, action, self.entity.cw_edited) ) |
0 | 129 |
|
130 |
||
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
131 |
class BeforeDelEntitySecurityHook(SecurityHook): |
3376
f5c69485381f
[appobjects] use __regid__ instead of __id__, more explicit
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2968
diff
changeset
|
132 |
__regid__ = 'securitybeforedelentity' |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
133 |
events = ('before_delete_entity',) |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
134 |
|
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
135 |
def __call__(self): |
5557
1a534c596bff
[entity] continue cleanup of Entity/AnyEntity namespace
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
5449
diff
changeset
|
136 |
self.entity.cw_check_perm('delete') |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
137 |
|
1802
d628defebc17
delete-trailing-whitespace + some copyright update
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents:
479
diff
changeset
|
138 |
|
10388
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
139 |
def skip_inlined_relation_security(cnx, rschema, eid): |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
140 |
"""return True if security for the given inlined relation should be skipped, |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
141 |
in case where the relation has been set through modification of |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
142 |
`entity.cw_edited` in a hook |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
143 |
""" |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
144 |
assert rschema.inlined |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
145 |
try: |
10547
a05a698a12af
[hook] don't open-code Connection.entity_cache
Julien Cristau <julien.cristau@logilab.fr>
parents:
10388
diff
changeset
|
146 |
entity = cnx.entity_cache(eid) |
10388
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
147 |
except KeyError: |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
148 |
return False |
10548
2b398e58ea73
[hook] remove assumption about entity cache vs cw_edited
Julien Cristau <julien.cristau@logilab.fr>
parents:
10547
diff
changeset
|
149 |
edited = getattr(entity, 'cw_edited', None) |
2b398e58ea73
[hook] remove assumption about entity cache vs cw_edited
Julien Cristau <julien.cristau@logilab.fr>
parents:
10547
diff
changeset
|
150 |
if edited is None: |
2b398e58ea73
[hook] remove assumption about entity cache vs cw_edited
Julien Cristau <julien.cristau@logilab.fr>
parents:
10547
diff
changeset
|
151 |
return False |
2b398e58ea73
[hook] remove assumption about entity cache vs cw_edited
Julien Cristau <julien.cristau@logilab.fr>
parents:
10547
diff
changeset
|
152 |
return rschema.type in edited.skip_security |
10388
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
153 |
|
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
154 |
|
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
155 |
class BeforeAddRelationSecurityHook(SecurityHook): |
3376
f5c69485381f
[appobjects] use __regid__ instead of __id__, more explicit
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2968
diff
changeset
|
156 |
__regid__ = 'securitybeforeaddrelation' |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
157 |
events = ('before_add_relation',) |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
158 |
|
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
159 |
def __call__(self): |
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
160 |
if self.rtype in BEFORE_ADD_RELATIONS: |
2968
0e3460341023
somewhat painful backport of 3.5 branch, should mostly be ok
Sylvain Thénault <sylvain.thenault@logilab.fr>
diff
changeset
|
161 |
nocheck = self._cw.transaction_data.get('skip-security', ()) |
0e3460341023
somewhat painful backport of 3.5 branch, should mostly be ok
Sylvain Thénault <sylvain.thenault@logilab.fr>
diff
changeset
|
162 |
if (self.eidfrom, self.rtype, self.eidto) in nocheck: |
0e3460341023
somewhat painful backport of 3.5 branch, should mostly be ok
Sylvain Thénault <sylvain.thenault@logilab.fr>
diff
changeset
|
163 |
return |
2847
c2ee28f4d4b1
use ._cw instead of .cw_req
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2835
diff
changeset
|
164 |
rschema = self._cw.repo.schema[self.rtype] |
10388
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
165 |
if rschema.inlined and skip_inlined_relation_security( |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
166 |
self._cw, rschema, self.eidfrom): |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
167 |
return |
9469
032825bbacab
[multi-sources-removal] Drop entities.source column
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
9395
diff
changeset
|
168 |
rdef = rschema.rdef(self._cw.entity_metas(self.eidfrom)['type'], |
032825bbacab
[multi-sources-removal] Drop entities.source column
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
9395
diff
changeset
|
169 |
self._cw.entity_metas(self.eidto)['type']) |
4190
742e3eb16f81
fix bad merge
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4048
diff
changeset
|
170 |
rdef.check_perm(self._cw, 'add', fromeid=self.eidfrom, toeid=self.eidto) |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
171 |
|
0 | 172 |
|
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
173 |
class AfterAddRelationSecurityHook(SecurityHook): |
3376
f5c69485381f
[appobjects] use __regid__ instead of __id__, more explicit
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2968
diff
changeset
|
174 |
__regid__ = 'securityafteraddrelation' |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
175 |
events = ('after_add_relation',) |
0 | 176 |
|
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
177 |
def __call__(self): |
10388
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
178 |
if self.rtype not in BEFORE_ADD_RELATIONS: |
2968
0e3460341023
somewhat painful backport of 3.5 branch, should mostly be ok
Sylvain Thénault <sylvain.thenault@logilab.fr>
diff
changeset
|
179 |
nocheck = self._cw.transaction_data.get('skip-security', ()) |
0e3460341023
somewhat painful backport of 3.5 branch, should mostly be ok
Sylvain Thénault <sylvain.thenault@logilab.fr>
diff
changeset
|
180 |
if (self.eidfrom, self.rtype, self.eidto) in nocheck: |
0e3460341023
somewhat painful backport of 3.5 branch, should mostly be ok
Sylvain Thénault <sylvain.thenault@logilab.fr>
diff
changeset
|
181 |
return |
2847
c2ee28f4d4b1
use ._cw instead of .cw_req
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2835
diff
changeset
|
182 |
rschema = self._cw.repo.schema[self.rtype] |
10388
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
183 |
if rschema.inlined and skip_inlined_relation_security( |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
184 |
self._cw, rschema, self.eidfrom): |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
185 |
return |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
186 |
if self.rtype in ON_COMMIT_ADD_RELATIONS: |
6426
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
187 |
CheckRelationPermissionOp.get_instance(self._cw).add_data( |
541659c39f6a
[hook/operation] nicer api to achieve same result as set_operation, as described in #1253630
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
6142
diff
changeset
|
188 |
('add', rschema, self.eidfrom, self.eidto) ) |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
189 |
else: |
9469
032825bbacab
[multi-sources-removal] Drop entities.source column
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
9395
diff
changeset
|
190 |
rdef = rschema.rdef(self._cw.entity_metas(self.eidfrom)['type'], |
032825bbacab
[multi-sources-removal] Drop entities.source column
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
9395
diff
changeset
|
191 |
self._cw.entity_metas(self.eidto)['type']) |
4003
b9436fe77c9e
fix bad merge
Sandrine Ribeau <sandrine.ribeau@logilab.fr>
parents:
3890
diff
changeset
|
192 |
rdef.check_perm(self._cw, 'add', fromeid=self.eidfrom, toeid=self.eidto) |
2835
04034421b072
[hooks] major refactoring:
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
2647
diff
changeset
|
193 |
|
4048
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
194 |
|
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
195 |
class BeforeDeleteRelationSecurityHook(SecurityHook): |
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
196 |
__regid__ = 'securitybeforedelrelation' |
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
197 |
events = ('before_delete_relation',) |
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
198 |
|
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
199 |
def __call__(self): |
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
200 |
nocheck = self._cw.transaction_data.get('skip-security', ()) |
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
201 |
if (self.eidfrom, self.rtype, self.eidto) in nocheck: |
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
202 |
return |
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
203 |
rschema = self._cw.repo.schema[self.rtype] |
10388
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
204 |
if rschema.inlined and skip_inlined_relation_security( |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
205 |
self._cw, rschema, self.eidfrom): |
90fcddcce166
when some inlined relation is set using cw_edited, its security shouldn't be checked.
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
10156
diff
changeset
|
206 |
return |
9469
032825bbacab
[multi-sources-removal] Drop entities.source column
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
9395
diff
changeset
|
207 |
rdef = rschema.rdef(self._cw.entity_metas(self.eidfrom)['type'], |
032825bbacab
[multi-sources-removal] Drop entities.source column
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
9395
diff
changeset
|
208 |
self._cw.entity_metas(self.eidto)['type']) |
4190
742e3eb16f81
fix bad merge
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4048
diff
changeset
|
209 |
rdef.check_perm(self._cw, 'delete', fromeid=self.eidfrom, toeid=self.eidto) |
4048
12c4f7e2bed6
had been involontarly dropped
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents:
4003
diff
changeset
|
210 |