doc/book/devweb/edition/examples.rst
author Philippe Pepiot <ph@itsalwaysdns.eu>
Tue, 31 Mar 2020 19:15:03 +0200
changeset 12957 0c973204033a
parent 12879 7347715bf0ee
permissions -rw-r--r--
[server] prevent returning closed cursor to the database pool In since c8c6ad8 init_repository use repo.internal_cnx() instead of repo.system_source.get_connection() so it use the pool and we should not close cursors from the pool before returning it back. Otherwise we may have "connection already closed" error. This bug only trigger when connection-pool-size = 1. Since we are moving to use a dynamic pooler we need to get this fixed. This does not occur with sqlite since the connection wrapper instantiate new cursor everytime, but this occur with other databases.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
     1
Examples
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
     2
--------
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
     3
5476
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
     4
(Automatic) Entity form
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
     5
~~~~~~~~~~~~~~~~~~~~~~~
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
     6
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
     7
Looking at some cubes available on the `cubicweb forge`_ we find some
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
     8
with form manipulation. The following example comes from the the
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
     9
`conference`_ cube. It extends the change state form for the case
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    10
where a ``Talk`` entity is getting into ``submitted`` state. The goal
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    11
is to select reviewers for the submitted talk.
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    12
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    13
.. _`cubicweb forge`: http://www.cubicweb.org/view?rql=Any+P+ORDERBY+N+WHERE+P+name+LIKE+%22cubicweb-%25%22%2C+P+is+Project%2C+P+name+N
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    14
.. _`conference`: http://www.cubicweb.org/project/cubicweb-conference
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    15
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    16
.. sourcecode:: python
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    17
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    18
 from cubicweb.web import formfields as ff, formwidgets as fwdgs
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    19
 class SendToReviewerStatusChangeView(ChangeStateFormView):
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    20
     __select__ = (ChangeStateFormView.__select__ &
6152
6824f8b61098 use is_instance in a number of places (esp. documentation) rather than the deprecated implements
Alexandre Fayolle <alexandre.fayolle@logilab.fr>
parents: 5476
diff changeset
    21
                   is_instance('Talk') &
5476
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    22
                   rql_condition('X in_state S, S name "submitted"'))
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    23
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    24
     def get_form(self, entity, transition, **kwargs):
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    25
         form = super(SendToReviewerStatusChangeView, self).get_form(entity, transition, **kwargs)
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    26
         relation = ff.RelationField(name='reviews', role='object',
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    27
                                     eidparam=True,
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    28
                                     label=_('select reviewers'),
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    29
                                     widget=fwdgs.Select(multiple=True))
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    30
         form.append_field(relation)
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    31
         return form
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    32
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    33
Simple extension of a form can be done from within the `FormView`
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    34
wrapping the form. FormView instances have a handy ``get_form`` method
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    35
that returns the form to be rendered. Here we add a ``RelationField``
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    36
to the base state change form.
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    37
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    38
One notable point is the ``eidparam`` argument: it tells both the
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    39
field and the ``edit controller`` that the field is linked to a
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    40
specific entity.
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    41
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    42
It is hence entirely possible to add ad-hoc fields that will be
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    43
processed by some specialized instance of the edit controller.
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    44
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    45
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    46
Ad-hoc fields form
23758c00d3ab [doc/book] a very simple example of entity form extension
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents: 5463
diff changeset
    47
