Having Your View Directly Instantiate An Object¶
We now reach the first of our four techniques!
The simplest way to create a transient object for display on the web involves a
technique you may remember from the main Grok tutorial: providing an
update()
method on your View that creates the object you need and saves it
as an attribute of the View. As a simple example, create an app.py
file
with these contents:
import grok
from transient.natural import Natural
class TransientApp(grok.Application, grok.Container):
pass
class Index(grok.View):
def update(self):
self.num = Natural(126)
Do you see what will happen? Right before Grok renders your View to answer a
web request, Grok will call its update()
method, and your View will gain an
attribute named num
whose value is a new instance of the Natural
class.
This attribute can then be referenced from the page template corresponding to
your view! Let use write a small page template that accesses the new object.
Try creating an /app_templates/index.pt
file that looks like:
<html><body>
<p>
Behold the number <b tal:content="view/num">x</b>!
<span tal:condition="view/num/is_prime">It is prime.</span>
<span tal:condition="view/num/is_composite">Its prime factors are:</span>
</p>
<ul tal:condition="view/num/factors">
<li tal:repeat="factor view/num/factors">
<b tal:content="factor">f</b>
</li>
</ul>
</body></html>
If you now run your instance and view the main page of your application, your browser should show you something like:
Behold the number 126! It has several prime factors:
- 2
- 3
- 3
- 7
You should remember, when creating an object through an update()
method,
that a new object gets created every time your page is viewed! This is hard to
see with the above example, of course, because no matter how many times you hit
“reload” on your web browser you will still see the same number. So adjust your
app.py
file so that it now looks like this:
import grok, random
from transient.natural import Natural
class TransientApp(grok.Application, grok.Container):
pass
class Index(grok.View):
def update(self):
self.num = Natural(random.randint(1,1000))
Re-run your application and hit “reload” several times; each time you should see a different number.
The most important thing to realize when using this method is that this
Natural
object is not the object that Grok is wrapping with the View for
display! The object actually selected by the URL in this example is your
TransientApp
application object itself; it is this application object which
is the context
of the View. The Natural
object we are creating is
nothing more than an incidental attribute of the View; it neither has its own
URL, nor a View of its own to display it.