def test_fields(self): form = UserProfileEditForm(self.profile1, self.request) form.update() fields = form.fields.keys() # By default should include all core fields apart from portrait # and recent_contacts for fieldname in schema.getFieldNames(IUserProfile): if fieldname not in ('portrait', 'recent_contacts'): self.assertIn( fieldname, fields, '{0} missing from edit form'.format(fieldname) ) else: self.assertNotIn( fieldname, fields, '{0} in edit form'.format(fieldname) ) # And any additional fields for fieldname in schema.getFieldNames(IUserProfileAdditional): self.assertIn( 'IUserProfileAdditional.{0}'.format(fieldname), fields, '{0} missing from edit form'.format(fieldname) )
def applyProperties(self, userid, data): portal = getToolByName(self.context, 'portal_url').getPortalObject() mt = getToolByName(self.context, 'portal_membership') member = mt.getMemberById(userid) # cache adapters adapters = {} # Set any fields that are simply properties for the new user, rather # than fields to help create the new user register_fields = getFieldNames(IRegisterSchema) + \ getFieldNames(IAddUserSchema) for k, value in data.items(): # skip fields not available in the schema if k in ['login_name', 'user_id']: continue # skip fields that are handled exclusively on user registration and # are not part of personal information form if k in register_fields: continue # get schema adapter schema = self.fields[k].field.interface if schema in adapters: adapter = adapters[schema] else: adapters[schema] = adapter = getAdapter(portal, schema) adapter.context = member adapter.schema = schema # finally set value setattr(adapter, k, value)
def update_properties(self, properties, request=None): # pylint: disable=unused-argument """Document properties updater""" if 'tags' in properties: self.tags = properties.pop('tags', None) for name in getFieldNames(IDocumentVersion) + getFieldNames( IDocumentRoles): if name in properties: properties.pop(name) properties = properties.pop('properties', properties) if properties: self_properties = self.properties or {} self_properties.update(properties) self.properties = self_properties or None
def can_be_division(self): ''' Check if this object can be a division, i.e. has a division field in the schema or in a behavior ''' schema = self.context.getTypeInfo().lookupSchema() if 'is_division' in getFieldNames(schema): return True behavior_assignable = IBehaviorAssignable(self.context) if behavior_assignable: behaviors = behavior_assignable.enumerateBehaviors() for behavior in behaviors: if 'is_division' in getFieldNames(schema): return True return False
def test_getFieldNamesAll(self): names = getFieldNames(ISchemaTestSubclass) self.assertEqual(len(names),4) self.assert_('title' in names) self.assert_('description' in names) self.assert_('spam' in names) self.assert_('foo' in names)
def __init__(self, **kwargs): for k,v in kwargs.items(): if k=='value' and isinstance(v, str): self.value = v.decode('utf=8') continue elif k in getFieldNames(IFilterSpecification): setattr(self, k, v)
def __call__(self): context = self.context data = {} data['document_id'] = context.id data['url'] = context.absolute_url() data['path'] = '/'.join(context.getPhysicalPath()) data['uid'] = context.UID() if base_hasattr(context, 'title') and context.title: data['Title'] = context.title if base_hasattr(context, 'creators'): creator = context.creators[0] user = api.user.get(creator) if user: data['Author'] = user.getProperty('fullname', '') or creator else: data['Author'] = creator if base_hasattr(context, 'description') and context.description: description = context.description.replace('\n', ' ').strip() if description: data['Subject'] = data['Description'] = description if base_hasattr(context, 'subject') and context.subject: keywords = tuple([k.strip() for k in context.subject if k.strip()]) data['Keywords'] = keywords fti = getUtility(IDexterityFTI, name=context.portal_type) schema = fti.lookupSchema() for name in getFieldNames(schema): #@TODO: ignore files data[name] = getattr(context, name, None) return data
def __init__(self, context): self.context = context attributes = {} for name in getFieldNames(IEntity): attributes[name] = getattr(context, name) super(CachableItemForEntity, self).__init__(key='id', attributes=attributes)
def populate_dexterity_type(obj, data): request = getRequest() for schema in get_dexterity_schemas(context=obj): for name in getFieldNames(schema): field = schema[name] autoform_widgets = schema.queryTaggedValue(WIDGETS_KEY, default={}) if name in autoform_widgets: widgetclass = utils.resolveDottedName(autoform_widgets[name]) widget = widgetclass(field, request) else: widget = component.getMultiAdapter((field, request), IFieldWidget) widget.context = obj widget.ignoreRequest = True widget.update() value = widget.value if not value or value in [NOT_CHANGED, NO_VALUE] or \ not IDataConverter(widget).toFieldValue(widget.value): value = get_dummy_dexterity_value(obj, widget, data) if value: dm = component.getMultiAdapter((obj, field), IDataManager) try: dm.set(value) except WrongType: value = IDataConverter(widget).toFieldValue(value) dm.set(value)
def test_getFieldNamesAll(self): names = getFieldNames(ISchemaTestSubclass) self.assertEqual(len(names), 4) self.assertTrue('title' in names) self.assertTrue('description' in names) self.assertTrue('spam' in names) self.assertTrue('foo' in names)
def bindClass(klass, mapper=None): """ attach validation to a sqlalchemy mapped class, based on its implemented schemas, via property validators, taking care to wrap sqlalchemy properties. """ if mapper is None: mapper = getattr(klass, 'mapper') # compile the klass mapper, this will add instrumented attributes to the class # we could alternatively do.. mapper.compile() compiles all extant mappers mapper.compile() # find all the model schemas implemented by the class for iface in interface.implementedBy(klass): if not IIModelInterface.providedBy(iface): continue # for any field in the schema, see if we have an sa property for field_name in schema.getFieldNames(iface): v = klass.__dict__.get(field_name) # if so then wrap it in a field property if not isinstance(v, attributes.InstrumentedAttribute): continue field = iface[field_name] vproperty = ValidatedProperty(field, v, field_name) setattr(klass, field_name, vproperty)
def bindClass( klass, mapper=None ): """ attach validation to a sqlalchemy mapped class, based on its implemented schemas, via property validators, taking care to wrap sqlalchemy properties. """ if mapper is None: mapper = getattr( klass, 'mapper') # compile the klass mapper, this will add instrumented attributes to the class # we could alternatively do.. mapper.compile() compiles all extant mappers mapper.compile() # find all the model schemas implemented by the class for iface in interface.implementedBy( klass ): if not IIModelInterface.providedBy( iface ): continue # for any field in the schema, see if we have an sa property for field_name in schema.getFieldNames( iface ): v = klass.__dict__.get( field_name ) # if so then wrap it in a field property if not isinstance( v, attributes.InstrumentedAttribute): continue field = iface[ field_name ] vproperty = ValidatedProperty( field, v, field_name ) setattr( klass, field_name, vproperty )
def bindClass( klass, mapper=None ): """ insert validated properties into a class based on its primary mapper, and model schemas """ # compile the klass mapper, this will add instrumented attributes to the class # we could alternatively do.. mapper.compile() compiles all extant mappers if mapper is None: mapper = getattr( klass, 'mapper') mapper.compile() # find all the model schemas implemented by the class for iface in providedByInstances( klass ): if not IIModelInterface.providedBy( iface ): continue # for any field in the schema, see if we have an sa property for field_name in schema.getFieldNames( iface ): v = klass.__dict__.get( field_name ) # if so then wrap it in a field property if not isinstance( v, attributes.InstrumentedAttribute): continue field = iface[ field_name ] vproperty = ValidatedProperty( field, v, field_name ) setattr( klass, field_name, vproperty )
def bindClass(klass, mapper=None): """ insert validated properties into a class based on its primary mapper, and model schemas """ # compile the klass mapper, this will add instrumented attributes to the class # we could alternatively do.. mapper.compile() compiles all extant mappers if mapper is None: mapper = getattr(klass, 'mapper') mapper.compile() # find all the model schemas implemented by the class for iface in providedByInstances(klass): if not IIModelInterface.providedBy(iface): continue # for any field in the schema, see if we have an sa property for field_name in schema.getFieldNames(iface): v = klass.__dict__.get(field_name) # if so then wrap it in a field property if not isinstance(v, attributes.InstrumentedAttribute): continue field = iface[field_name] vproperty = ValidatedProperty(field, v, field_name) setattr(klass, field_name, vproperty)
def importRecords(self, node): # May raise ImportError if interface can't be found or KeyError if # attribute is missing. interfaceName = node.attrib.get('interface', None) if interfaceName is None: raise KeyError(u"A <records /> node must have an 'interface' attribute.") prefix = node.attrib.get('prefix', None) # None means use interface.__identifier__ if node.attrib.get('delete') is not None: self.logger.warning(u"The 'delete' attribute of <record /> nodes " u"is deprecated, it should be replaced with " u"'remove'.") remove = node.attrib.get('remove', node.attrib.get('delete', 'false')).lower() == 'true' # May raise ImportError interface = resolve(interfaceName) omit = [] values = [] # Fields that should have their value set as they don't exist yet for child in node: if not isinstance(child.tag, str): continue elif child.tag.lower() == 'omit': if child.text: omit.append(unicode(child.text)) elif child.tag.lower() == 'value': values.append(child) if remove and values: raise ValueError("A <records /> node with 'remove=\"true\"' must not contain " "<value /> nodes.") elif remove: for f in getFieldNames(interface): if f in omit: continue child = etree.Element('value', key=f, purge='True') values.append(child) # May raise TypeError self.context.registerInterface(interface, omit=tuple(omit), prefix=prefix) if not values and not remove: # Skip out if there are no value records to handle return # The prefix we ended up needs to be found if prefix is None: prefix = interface.__identifier__ for value in values: field = etree.Element("record", interface=interface.__identifier__, field=value.attrib["key"], prefix=prefix, remove=repr(remove).lower()) field.append(value) self.importRecord(field)
def schema_field_mapping(self): """Create a mapping of field_name to schema field object. This can then be used for validation """ field_mapping = {} for user_schema in self.user_schemata: for name in schema.getFieldNames(user_schema): field_mapping[name] = user_schema[name] return field_mapping
def testHaveFields(self): """ Set and check IDonatableMarker schema """ for f in ('product_code', 'price', 'donation_text', 'made_payable_by'): self.failUnless(f in getFieldNames(igetpaid.IDonationContent)) #sample for one field donatable_fields = getFields(igetpaid.IDonationContent) fieldDonationText = donatable_fields['donation_text'] self.assertRaises(RequiredMissing, fieldDonationText.validate, None)
def __init__(self, empInfo): fieldNSmapping = {} for fieldName in getFieldNames(IEmployee): fieldNSmapping[self.NS[fieldName]] = fieldName # predicate, object for p, o in empInfo: fieldName = fieldNSmapping.get(p, None) if fieldName: setattr(self, fieldName, o.encode('utf8'))
def get_field(context, field_name): schema_interfaces = [] if hasattr(context, 'schema'): schema_interfaces = [context.schema] for interface in (schema_interfaces or providedBy(context)): if field_name in getFieldNames(interface): return interface[field_name] return None
def __call__(self, context): # default list of Registration Form fields values = getFieldNames(RegistrationForm.schema) # make sure required minimum number of fields is present for val in JOIN_CONST: if val not in values: values.append(val) return SimpleVocabulary([SimpleTerm(v, v, v) for v in values])
def test_all_settings_are_tested(self): """ This test will fail if new settings are added to "IStatusMessageConfigForm" without having been added in this test case. """ self.assertEqual( set(self.expected_settings.keys()), set(getFieldNames(IStatusMessageConfigForm)), msg='Have you added some fields to "IStatusMessageConfigForm" without updating the test case?' )
def getContent(self): content = self.wizard.getContent() data = removeAllProxies(content.getFieldData()) for schema in (removeAllProxies(content).__schema__, IField): for name in getFieldNames(schema): field = schema[name].bind(content) data[name] = field.get(content) return data
def set(self, value): self._value = value self.updateWidgets() # ensure that we apply our new values to the widgets if value is not interfaces.NO_VALUE: active_names = self.subform.fields.keys() for name in getFieldNames(self.field.schema): if name in active_names: self.applyValue(self.subform.widgets[name], value.get(name, interfaces.NO_VALUE))
def get_settings_data(self): registry = getUtility(IRegistry) settings = registry.forInterface(IStatusMessageConfigForm, check=False) data = { field_name: getattr(settings, field_name) for field_name in getFieldNames(IStatusMessageConfigForm) } return data
def update(self, settings): """Update connection properties with settings as *dict* :param dict settings: typically extracted via the :py:meth:`get_settings` method from another process """ names = getFieldNames(IZEOConnection) for key, value in settings.items(): if key in names: setattr(self, key, value)
def test_fields(self): form = UserProfileEditForm(self.profile1, self.request) form.update() fields = form.fields.keys() # By default should include all core fields apart from portrait for fieldname in schema.getFieldNames(IUserProfile): if fieldname != 'portrait': self.assertIn( fieldname, fields, '{0} missing from edit form'.format(fieldname) ) # And any additional fields for fieldname in schema.getFieldNames(IUserProfileAdditional): self.assertIn( 'IUserProfileAdditional.{0}'.format(fieldname), fields, '{0} missing from edit form'.format(fieldname) )
def test_all_settings_are_tested(self): """ This test will fail if new settings are added to "IStatusMessageConfigForm" without having been added in this test case. """ self.assertEqual( set(self.expected_settings.keys()), set(getFieldNames(IStatusMessageConfigForm)), msg= 'Have you added some fields to "IStatusMessageConfigForm" without updating the test case?' )
def __call__(self, context): # default list of Registration Form fields util = getUtility(IRegisterSchemaProvider) schema = util.getSchema() values = getFieldNames(schema) # make sure required minimum number of fields is present for val in JOIN_CONST: if val not in values: values.append(val) return SimpleVocabulary([SimpleTerm(v, v, v) for v in values])
def getProperties(obj): """Get properties from obj with Interface.""" interfaces = list(providedBy(obj)) if interfaces == []: clsname = obj.__class__.__name__ mes = "The class: '{0}' have not any interfaces.".format(clsname) raise NotFoundInterfaceError(mes) properties = [] for inter in interfaces: properties.extend( getFieldNames(inter) ) return properties
def get_settings(self): """Get mapping of all connection settings These settings can be converted to JSON and sent to another process, for example via a ØMQ connection. :return: dict """ result = {} for name in getFieldNames(IZEOConnection): result[name] = getattr(self, name) return result
def populate_dexterity(obj, data): request = getRequest() for schema in get_dexterity_schemas(context=obj): for name in getFieldNames(schema): field = schema[name] if name in ['expires', 'effective', 'relatedItems']: # skip some fields continue if getattr(field, 'readonly', False): continue autoform_widgets = schema.queryTaggedValue(WIDGETS_KEY, default={}) if name in autoform_widgets: try: widgetclass = utils.resolveDottedName( autoform_widgets[name]) except AttributeError: # XXX: Investigate: # AttributeError: 'ParameterizedWidget' object has no # attribute 'split' continue widget = widgetclass(field, request) else: widget = component.getMultiAdapter( (field, request), IFieldWidget) widget.context = obj widget.ignoreRequest = True widget.update() if HAS_RECURRENCE_WIDGET and IRecurrenceWidget.providedBy(widget): # We cannot yet deal with the recurrence widget continue if name == 'title': value = unicode(data['title']) else: value = widget.value if not value or value in [NOT_CHANGED, NO_VALUE] or \ not IDataConverter(widget).toFieldValue(value): value = get_dummy_dexterity_value(obj, widget, data) if value is None: continue if interfaces.ICollection.providedBy(widget.field) or \ interfaces.IChoice.providedBy(widget.field): value = [value] if value: dm = component.getMultiAdapter((obj, field), IDataManager) try: dm.set(IDataConverter(widget).toFieldValue(value)) except TypeError: dm.set(value)
def test_receiver(self, browser): browser.login().open(self.portal, view='@@global_statusmessage_config_receiver', data={'jsondata': self.payload}) registry = getUtility(IRegistry) settings = registry.forInterface(IStatusMessageConfigForm, check=False) self.assertDictEqual( { field_name: getattr(settings, field_name) for field_name in getFieldNames(IStatusMessageConfigForm) }, self.expected_settings)
def test_value_proxy(self): """Test that CAS4PAS plugin receives values from registry.""" record = getUtility(IRegistry).forInterface(ICAS4PASPluginSchema) record.login_url = u'http://login' record.logout_url = u'http://logout' record.validate_url = u'http://validate' record.session_var = u'cookie' record.use_ACTUAL_URL = False cas = self.portal.acl_users.cas for field in getFieldNames(ICAS4PASPluginSchema): if hasattr(cas, field): self.assertEqual(getattr(cas, field), getattr(record, field))
def __call__(self): data = encode_after_json(json.loads(self.request.form.get('jsondata'))) if not data: return createResponse(states.InvalidRequestError()) registry = getUtility(IRegistry) settings = registry.forInterface(IStatusMessageConfigForm, check=False) for field_name in getFieldNames(IStatusMessageConfigForm): if field_name in data: setattr(settings, field_name, data[field_name]) return createResponse(states.SuccessState())
def UserDataWidget(field, request): """ Create selector with schema fields vocab """ util = getUtility(IUserDataSchemaProvider) schema = util.getSchema() schemaFieldNames = getFieldNames(schema) values = [f.__name__ for f in form.Fields(schema)] values.extend([val for val in JOIN_CONST if val not in schemaFieldNames]) terms = [SimpleTerm(v, v, v) for v in values] vocabulary = SimpleVocabulary(terms) return OrderedMultiSelectWidget(field, vocabulary, request)
def dexterity_update(obj, request=None): """ Utility method to update the fields of all the schemas of the Dexterity object 'obj'. """ modified = False if not request: request = obj.REQUEST # Call processInputs to decode strings to unicode, otherwise the # z3c.form dataconverters complain. processInputs(request) errors = [] for schema in get_dexterity_schemas(context=obj): for name in getFieldNames(schema): field = schema[name] widget = component.getMultiAdapter( (field, request), IFieldWidget) widget.context = obj value = field.missing_value widget.update() try: raw = widget.extract() except MultipleErrors, e: errors.append(e) log.warn("Multiple errors while extracting field: %s" % name) continue if raw is NOT_CHANGED: continue if raw is NO_VALUE: continue value = IDataConverter(widget).toFieldValue(safe_unicode(raw)) try: field.validate(value) except interfaces.RequiredMissing, e: errors.append(e) log.warn("Required field have missing value: %s" % name) # XXX: we might not want to continue here, since we then remove # the ability to remove field values. Client side validation # should prevent this situation from arising, but it's not yet # perfect. # continue except interfaces.ConstraintNotSatisfied, e: log.warn("Constraint not satisfied for field: %s" % name) log.warn(e) continue
def __call__(self): data = encode_after_json( json.loads(self.request.form.get('jsondata')) ) if not data: return createResponse(states.InvalidRequestError()) registry = getUtility(IRegistry) settings = registry.forInterface(IStatusMessageConfigForm, check=False) for field_name in getFieldNames(IStatusMessageConfigForm): if field_name in data: setattr(settings, field_name, data[field_name]) return createResponse(states.SuccessState())
def test_receiver(self, browser): browser.login().open( self.portal, view='@@global_statusmessage_config_receiver', data={'jsondata': self.payload}) registry = getUtility(IRegistry) settings = registry.forInterface(IStatusMessageConfigForm, check=False) self.assertDictEqual( { field_name: getattr(settings, field_name) for field_name in getFieldNames(IStatusMessageConfigForm) }, self.expected_settings )
def setUpWidgets(self, ignore_request=False): data = {} ptool = getUtility(IPropertiesTool) charset = ptool.getProperty('default_charset', None) for name in getFieldNames(IPortalConfig): value = ptool.getProperty(name) try: value = value.decode(charset) except (AttributeError, UnicodeEncodeError): pass data[name] = value data['smtp_server'] = ptool.smtp_server() self.widgets = form.setUpDataWidgets( self.form_fields, self.prefix, self.context, self.request, data=data, ignore_request=ignore_request)
def code(self): """ fill code property with values """ context = self.context d = dict([(x, getattr(context, x)) for x in getFieldNames(IBanner)]) container = context.__parent__ name = u"/".join(["/@@/zojax-banners", context.__parent__.__name__, context.__name__]) if container.useFakePlace: d["prefix"] = container.fakePlaceRoot d["name"] = name else: d["prefix"] = absoluteURL(getSite(), self.request) d["name"] = name return context.code % d
def forInterface(self, interface, check=True, omit=(), prefix=None, factory=None): if prefix is None: prefix = interface.__identifier__ if not prefix.endswith("."): prefix += '.' if check: for name in getFieldNames(interface): if name not in omit and prefix + name not in self: raise KeyError("Interface `%s` defines a field `%s`, " "for which there is no record." % (interface.__identifier__, name)) if factory is None: factory = RecordsProxy return factory(self, interface, omitted=omit, prefix=prefix)
def __call__(self): user = self.context portal = getSite() # Global roles roles = user.getRoles() # Anonymous and Authenticated are pseudo roles assign automatically # to logged-in or logged-out users. They should not be exposed here roles = list(set(roles) - set([ 'Anonymous', 'Authenticated', ])) data = { '@id': '{}/@users/{}'.format(portal.absolute_url(), user.id), 'id': user.id, 'username': user.getUserName(), 'roles': roles, } if HAS_TTW_SCHEMAS: schema = getUserDataSchema() else: util = getUtility(IUserDataSchemaProvider) schema = util.getSchema() for name in getFieldNames(schema): if name == 'portrait': memberdata = getToolByName(portal, 'portal_memberdata') if user.id in memberdata.portraits: value = '{}/portal_memberdata/portraits/{}'.format( portal.absolute_url(), user.id) else: value = None elif name == 'pdelete': continue else: value = user.getProperty(name, '') if value == '': value = None if value: value = safe_unicode(value) data[name] = value return data
def get_settings_from_interface(iface): """Get the configuration settings associated to a list of schema interfaces :param iface: The schema interface from which we want to get its fields :return: Dictionary with iface name as key and as value a dictionary with the setting names (keys) linked to that schema and its values. """ settings = {} schema_id = iface.getName() settings[schema_id] = {} schema = getAdapter(api.get_portal(), iface) for setting in getFieldNames(iface): value = getattr(schema, setting, None) if is_json_serializable(value): settings[schema_id][setting] = value return settings
def datagrid_field_get(self): # value (get) cannot raise an exception, then we return # insane values try: return self.extract() except MultipleErrors: value = {} active_names = self.subform.fields.keys() for name in getFieldNames(self.field.schema): if name not in active_names: continue widget = self.subform.widgets[name] widget_value = widget.value try: converter = interfaces.IDataConverter(widget) value[name] = converter.toFieldValue(widget_value) except (FormatterValidationError, ValidationError, ValueError): value[name] = widget_value return value
def __call__(self): user = self.context portal = getSite() # Global roles roles = user.getRoles() # Anonymous and Authenticated are pseudo roles assign automatically # to logged-in or logged-out users. They should not be exposed here roles = list(set(roles) - set(["Anonymous", "Authenticated"])) data = { "@id": "{}/@users/{}".format(portal.absolute_url(), user.id), "id": user.id, "username": user.getUserName(), "roles": roles, } if HAS_TTW_SCHEMAS: schema = getUserDataSchema() else: util = getUtility(IUserDataSchemaProvider) schema = util.getSchema() for name in getFieldNames(schema): if name == "portrait": memberdata = getToolByName(portal, "portal_memberdata") if user.id in memberdata.portraits: value = "{}/portal_memberdata/portraits/{}".format( portal.absolute_url(), user.id) else: value = None elif name == "pdelete": continue else: value = user.getProperty(name, "") if value == "": value = None if value: value = safe_unicode(value) data[name] = value return data
def __call__(self, context): """Build a vocabulary of user attributes. Get them from the IUserDataSchemaProvider utility and add additional ones to support extra functionality. """ schema_provider = getUtility(IUserDataSchemaProvider) schema = schema_provider.getSchema() user_attributes = getFieldNames(schema) # Add some additional attributes user_attributes.insert(0, 'username') user_attributes.append('groups') user_attributes.append('vcard') items = [ SimpleTerm(attr, attr, attr) for attr in user_attributes if attr not in MEMBER_PROPERTIES_TO_EXCLUDE ] return SimpleVocabulary(items)
def datagrid_field_set(self, value): self._value = value self.updateWidgets() # ensure that we apply our new values to the widgets if value is not interfaces.NO_VALUE: active_names = self.subform.fields.keys() for name in getFieldNames(self.field.schema): fieldset_field = self.field.schema[name] if fieldset_field.readonly: continue if name in active_names: if isinstance(value, dict): v = value.get(name, interfaces.NO_VALUE) else: v = getattr(value, name, interfaces.NO_VALUE) # probably there is a more generic way to do this ... if HAS_REL_FIELD and \ isinstance(fieldset_field, RelationChoice) \ and v == interfaces.NO_VALUE: v = '' self.applyValue(self.subform.widgets[name], v)
def _callFUT(self, schema): from zope.schema import getFieldNames return getFieldNames(schema)