~~~~~~~~~~~~~~~~~~
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    48
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    49
We want to define a form doing something else than editing an entity. The idea is
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    50
to propose a form to send an email to entities in a resultset which implements
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    51
:class:`IEmailable`.  Let's take a simplified version of what you'll find in
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    52
:mod:`cubicweb.web.views.massmailing`.
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    53
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    54
Here is the source code:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    55
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    56
.. sourcecode:: python
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    57
9423
76c0c96557f8 [doc] Pass field to value callback in FieldsForm example
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 8032
diff changeset
    58
    def sender_value(form, field):
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    59
        return '%s <%s>' % (form._cw.user.dc_title(), form._cw.user.get_email())
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    60
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    61
    def recipient_choices(form, field):
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    62
        return [(e.get_email(), e.eid)
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    63
                 for e in form.cw_rset.entities()
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    64
                 if e.get_email()]
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    65
9423
76c0c96557f8 [doc] Pass field to value callback in FieldsForm example
Denis Laxalde <denis.laxalde@logilab.fr>
parents: 8032
diff changeset
    66
    def recipient_value(form, field):
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    67
        return [e.eid for e in form.cw_rset.entities()
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    68
                if e.get_email()]
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    69
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    70
    class MassMailingForm(forms.FieldsForm):
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    71
        __regid__ = 'massmailing'
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    72
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    73
        needs_js = ('cubicweb.widgets.js',)
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    74
        domid = 'sendmail'
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    75
        action = 'sendmail'
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    76
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    77
        sender = ff.StringField(widget=TextInput({'disabled': 'disabled'}),
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    78
                                label=_('From:'),
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    79
                                value=sender_value)
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    80
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    81
        recipient = ff.StringField(widget=CheckBox(),
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    82
                                   label=_('Recipients:'),
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    83
                                   choices=recipient_choices,
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    84
                                   value=recipients_value)
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    85
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    86
        subject = ff.StringField(label=_('Subject:'), max_length=256)
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    87
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    88
        mailbody = ff.StringField(widget=AjaxWidget(wdgtype='TemplateTextField',
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    89
                                                    inputid='mailbody'))
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    90
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    91
        form_buttons = [ImgButton('sendbutton', "javascript: $('#sendmail').submit()",
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    92
                                  _('send email'), 'SEND_EMAIL_ICON'),
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    93
                        ImgButton('cancelbutton', "javascript: history.back()",
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
    94
                                  stdmsgs.BUTTON_CANCEL, 'CANCEL_EMAIL_ICON')]
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    95
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    96
Let's detail what's going on up there. Our form will hold four fields:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    97
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    98
* a sender field, which is disabled and will simply contains the user's name and
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
    99
  email
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   100
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   101
* a recipients field, which will be displayed as a list of users in the context
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   102
  result set with checkboxes so user can still choose who will receive his mailing
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   103
  by checking or not the checkboxes. By default all of them will be checked since
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   104
  field's value return a list containing same eids as those returned by the
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   105
  vocabulary function.
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   106
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   107
* a subject field, limited to 256 characters (hence we know a
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   108
  :class:`~cubicweb.web.formwidgets.TextInput` will be used, as explained in
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   109
  :class:`~cubicweb.web.formfields.StringField`)
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   110
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   111
* a mailbody field. This field use an ajax widget, defined in `cubicweb.widgets.js`,
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   112
  and whose definition won't be shown here. Notice though that we tell this form
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   113
  need this javascript file by using `needs_js`
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   114
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   115
Last but not least, we add two buttons control: one to post the form using
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   116
javascript (`$('#sendmail')` being the jQuery call to get the element with DOM id
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   117
set to 'sendmail', which is our form DOM id as specified by its `domid`
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   118
attribute), another to cancel the form which will go back to the previous page
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   119
using another javascript call. Also we specify an image to use as button icon as a
6880
4be32427b2b9 [book] fixes some references and other doc construction pbs
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 6152
diff changeset
   120
resource identifier (see :ref:`uiprops`) given as last argument to
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   121
:class:`cubicweb.web.formwidgets.ImgButton`.
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   122
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   123
To see this form, we still have to wrap it in a view. This is pretty simple:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   124
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   125
.. sourcecode:: python
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   126
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   127
    class MassMailingFormView(form.FormViewMixIn, EntityView):
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
   128
        __regid__ = 'massmailing'
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
   129
        __select__ = is_instance(IEmailable) & authenticated_user()
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   130
12879
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
   131
        def call(self):
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
   132
            form = self._cw.vreg['forms'].select('massmailing', self._cw,
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
   133
                                                 rset=self.cw_rset)
7347715bf0ee [doc] replace tabs with spaces (and make linter happy)
Nicolas Chauvat <nicolas.chauvat@logilab.fr>
parents: 10491
diff changeset
   134
            form.render(w=self.w)
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   135
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   136
As you see, we simply define a view with proper selector so it only apply to a
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   137
result set containing :class:`IEmailable` entities, and so that only users in the
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   138
managers or users group can use it. Then in the `call()` method for this view we
6880
4be32427b2b9 [book] fixes some references and other doc construction pbs
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 6152
diff changeset
   139
simply select the above form and call its `.render()` method with our output
4be32427b2b9 [book] fixes some references and other doc construction pbs
Sylvain Thénault <sylvain.thenault@logilab.fr>
parents: 6152
diff changeset
   140
