[Zope3-Users] schema.List validation does not accept PersistentList

Leonardo Rochael leo at enfoldsystems.com
Thu Jul 19 09:47:57 EDT 2007

Hi Alex,

Alek Kowalczyk wrote:
> I have a schema with the List field defined:
> from zope.interface import Interface
> from zope.schema import List, TextLine
> class IMyObject(Interface):
>    myList = List(title=u'mylist', value_type=TextLine(title=u'item'))
> Then I implement this using field property. 
> Then in constructor I assign a Persistent List to this field.
> from zope.schema.fieldproperty import FieldProperty
> class MyObject(Persistent, Contained):
>    myList = FieldProperty(IMyObject['myList'])
>    def __init__(self):
>       self.myList = PersistentList()
> and I get the following stack trace. 
> Is it intended behavior that schema.List doesn't accept PersistentList? 
> How do you work around that? I don't want to abadon field validation using
> FieldProperty.
>   File "C:\Python24\Lib\site-packages\zope\schema\fieldproperty.py", line
> 52, in
> __set__
>     field.validate(value)
>   File "C:\Python24\Lib\site-packages\zope\schema\_bootstrapfields.py",
> line
> 138, in validate
>     self._validate(value)
>   File "C:\Python24\Lib\site-packages\zope\schema\_field.py", line 358, in
> _validate
>     super(AbstractCollection, self)._validate(value)
>   File "C:\Python24\Lib\site-packages\zope\schema\_bootstrapfields.py",
> line
> 263, in _validate
>     super(MinMaxLen, self)._validate(value)
>   File "C:\Python24\Lib\site-packages\zope\schema\_bootstrapfields.py",
> line
> 201, in _validate
>     super(Iterable, self)._validate(value)
>   File "C:\Python24\Lib\site-packages\zope\schema\_bootstrapfields.py",
> line
> 189, in _validate
>     super(Container, self)._validate(value)
>   File "C:\Python24\Lib\site-packages\zope\schema\_bootstrapfields.py",
> line
> 165, in _validate
>     raise WrongType(value, self._type)
> WrongType: ([], <type 'list'>)

This happens because of the following snippet in the Field base class:

    def _validate(self, value):
        if self._type is not None and not isinstance(value, self._type):
            raise WrongType(value, self._type)

        if not self.constraint(value):
            raise ConstraintNotSatisfied(value)

As it happens, PersistentList is not an instance of "list". Proponents of
strong dynamically-typed OO would complain that this code is forcing the
comingling of the "type" concept (a.k.a. interface) into the concept of
class inheritance (just the other day, Luciano was complaining of the
Javaification of zope.schema exaclty because of this piece of code, when he
tried to use the List field with a tuple value).

The solution is for you to define your own schema field for this:

class PersistentListField(List):

    _type = PersistentList

And use the above in your schema instead of List. You should get the same
widget associatinos as PersistentListField will inherit all List interfaces

View this message in context: http://www.nabble.com/schema.List-validation-does-not-accept-PersistentList-tf4109785.html#a11689717
Sent from the Zope3 - users mailing list archive at Nabble.com.

More information about the Zope3-users mailing list