首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何在z3c.form的DictionaryField中使用批注

如何在z3c.form的DictionaryField中使用批注
EN

Stack Overflow用户
提问于 2015-10-23 23:01:35
回答 2查看 78关注 0票数 4

有关于使用Python dict with z3c.form (加载和存储表单数据)的documentation

但是,用于字典的z3c.form datamanager没有为其他类型或接口注册(请参阅reference),而批注通常使用类似PersistentDict的内容。

在这种情况下,如何使用DictionaryField datamanager?即。因此,在表单的getContent方法中,我只返回PersistentDict注释。

EN

回答 2

Stack Overflow用户

发布于 2015-10-23 23:38:06

不幸的是,这个需求似乎没有简单的解决方案。我曾经在使用z3c表单中的数据网格字段时遇到过同样的问题。

下面的指令解决了datagrid字段的问题,它是一个list (PersistentList of dicts (PersistentMappings) )。

我想你可以根据你的情况调整这个解决方案。

首先,您需要将以下代码添加到getContent方法:

代码语言:javascript
复制
from plone.directives import form

class MyForm(form.SchemaEditForm):

    schema = IMyFormSchema
    ignoreContext = False

    def getContent(self):
        annotations = IAnnotations(self.context)
        if ANNOTATION_KEY not in annotations:
            annotations[ANNOTATION_KEY] = PersistentMapping()
        return YourStorageConfig(annotations[ANNOTATION_KEY])

重要说明:我包装了注释存储,以满足z3c表单的get/set行为。检查以下YourStorageConfig实现,您将了解原因:-)。

代码语言:javascript
复制
class YourStorageConfig(object):
    implements(IMyFormSchema)

    def __init__(self, storage):
        self.storage = storage

    def __getattr__(self, name):
        if name == 'storage':
            return object.__getattr__(self, name)
        value = self.storage.get(name)
        return value

    def __setattr__(self, name, value):
        if name == 'storage':
            return object.__setattr__(self, name, value)
        if name == 'yourfieldname':
            self.storage[name] = PersistentList(map(PersistentMapping, value))
            return

        raise AttributeError(name)

yourfieldname应该是您在表单架构中使用的字段名称。

要实现a datagrid字段,还有一些工作要做,但对于您的情况来说,这可能就足够了。

请发表评论,或回溯,这样我就可以提供进一步的帮助。如有必要,我将添加更多细节/解释;-)

票数 2
EN

Stack Overflow用户

发布于 2015-10-25 00:03:06

答案就像下面的ZCML适配器注册一样简单:

代码语言:javascript
复制
<adapter
  for="persistent.dict.PersistentDict zope.schema.interfaces.IField"
  provides="z3c.form.interfaces.IDataManager"
  factory="z3c.form.datamanager.DictionaryField"
 />

这样,以下表单定制就足以使用(PersistentDict)注释来加载和存储表单数据:

代码语言:javascript
复制
def getContent(self):
   "return the object the form will manipulate (load from & store to)"
   annotations =  IAnnotations(self.context)
   return annotations[SOME_ANNOTATIONS_KEY_HERE]

这是假设之前已经在annotations[SOME_ANNOTATIONS_KEY_HERE]中存储了一个PersistentDict -否则上面的代码将导致KeyError。在getContent之上进行更改可能是一个好主意,这样如果注释还不存在,它就会被创建并使用一些默认值进行初始化。

最后,请注意,由于某些原因,z3c.form warns反对为每种映射类型启用DictionaryField,因此,谨慎的做法可能是将PersistentDict子类用于表单存储,而不是直接使用它。我向z3c.form提交了an issue,要求澄清那个警告。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/33305555

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档