[views] Display attributes in entity creation form based on "add" permission
Previously, the "update" permission was used. Hence in case the latter is
more restrictive that the "add" permission, an user may not be able to set
such an attribute, despite she may have "add" permission on it.
As a result of the change of permissions action in `editable_attributes`
method (add/update depending on whether the entity is being created or
modified), the "eid" attribute would have shown up in the edition form. To
avoid this, it is moved in the "hidden" section (where it should arguably
belong anyways).
Closes #4342844.
--- a/web/test/data/schema.py Thu Sep 18 11:03:39 2014 +0200
+++ b/web/test/data/schema.py Thu Sep 11 16:43:20 2014 +0200
@@ -43,7 +43,11 @@
class Personne(EntityType):
nom = String(fulltextindexed=True, required=True, maxsize=64)
prenom = String(fulltextindexed=True, maxsize=64)
- sexe = String(maxsize=1, default='M')
+ sexe = String(maxsize=1, default='M',
+ __permissions__={
+ 'read': ('managers', 'users', 'guests',),
+ 'add': ('managers', 'users'),
+ 'update': ('managers', )})
promo = String(vocabulary=('bon','pasbon'))
titre = String(fulltextindexed=True, maxsize=128)
ass = String(maxsize=128)
--- a/web/test/unittest_views_editforms.py Thu Sep 18 11:03:39 2014 +0200
+++ b/web/test/unittest_views_editforms.py Thu Sep 11 16:43:20 2014 +0200
@@ -148,6 +148,26 @@
self.vreg['forms'].select('edition', req, entity=rset.get_entity(0, 0))
self.assertFalse(any(f for f in form.fields if f is None))
+ def test_attribute_add_permissions(self):
+ # https://www.cubicweb.org/ticket/4342844
+ with self.admin_access.repo_cnx() as cnx:
+ self.create_user(cnx, 'toto')
+ cnx.commit()
+ with self.new_access('toto').web_request() as req:
+ e = self.vreg['etypes'].etype_class('Personne')(req)
+ cform = self.vreg['forms'].select('edition', req, entity=e)
+ self.assertIn('sexe',
+ [rschema.type
+ for rschema, _ in cform.editable_attributes()])
+ with self.new_access('toto').repo_cnx() as cnx:
+ person_eid = cnx.create_entity('Personne', nom=u'Robert').eid
+ cnx.commit()
+ person = req.entity_from_eid(person_eid)
+ mform = self.vreg['forms'].select('edition', req, entity=person)
+ self.assertNotIn('sexe',
+ [rschema.type
+ for rschema, _ in mform.editable_attributes()])
+
class FormViewsTC(CubicWebTC):
--- a/web/views/autoform.py Thu Sep 18 11:03:39 2014 +0200
+++ b/web/views/autoform.py Thu Sep 11 16:43:20 2014 +0200
@@ -844,9 +844,9 @@
return [(schema[rtype], role) for rtype, role in self.display_fields]
if self.edited_entity.has_eid() and not self.edited_entity.cw_has_perm('update'):
return []
- # XXX we should simply put eid in the generated section, no?
+ action = 'update' if self.edited_entity.has_eid() else 'add'
return [(rtype, role) for rtype, _, role in self._relations_by_section(
- 'attributes', 'update', strict)]
+ 'attributes', action, strict)]
def editable_relations(self):
"""return a sorted list of (relation's label, relation'schema, role) for
@@ -988,7 +988,7 @@
_AFS = uicfg.autoform_section
# use primary and not generated for eid since it has to be an hidden
-_AFS.tag_attribute(('*', 'eid'), 'main', 'attributes')
+_AFS.tag_attribute(('*', 'eid'), 'main', 'hidden')
_AFS.tag_attribute(('*', 'eid'), 'muledit', 'attributes')
_AFS.tag_attribute(('*', 'description'), 'main', 'attributes')
_AFS.tag_attribute(('*', 'has_text'), 'main', 'hidden')
--- a/web/views/uicfg.py Thu Sep 18 11:03:39 2014 +0200
+++ b/web/views/uicfg.py Thu Sep 11 16:43:20 2014 +0200
@@ -332,7 +332,7 @@
assert section in ('attributes', 'metadata', 'hidden')
relpermission = 'add'
else:
- assert section not in ('attributes', 'metadata', 'hidden')
+ assert section not in ('metadata', 'hidden')
relpermission = permission
for rschema, targetschemas, role in eschema.relation_definitions(True):
_targetschemas = []