跳转到主要内容

类似于Grok的表单配置指令

项目描述

本软件包提供可选的Grok-like指令,用于配置表单,由z3c.form库定义,使用由plone.supermodel定义的XML架构,或使用由plone.autoform定义的小部件表单布局。它依赖于five.grok,反过来它依赖于各种可重用的grokcore.*软件包,但不依赖于Grok本身。

安装

要使用此软件包,您必须首先安装它,要么在您的自己的setup.py中依赖它(在install_requires列表下),要么直接将其添加到您的buildout中。

这将引入许多依赖项。您可能希望使用已知良好的版本集将这些依赖项锁定在已知良好的版本上。有关起点,请参阅five.grok的安装说明。

您还必须从meta.zcmlconfigure.zcml加载相关的配置。例如,您可以在您的configure.zcml中使用以下语句

<include package="plone.directives.form" file="meta.zcml" />
<include package="plone.directives.form" />

或者如果您在setup.py中使用install_requires声明依赖项

<includeDependencies package="." />

从XML加载的架构

plone.directives.form曾经包含一个指令,用于将基于XML的模式模型加载到Python接口中。此指令已移动到plone.supermodel,作为plone.supermodel.model.load

表单小部件提示

plone.directives.form曾经包含多个指令,用于从模式生成表单,使用存储在该模式上的标记值中的提示来控制表单的布局和字段小部件。这些指令现在已移动到其他软件包,以避免Dexterity对Grok的依赖。

fieldsetprimary指令现在在plone.supermodel.model中。

omittedno_omitmodewidgetorder_beforeorder_afterread_permissionwrite_permission指令现在在plone.autoform.directives中。

值适配器

z3c.form有“值适配器”的概念,这是一个可以在运行时为属性提供值的组件(通常是小部件和按钮)。此软件包包含一些有用的装饰器来注册用于计算值的值适配器。例如

from plone.directives import form
from zope import schema

class IMySchema(form.Schema):

    title = schema.TextLine(title=u"Title")

@form.default_value(field=IMySchema['title'])
def default_title(data):
    return data.context.suggested_title

装饰器接受一个或多个区分器。可供default_value使用的区分器有

上下文

上下文类型(例如接口)

请求

请求类型(例如层标记接口)。您可以使用“layer”作为“request”的别名,但请注意,传递给函数的数据将只有“request”属性。

视图

表单类型(例如表单实例或接口)。您可以使用“form”作为“view”的别名,但请注意,传递给函数的数据将只有“view”属性。

字段

字段实例(或字段接口)。

小部件

小部件类型(例如接口)。

您必须指定fieldwidget。传递给装饰函数的对象为每个区分器具有一个属性。

还有两个其他装饰器

widget_label

为小部件提供动态标签。与default_value装饰器具有相同的判别器。

button_label – 为按钮提供动态标签。接受参数

内容(别名上下文)、请求(别名层)、表单(别名视图)、管理器和按钮。

请注意,按钮描述符(内容与上下文、表单与视图)和小部件描述符之间的命名存在一些不愉快的差异。描述符将接受相同的名称,但传递给函数的数据对象将只包含在z3c.form中定义的名称,因此请小心。

验证器

默认情况下,z3c.form使用字段的原生验证,该验证通过IField.validate()方法实现,以及字段约束(作为字段的constraint参数传递的函数)和模式不变性(在模式接口中使用@zope.interface.invariant装饰器)。此外,您可以定义自己的小部件验证器(用于表单的个别字段)和小部件管理器验证器(涵盖整个表单)。如果您不想在模式上定义验证器,这很有用,例如,因为模式也用于其他地方,或者如果您想创建一个更通用的验证器,该验证器适用于任何匹配其判别器的字段。

此软件包提供了一个grokked装饰器,您可以使用它来定义简单的验证器,称为@form.validator()

from plone.directives import form
from zope import schema

class IMySchema(form.Schema):

    title = schema.TextLine(title=u"Title")

@form.validator(field=IMySchema['title'])
def validateTitle(value):
    if value == value.upper():
        raise schema.ValidationError(u"Please don't shout")

如果字段有效,验证器应返回无内容,或者抛出带有错误消息的zope.schema.ValidationError异常。

@form.validator()装饰器可以接受各种关键字参数,这些参数确定验证器何时被调用。这些是

