Skip to content

Commit

Permalink
Update metadata.py
Browse files Browse the repository at this point in the history
This would fix plone/plone.app.vocabularies#59, but I'm only floating this change as an idea, hoping for some feedback.

`z3c.form.widget.Widget.update()` passes the result of `creatorsDefault` (which is called by an `IValue` adapter's `get()` method) to `plone.app.z3cform.converters.AjaxSelectWidgetConverter.toWidgetValue()`.

`getSecurityManager().getUser()` returns a regular `<PropertiedUser>` for most requests and thus the return value is a tuple, e.g. `('admin',)`.

However, for ajax requests, e.g. `/++add++MyContentType/++widget++form.widgets.IMyBehavior.behavior_field`, the user is anonymous:

```
(Pdb) user
<SpecialUser 'Anonymous User'>
(Pdb) pp user.__dict__
{'__': '', 'domains': [], 'name': 'Anonymous User', 'roles': ('Anonymous',)}
```

Thus, the return value is the tuple `(None,)`.  This breaks `AjaxSelectWidgets` when the content type includes the Dublin Core behavior or just the ownership field, even though the field itself is a `RelationList` with a `value_type=RelationChoice( source=CatalogSource(portal_type='MyContentType) )`.  In other words, even though the broken field has no need for the item's creator, the creator gets calculated anyway when the request is handled.

The problem with the tuple `(None,)` is that `toWidgetValue()` does not know how to deal with it and so it returns `None` instead of `field.missing_value` as it should.

This could be fixed in at least four different places:

1. plone.app.dexterity.behaviors.metadata.creatorsDefault
2. plone.app.z3cform.converters.AjaxSelectWidgetConverter.toWidgetValue
3. z3c.form.widget.Widget.update
4. have getSecurityManager().getUser() return the logged in user even on Ajax requests.

1. is the origin of the unexpected value, however, I don't know if making it return `None` for anonymous users would make any other code mad.
2. is the place that does not expect a `(None,)` tuple instead of `None`, so this could be fixed by simply adding a check for `(None,)`.
3. is the "middleman" between 1 and 2, so it could convert `(None,)` to `None` before passing it on.
4. I have no idea what this would entail.
  • Loading branch information
fulv authored Aug 6, 2020
1 parent 6e4913b commit 33b98bf
Showing 1 changed file with 1 addition and 1 deletion.
2 changes: 1 addition & 1 deletion plone/app/dexterity/behaviors/metadata.py
Original file line number Diff line number Diff line change
Expand Up @@ -246,7 +246,7 @@ class IOwnership(model.Schema):
def creatorsDefault(data):
user = getSecurityManager().getUser()
# NB: CMF users are UTF-8 encoded bytes, decode them before inserting
return user and (safe_unicode(user.getId()),)
return user and user.getId() and (safe_unicode(user.getId()),)

CreatorsDefaultValue = ComputedWidgetAttribute(
creatorsDefault,
Expand Down

0 comments on commit 33b98bf

Please sign in to comment.