- If you use a schema with deferred `validator, missing` or

``default`` attributes, but you use it to perform serialization and
  deserialization without calling its ``bind`` method:

  - If ``validator`` is deferred, no validation will be performed.

  - If ``missing`` is deferred, the field will be considered *required*.

  - If ``default`` is deferred, the serialization default will be
    assumed to be ``colander.null``.
This commit is contained in:
Chris McDonough
2010-10-06 21:34:16 +00:00
parent 6d0737e9fa
commit 2f4e389cbe
4 changed files with 56 additions and 1 deletions

View File

@@ -10,6 +10,18 @@ Changes
- Added Spanish locale: thanks to Douglas Cerna for the translations!
- If you use a schema with deferred ``validator``, ``missing`` or
``default`` attributes, but you use it to perform serialization and
deserialization without calling its ``bind`` method:
- If ``validator`` is deferred, no validation will be performed.
- If ``missing`` is deferred, the field will be considered *required*.
- If ``default`` is deferred, the serialization default will be
assumed to be ``colander.null``.
0.8 (2010/09/08)
-----------------

View File

@@ -1220,6 +1220,8 @@ class SchemaNode(object):
A return value of ``True`` implies that a ``missing`` value
wasn't specified for this node. A return value of ``False``
implies that a ``missing`` value was specified for this node."""
if isinstance(self.missing, deferred): # unbound schema with deferreds
return True
return self.missing is _marker
def serialize(self, appstruct=null):
@@ -1236,6 +1238,8 @@ class SchemaNode(object):
"""
if appstruct is null:
appstruct = self.default
if isinstance(appstruct, deferred): # unbound schema with deferreds
appstruct = null
cstruct = self.typ.serialize(self, appstruct)
return cstruct
@@ -1262,11 +1266,14 @@ class SchemaNode(object):
appstruct = self.missing
if appstruct is _marker:
raise Invalid(self, _('Required'))
if isinstance(appstruct, deferred): # unbound schema with deferreds
raise Invalid(self, _('Required'))
# We never deserialize or validate the missing value
return appstruct
appstruct = self.typ.deserialize(self, cstruct)
if self.validator is not None:
if not isinstance(self.validator, deferred): # unbound
self.validator(self, appstruct)
return appstruct

View File

@@ -1322,6 +1322,11 @@ class TestSchemaNode(unittest.TestCase):
node = self._makeOne(None, missing=1)
self.assertEqual(node.required, False)
def test_required_deferred(self):
from colander import deferred
node = self._makeOne(None, missing=deferred('123'))
self.assertEqual(node.required, True)
def test_deserialize_no_validator(self):
typ = DummyType()
node = self._makeOne(typ)
@@ -1362,6 +1367,15 @@ class TestSchemaNode(unittest.TestCase):
node.missing = null
self.assertEqual(node.deserialize(null), null)
def test_deserialize_appstruct_deferred(self):
from colander import null
from colander import deferred
from colander import Invalid
typ = DummyType()
node = self._makeOne(typ)
node.missing = deferred('123')
self.assertRaises(Invalid, node.deserialize, null)
def test_serialize(self):
typ = DummyType()
node = self._makeOne(typ)
@@ -1389,6 +1403,14 @@ class TestSchemaNode(unittest.TestCase):
node.default = 'abc'
self.assertEqual(node.serialize(), 'abc')
def test_serialize_default_deferred(self):
from colander import deferred
from colander import null
typ = DummyType()
node = self._makeOne(typ)
node.default = deferred('abc')
self.assertEqual(node.serialize(), null)
def test_add(self):
node = self._makeOne(None)
node.add(1)

View File

@@ -237,6 +237,20 @@ will be the set of keywords passed to the ``bind`` method. It usually
operates on the ``node`` it is passed using the API methods described
in :class:`SchemaNode`.
Unbound Schemas With Deferreds
------------------------------
If you use a schema with deferred ``validator``, ``missing`` or
``default`` attributes, but you use it to perform serialization and
deserialization without calling its ``bind`` method:
- If ``validator`` is deferred, no validation will be performed.
- If ``missing`` is deferred, the field will be considered *required*.
- If ``default`` is deferred, the serialization default will be
assumed to be ``colander.null``.
See Also
--------