上下文

上下文类型(例如接口)

请求

请求类型(例如,层标记接口)。

视图

表单类型(例如,表单实例或接口)。

字段

字段实例(或字段接口)。

小部件

小部件类型(例如接口)。

请注意,此验证器函数不提供对标准验证器的完整上下文访问,例如字段、小部件、上下文或请求。如果您需要这些,您可以创建一个标准验证器适配器,例如使用grok.Adapter。有关详细信息,请参阅z3c.form文档。

请注意,标准字段验证器将在自定义验证器被调用之前调用。如果您需要完全覆盖验证器,您可以使用自定义适配器再次这样做。

错误信息

使用自定义验证器时,很容易提供定制的错误消息。然而,来自默认字段验证机制(例如,当省略必填字段时)的错误消息是必要的更通用的。有时,可能需要覆盖这些消息,以使其更具用户友好性。

要自定义错误消息,您可以使用@form.error_message grokked装饰器。例如

from plone.directives import form
from zope import schema

from zope.schema.interfaces import TooShort

class IMySchema(form.Schema):

    title = schema.TextLine(title=u"Title", min_length=2)

@form.error_message(error=TooShort, field=IMySchema['title'])
def titleTooShort(value):
    return u"The title '%s' is too short" % value

装饰的函数将在构建给定字段的错误消息时被调用。它应返回一个Unicode字符串或可翻译的消息。传递的值是未通过验证的值。

@form.error_message验证器接受确定消息何时使用的关键字参数。可以为给定类型的错误注册一个通用错误消息,该错误消息适用于所有字段,或者,如上所示,为特定字段和错误注册一个特定消息。后者更为常见。通常,如果您省略了errorfield判别器之一或两个,都应小心。

错误

表示错误的异常类。所有错误都继承自zope.interface.Invalid,大多数错误也继承自zope.schema.interfaces.ValidationError。以下是一些常见的异常类型列表。

请求

当前请求。使用此信息将错误与特定的浏览器层接口相关联。

小部件

使用的 Widget。可能是 Widget 接口或特定的 Widget 类。

字段

使用的字段,通常是从接口获得的字段实例,如上图所示。

表单

当前表单,无论是作为类还是接口。如果同一个接口在多个表单中使用,但只想在一个表单中显示错误,这将很有用。

内容

作为表单上下文的内容项。可以指定为接口或类。

这些参数都不是必需的,但通常至少需要提供error。在大多数情况下,还应提供如上所示的field

最常见的验证错误异常类型定义在zope.schema中,可以从zope.schema.interfaces导入。

  • RequiredMissing,当提交必填字段时未提供值时使用。

  • WrongType,当字段传递了无效类型的值时使用。

  • TooBigTooSmall,当值超出有序字段(例如数字或日期字段)指定的min和/或max范围时使用。

  • TooLongTooShort,当值超出长度感知字段(例如文本或序列字段)指定的min_length和/或max_length范围时使用。

  • InvalidValue,当值无效时使用,例如将非ASCII字符传递给ASCII字段。

  • ConstraintNotSatisfied,当约束方法返回False时使用。

  • WrongContainedType,如果向序列添加了无效类型的对象(即类型不符合字段的value_type)时使用。

  • NotUnique,如果违反了唯一性约束时使用。

  • InvalidURI,对于URI字段,如果值不是有效的URI时使用。

  • InvalidId,对于Id字段,如果值不是有效的id时使用。

  • InvalidDottedName,对于DottedName字段,如果值不是有效的点名称时使用。

表单基类

如果您需要创建自己的表单,此包提供了一些方便的基类,这些基类的工作方式类似于grok.View

在Zope 2.10中,解析器负责将表单包裹在plone.z3cform FormWrapper中。在Zope 2.12及更高版本中,默认情况下没有包装器。如果需要(例如,如果您正在使用自定义模板并且需要在Zope 2.10和2.12中工作),您可以在表单类中使用form.wrap()指令。

所有基类都可以从plone.directives.form导入,例如

from five import grok
from plone.directives import form, button
from z3c.form import field

class MyForm(form.Form):
    grok.context(ISomeContext)
    grok.require('zope2.View')

    fields = field.Fields(IMyFormSchema)

    @button.buttonAndHandler(u'Submit')
    def handleApply(self, action):
        data, errors = self.extractData()
        ...

