On Jan 30, 8:43 am, "Daniel Fetchinson" <[EMAIL PROTECTED]>
wrote:
> >http://code.google.com/p/webpyte/wiki/FormettoFramework
>
> > I have written up the above page about why I was unsatisfied with the
> > interface of TG widgets (which puts widgets in our controllers instead
> > of our template) and why I am making a new interface: Formetto.
>
> I haven't looked at your code yet but have to say that I also don't
> like very much the fact that I have to define what widgets are used in
> the controller. It feels more natural to declare this in the template.
> I don't claim to have a very precise opinion on what solution would be
> the best but it just doesn't feel right how things are now (and
> probably will be with TW) although I go with the flow and do it the TG
> way anyway because it's not a really big deal.
>
> Now that we are at it could one or more of the developers expand on
> what lead to the current design decision regarding widgets? I mean
> that they need to be declared in the controller. I'm sure there are
> very good reasons to do things this way I just fail to see them.
There are two reasons for which the may be defined outside the
template (not necessarily "the controller", I don't consider a
"widgets" package to be controller code just because it's not in the
template):
1) To have a reference to the form instance to validate input. This is
the only hard reason, but a single line is needed in the module where
controllers are declared to avoid cluttering it with widget
declarations ;)
2) So resources (js & css) needed for the widgets are picked up to be
injected in the template. The current implementation scans the output
dict returned by controllers and picks up widgets from there, it is
done this way because the resources in the <head> are rendered before
any other widget is so its impossible to know in advance which widgets
are actually going to be rendered.
In TW I was experimenting with another approach which injected the
resources after the page was finished using lxml. This allowed you to
import, or even declare, widgets in the template and their resources
would be included too. Unfortunately I consider the experiment of mild
success since lxml, being a C coded extension, causes installation
problems for some and because of the fact that lxml currently cannot
serialize XHTML, only HTML. Genshi could be used to inject resources
post-widget-render but will be terribly inefficient with string-based
templates (like Mako). Ideas welcomed :)
Regarding validation:
Having validation in the model can be useful too, but that doesn't
contradict having validation in the widgets as well, they serve
different purposes. TW/TG input widgets are designed to perform
validation and conversion to python in the "frontier" between the web
and the app so when controllers are called their args are already
python values. This allows you top use input widgets not only to edit/
create model objects but to deal with any kind of input. For example,
pagination query args ("is limit a postitive integer?"), date ranges,
etc, etc..
The point is, furher validation can be done in the model if needed (in
fact, SQlObject uses FormEncode internally just for that)
A way to keep things DRY in TG/TW would annotate the model with
metadata (eg, this field holds and email, etc...) which can then be
inspected by the form generator to bind the proper validators. This
technique was discussed some time ago in the trunk ML but I'm not sure
if anything has come out yet...
Regarding Formetto:
Some statements made in the web-page are simply not true, for example:
- Where it says tg forms only accept dicts as values. TG forms accept
any model instance as a value and will convert it into a dict
internally. TW takes one step further and does this for any compound
widget, for example, given a model object with a many-to-one relation
(ie, a "list" of related items as a property) it will adapt the
related items recursively to fill in the repeated widgets. What's even
better is that when the form is submitted back, the validator will
validate and re-create the nested structure which can be trivially
used to update the model.
- Widgets are *not* in the controller layer (even if they appear in
the same module as controller classes in the examples for illustration
purposes). Nothing prevents declaring widgets in a separate module
which makes them reusable in different templates and controllers and
even projects. Hence widgets don't necessarily make controller code
longer, quite the opposite if used well since the arguments passed to
a validate()-decorated controller methods are already python values.
>From a brief skim at the code, I see that Formetto generates
javascript after rendering the widgets, does this allow to insert
javascript and css links in the <head> (or anywhere before the widgets
are rendered for the matter)? I'm pointing this out because its
probably the biggest reason why tg/tw widgets need to be passed from
the controller to the template (although, as I've said, this doesn't
have to be this way, albeit with its own limitations)
All in all, it's interesting to see other approaches to solve similar
problems. :)
Alberto
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups
"TurboGears" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at
http://groups.google.com/group/turbogears?hl=en
-~----------~----~----~----~------~----~------~--~---