stream as argument.
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   141
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   142
When this form is submitted, a controller with id 'sendmail' will be called (as
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   143
specified using `action`). This controller will be responsible to actually send
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   144
the mail to specified recipients.
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   145
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   146
Here is what it looks like:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   147
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   148
.. sourcecode:: python
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   149
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   150
   class SendMailController(Controller):
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   151
       __regid__ = 'sendmail'
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   152
       __select__ = (authenticated_user() &
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   153
                     match_form_params('recipient', 'mailbody', 'subject'))
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   154
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   155
       def publish(self, rset=None):
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   156
           body = self._cw.form['mailbody']
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   157
           subject = self._cw.form['subject']
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   158
           eids = self._cw.form['recipient']
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   159
           # eids may be a string if only one recipient was specified
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   160
           if isinstance(eids, basestring):
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   161
               rset = self._cw.execute('Any X WHERE X eid %(x)s', {'x': eids})
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   162
           else:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   163
               rset = self._cw.execute('Any X WHERE X eid in (%s)' % (','.join(eids)))
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   164
           recipients = list(rset.entities())
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   165
           msg = format_mail({'email' : self._cw.user.get_email(),
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   166
                              'name' : self._cw.user.dc_title()},
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   167
                             recipients, body, subject)
8032
bcb87336c7d2 [doc] fix most of ReST compilation errors and warnings
Adrien Di Mascio <Adrien.DiMascio@logilab.fr>
parents: 6880
diff changeset
   168
           if not self._cw.vreg.config.sendmails([(msg, recipients)]):
5463
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   169
               msg = self._cw._('could not connect to the SMTP server')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   170
           else:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   171
               msg = self._cw._('emails successfully sent')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   172
           raise Redirect(self._cw.build_url(__message=msg))
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   173
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   174
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   175
The entry point of a controller is the publish method. In that case we simply get
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   176
back post values in request's `form` attribute, get user instances according
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   177
to eids found in the 'recipient' form value, and send email after calling
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   178
:func:`format_mail` to get a proper email message. If we can't send email or
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   179
if we successfully sent email, we redirect to the index page with proper message
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   180
to inform the user.
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   181
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   182
Also notice that our controller has a selector that deny access to it
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   183
to anonymous users (we don't want our instance to be used as a spam
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   184
relay), but also checks if the expected parameters are specified in
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   185
forms. That avoids later defensive programming (though it's not enough
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   186
to handle all possible error cases).
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   187
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   188
To conclude our example, suppose we wish a different form layout and that existent
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   189
renderers are not satisfying (we would check that first of course :). We would then
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   190
have to define our own renderer:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   191
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   192
.. sourcecode:: python
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   193
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   194
    class MassMailingFormRenderer(formrenderers.FormRenderer):
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   195
        __regid__ = 'massmailing'
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   196
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   197
        def _render_fields(self, fields, w, form):
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   198
            w(u'<table class="headersform">')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   199
            for field in fields:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   200
                if field.name == 'mailbody':
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   201
                    w(u'</table>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   202
                    w(u'<div id="toolbar">')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   203
                    w(u'<ul>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   204
                    for button in form.form_buttons:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   205
                        w(u'<li>%s</li>' % button.render(form))
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   206
                    w(u'</ul>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   207
                    w(u'</div>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   208
                    w(u'<div>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   209
                    w(field.render(form, self))
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   210
                    w(u'</div>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   211
                else:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   212
                    w(u'<tr>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   213
                    w(u'<td class="hlabel">%s</td>' %
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   214
                      self.render_label(form, field))
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   215
                    w(u'<td class="hvalue">')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   216
                    w(field.render(form, self))
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   217
                    w(u'</td></tr>')
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   218
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   219
        def render_buttons(self, w, form):
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   220
            pass
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   221
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   222
We simply override the `_render_fields` and `render_buttons` method of the base form renderer
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   223
to arrange fields as we desire it: here we'll have first a two columns table with label and
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   224
value of the sender, recipients and subject field (form order respected), then form controls,
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   225
then a div containing the textarea for the email's content.
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   226
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   227
To bind this renderer to our form, we should add to our form definition above:
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   228
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   229
.. sourcecode:: python
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   230
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   231
    form_renderer_id = 'massmailing'
37a2455639b9 [doc/book] move examples to a separate chapter, fix autoform module docstring
Aurelien Campeas <aurelien.campeas@logilab.fr>
parents:
diff changeset
   232