允许的指令有

  • grok.context(),用于指定表单视图的上下文。如果没有提供,解析器将寻找模块级上下文,类似于标准grok.View

  • grok.require(),用于指定权限。对于标准表单,默认为zope2.View,对于编辑表单为cmf.ModifyPortalContent,对于添加表单为cmf.AddPortalContent

  • grok.layer(),用于指定浏览器层。

  • grok.name(),用于设置不同的名称。默认情况下,您的表单将作为视图@@yourformclassnamelowercase提供,但您可以使用grok.name()显式设置名称。

  • 使用 form.wrap() 将表单包裹在布局包装视图中。你可以传递一个 TrueFalse 参数来启用或禁用包裹。如果没有提供参数,则默认为 True。如果省略,则使用全局默认值,在 Zope 2.11 或更早版本中包裹,而在 Zope 2.12 或更高版本中不包裹。

如何使用 Grok 指令与表单结合的更复杂示例

from plone.directives import form
from Products.CMFCore.interfaces import ISiteRoot

class CompanyCreationForm(form.SchemaForm):
    """ A sample form how to "create companies".

    """

    # Which plone.directives.form.Schema subclass is used to define
    # fields for this form (not shown on this example)
    schema = ICompanyCreationFormSchema

    # Permission required to view/submit the form
    grok.require("cmf.ManagePortal")

    # The form does not care about the context object
    # and  should not try to extract field value
    # defaults out of it
    ignoreContext = True

    # This form is available at the site root only
    grok.context(ISiteRoot)

    # The form will be available in Plone site root only
    # Use http://yourhost/@@create_company URL to access this form
    grok.name("create_company")

每个表单基类都有一个“模式”等效类,可以用 schema 属性而不是 fields 属性来初始化。这些表单使用 plone.autoformAutoExtensibleForm 作为基类,允许处理如上所示的方案提示。

from plone.directives import form
from z3c.form import button

class MyForm(form.SchemaForm):
    grok.context(ISomeContext)
    grok.require('zope2.View')

    schema = IMySchema

    @button.buttonAndHandler(u'Submit')
    def handleApply(self, action):
        data, errors = self.extractData()
        ...

请注意,如果您使用 SchemaFormSchemaEditForm 并将接口作为 grok.context() 的参数提供,则可以省略 schema。在这种情况下,上下文接口将用作默认模式。

可用的表单基类有

表单

一个简单的页面表单,基本上是 z3c.form.form.Form 的 grokked 版本。

SchemaForm

一个使用 plone.autoform 的页面表单。您必须设置 schema 类变量(或将其实现为属性),以指定表单将要构建的模式接口表单。将考虑表单小部件提示。

AddForm

一个简单的添加表单,带有“添加”和“取消”按钮。您必须实现 create()add() 方法。有关更多详细信息,请参阅 z3c.form 文档。

SchemaAddForm

一个使用 plone.autoform 的添加表单。同样,您必须设置 schema 类变量。

EditForm

一个简单的编辑表单,带有“保存”和“取消”按钮。有关更多详细信息,请参阅 z3c.form 文档。

SchemaEditForm

一个使用 plone.autoform 的编辑表单。同样,您必须设置 schema 类变量。

DisplayForm

一个与自动关联的模板(如 grok.View)关联的视图,它使用显示小部件进行初始化。有关更多详细信息,请参阅 plone.autoformWidgetsView

上述所有 grokked 表单基类都支持将自定义模板与表单关联。这使用与 grok.View 相同的语义。有关详细信息,请参阅 grokcore.view,但简要来说

  • 如果您想完全自定义渲染,可以覆盖 render() 方法。

  • 如果您想在模块 my.package.forms 中调用名为 MyForm 的表单,并在 my.package 中创建一个名为 forms_templates 的目录(前缀应与模块名称匹配),并将一个名为 myform.pt 的文件放在其中。

  • 如果您既不这样做,将使用默认表单模板,这是 z3c.form 中的标准行为。

请注意,自动关联的表单模板可以使用 grok.View 方法,如 view.url()view.redirect(),这些方法定义在 grokked 表单基类中。

另外,如果您想使用来自 plone.app.z3cform 的视图 @@ploneform-macros 并使用一些标准表单标记,则可以这样做。例如,titlelessform 宏将渲染 <form > 元素以及所有分组和字段

