refactoring field processing: class FieldInstance for processing and collecting state information

git-svn-id: svn://svn.cy55.de/Zope3/src/cybertools/trunk@1971 fd906abe-77d9-0310-91a1-e0d9ade77398
This commit is contained in:
helmutm 2007-08-30 07:53:09 +00:00
parent 18ea13f7b8
commit 90377b06b9
5 changed files with 61 additions and 54 deletions

View file

@ -10,4 +10,6 @@
<adapter factory="cybertools.composer.schema.instance.ClientInstanceEditor"
name="editor" />
<adapter factory="cybertools.composer.schema.field.FieldInstance" />
</configure>

View file

@ -23,9 +23,10 @@ $Id$
"""
from zope.interface import implements
from zope.component import adapts
from cybertools.composer.base import Component
from cybertools.composer.schema.interfaces import IField, IFieldState
from cybertools.composer.schema.interfaces import IField, IFieldInstance
from cybertools.composer.schema.schema import formErrors
from cybertools.util.format import toStr, toUnicode
@ -53,6 +54,19 @@ class Field(Component):
def getTitleValue(self):
return self.title or self.name
class FieldInstance(object):
implements(IFieldInstance)
adapts(IField)
def __init__(self, context):
self.context = context
self.name = self.__name__ = context.name
self.errors = []
self.severity = 0
self.change = None
def marshall(self, value):
return value
#return toStr(value)
@ -64,23 +78,11 @@ class Field(Component):
def unmarshall(self, strValue):
return toUnicode(strValue) or u''
def validateValue(self, value):
def validate(self, value):
errors = []
severity = 0
if not value and self.required:
if not value and self.context.required:
error = formErrors['required_missing']
errors.append(error)
severity = error.severity
return FieldState(self.name, errors, severity)
class FieldState(object):
implements(IFieldState)
def __init__(self, name, errors=[], severity=0, change=None):
self.name = self.__name__ = name
self.errors = errors
self.severity = severity
self.change = change
self.errors.append(error)
self.severity = error.severity

View file

@ -28,7 +28,7 @@ from zope.interface import implements
from cybertools.composer.instance import Instance
from cybertools.composer.interfaces import IInstance
from cybertools.composer.schema.interfaces import IClient
from cybertools.composer.schema.interfaces import IClient, IFieldInstance
from cybertools.composer.schema.schema import FormState
@ -75,9 +75,10 @@ class ClientInstance(object):
values = attrs.setdefault(self.aspect, {})
if template is not None:
for f in template.fields:
fi = IFieldInstance(f)
name = f.name
value = values.get(name, u'')
value = mode == 'view' and f.display(value) or f.marshall(value)
value = mode == 'view' and fi.display(value) or fi.marshall(value)
result[name] = value
result['__name__'] = self.context.__name__
return result
@ -103,23 +104,25 @@ class ClientInstanceEditor(ClientInstance):
setattr(self.context, self.attrsName, attrs)
values = attrs.setdefault(self.aspect, OOBTree())
for f in template.fields:
#fi = IFieldInstance(f)
name = f.name
fieldState = formState.fieldStates[name]
value = f.unmarshall(data.get(name))
fi = formState.fieldInstances[name]
value = fi.unmarshall(data.get(name))
if name in data:
oldValue = values.get(name)
if value != oldValue:
values[name] = value
fieldState.change = (oldValue, value)
fi.change = (oldValue, value)
formState.changed = True
return formState
def validate(self, data):
formState = FormState()
for f in self.template.fields:
value = f.unmarshall(data.get(f.name))
fieldState = f.validateValue(value)
formState.fieldStates.append(fieldState)
formState.severity = max(formState.severity, fieldState.severity)
fi = IFieldInstance(f)
value = fi.unmarshall(data.get(f.name))
fi.validate(value)
formState.fieldInstances.append(fi)
formState.severity = max(formState.severity, fi.severity)
return formState

View file

@ -99,32 +99,12 @@ class IField(IComponent):
'(only for type textarea)'),
default=3,
required=False,)
# validator = schema.Text(),
# marshaller = schema.Text(),
def marshallValue(value):
""" Return a string (possibly unicode) representation of the
value given that may be used for editing.
"""
def displayValue(value):
""" Return a string (possibly unicode) representation of the
value given that may be used for presentation.
"""
def unmarshallValue(strValue):
""" Return the internal (real) value corresponding to the string
value given.
"""
def validateValue(value):
""" Check if the value given is valid. Return an object implementing
IFieldState.
"""
class IFieldState(Interface):
""" Represents the state of a field used for editing.
class IFieldInstance(Interface):
""" An adapter for checking and converting data values coming
from or being displayed on an external system (like a browser form).
It also keeps information on the processing state.
"""
name = Attribute('Field name.')
@ -133,15 +113,35 @@ class IFieldState(Interface):
severity = Attribute("An integer giving a state or error "
"code, 0 meaning 'OK'.")
def marshall(value):
""" Return a string (possibly unicode) representation of the
value given that may be used for editing.
"""
def display(value):
""" Return a string (possibly unicode) representation of the
value given that may be used for presentation.
"""
def unmarshall(strValue):
""" Return the internal (real) value corresponding to the string
value given.
"""
def validate(value):
""" Check if the value given is valid. Return an object implementing
IFieldState.
"""
class IFormState(Interface):
""" Represents the state of all fields when editing.
"""
fieldStates = Attribute('A mapping ``{fieldName: fieldState, ...}``.')
changed = Attribute('True if one of the fields has been changed or False.')
changed = Attribute('True if one of the fields has been changed')
severity = Attribute("An integer giving an overall state or error "
"code, typically the maximum of the field states' "
"code, typically the maximum of the field instances' "
"severities.")

View file

@ -64,8 +64,8 @@ class FormState(object):
implements(IFormState)
def __init__(self, fieldStates=[], changed=False, severity=0):
self.fieldStates = Jeep(fieldStates)
def __init__(self, fieldInstances=[], changed=False, severity=0):
self.fieldInstances = Jeep(fieldInstances)
self.changed = changed
self.severity = severity