<metal:block use-macro="context/@@ploneform-macros/titlelessform" />

故障排除

找不到表单

当您尝试在网站上访问表单时,您将收到页面未找到(NotFound异常)。

  • 请确保您正确输入了表单名称,并且它与 grok.name() 或小写类名匹配

  • 请确保您在您的附加产品配置.zcml中包含

变更日志

2.0.3 (2017-05-09)

错误修复

  • 删除了未使用的导入,并在示例中添加了缺失的导入。[bruno]

  • 更新 setup.py 以指向 GitHub 仓库。[esteele]

2.0.2 (2015-11-28)

修复

  • 将 i18n_domain 更改为 "plone"。[staeff]

  • 删除了不必要的 i18n-attribute。[staeff]

2.0.1 (2015-05-04)

  • pep8。[maurits]

  • 空白符清理。[gforcada]

2.0 (2012-08-30)

  • 更新以与 grokcore.view >= 2.2 兼容。这通常意味着该包不再与 Plone < 4.3 兼容。[davisagli]

  • 将 i18n 域更改为 plone.dexterity 以重用翻译。plone.dexterity 已经包含所有需要的字符串。[gaudenz]

  • 修复了文档化的 form.wrapped() 指令的错误,该指令实际上是 form.wrap()。[romanofski]

  • 将许多模式指令移动到其他包,并重新实现以不依赖于 grok。将 Schema 类以及 modelfieldsetprimary 指令移动到 plone.supermodel.model。将 omittedno_omitmodewidgetorder_beforeorder_afterread_permissionwrite_permission 指令移动到 plone.autoform.directives

    目前,这些指令仍然以它们的旧名称存在于本包中,但它们已弃用,可能在某个时刻被删除。

    一些相关的细微更改

    • 标记值现在在定义时立即存储在模式中,而不是在模式解析时。如果有的话,指令所需的附加操作将在 ZCML 配置的末尾执行。

    • 由于 zope.interface 中的错误,plone.supermodel.model.Schema 必须是任何应用指令的模式的首个基类。不幸的是,现在不再可能在不是 Schema 的接口上调用模式指令时抛出错误。

    [davisagli]

1.0 - 2011-05-20

  • 没有更改。

1.0b7 - 2010-04-20

  • 允许 fieldset 指令具有任意额外的参数。这对于想要调整 fieldset 行为或渲染的扩展很有用。[wichert]

  • 添加 no_omit 指令,以便可以重新包含已省略的字段,以在更具体的表单接口中使用。[davisagli]

  • 将表单接口作为可选位置参数接受 modeomitted 指令,并使用 plone.autoform 期望的新格式在标记值中存储它。[davisagli]

  • 添加 @form.error_message() 装饰器以注册错误和/或字段的自定义错误消息。[optilude]

  • 添加 @form.validator() 装饰器以注册简单的字段验证器。有关详细信息,请参阅 README.txt。[optilude]

  • 支持未包装的表单(在 Zope 2.12 中)。默认情况下,在 Zope < 2.12 中包装,而在 Zope >= 2.12 中不包装。可以使用新的 form.wrapped() 指令强制包装或不包装(通过传递 False 作为参数)。[optilude]

  • 当在未从 Schema 继承的接口上使用表单指令或使用引用无法找到的字段名的模式提示时,发出更强烈的警告。[optilude]

1.0b6 - 2009-10-08

  • 添加对 primary() 指令的支持,该指令用于设置 marshalling 的主字段。有关详细信息,请参阅 plone.rfc822。[optilude]

1.0b5 - 2009-07-21

  • 更新到新的 five.grok 发布版本。[optilude]

1.0b3 - 2009-07-12

  • 对plone.supermodel的API进行了调整。[optilude]

1.0b2 - 2009-06-15

  • 确保在使用@form.default_value()装饰器和其他值装饰器时不会丢失功能。[optilude]

1.0b1 - 2009-04-17

  • 初始发布

项目详情


下载文件

下载适用于您平台的文件。如果您不确定选择哪个,请了解有关安装包的更多信息。

源代码分发

plone.directives.form-2.0.3.tar.gz (36.7 kB 查看哈希值)

上传时间 源代码

由以下组织支持