Let’s keep on learning Google App Engine and Python, and the next step is to introduce templates. Templates are a good resource for creating and reusing HTML code. The code is available on GitHub.
Changes in the templates
I have modified the template for inserting a many, and also, to keep on using the template and always having the menu available in the center. The base of the example is designed for obtaining the content in the main zone, and that’s the way I need to set up the template:
So, let’s play with templates. Whenever someone click on “Saludo“, I will be using a new template, and when I click on “Lista“, I will be using a different one, although the content will be different but not where we want to show the content.
Saying Hello
In order to say Hello, let’s extent the base template, creating saludo.html, with this code:
{% extends '/base.html' %} {% block contenido %} <h1>Un saludo desde ManejandoDatos.es</h1> Estamos probando <strong>Google App Engine </strong>, y trabajar con plantillas!! {% endblock %}
The first line means that I am extending the base template (base.html) and also, I am introducing the content to a block named contenido.
Coding Listas.html
I will be doing almost the same for listas.html , as a new template using the base.html, template as an extension, but this time, let’s show the content of a list, by using the for instruction. This is the code:
{% extends '/base.html' %} {% block contenido %} <h1>Un saludo desde ManejandoDatos.es</h1> <ul class="list-group"> {% for post in posts %} <li class="list-group-item"> <strong>{{ post.title}}</strong> - {{ post.content}} </li> {% endfor %} </ul> {% endblock %}
As I did with saludo.html, I am creating an extention of base.html, and the data received on the variable posts is used with a for statement to show its content.
Modifying the app
Now I have the templates ready, it is time to make changes on the Python file .py, the engine of the app, and I need to redesign it. So, let’s create a new classes. In order to get a better performance, let’s define a new class first called Handler , based on the class webapp2.RequestHandler, by including two methods:
- render is the functions that “renders” the HTML code to be shown on the browser
- write shows the text that is sent to the browser
The new classes to create will be inherit the Handler class, and all of them has a property with the template associated with it. The get method is the one that shows the information.
There is also an important change in the app, for allowing to call to several URL, so I need to extent what the app can serve. This is done with adding more tuples (‘/’, Principal), (‘/saludo’, Saludo), (‘/lista’, Listas) to the app variable.
the final code is:
import webapp2 import jinja2 import os JINJA_ENVIRONMENT = jinja2.Environment(loader=jinja2.FileSystemLoader(os.path.dirname(__file__) + '/templates' ), extensions=['jinja2.ext.autoescape'], autoescape=True) def render_str(template, **params): t = JINJA_ENVIRONMENT.get_template(template) return t.render(params) class Handler(webapp2.RequestHandler): """ Clase que maneja todo el render y response """ def render(self, template, **kw): self.response.out.write(render_str(template, **kw)) def write(self, *a, **kw): self.response.out.write(*a, **kw) class Principal(Handler): template = 'base.html' def get(self): self.render(self.template) class Saludo(Handler): template = 'saludo.html' def get(self): self.render(self.template) class Listas(Handler): template = 'listas.html' def get(self): posts = [ {"title":"Titulo 1", "content":"Habia una vez ..."}, {"title":"Titulo 2", "content":"Que bueno que llegaste ..."}, {"title":"Titulo 4", "content":"Y ahora ..."}, {"title":"a title4", "content":"Vuelvo ..."} ] self.render(self.template, posts= posts) app = webapp2.WSGIApplication([ ('/', Principal), ('/saludo', Saludo), ('/lista', Listas)], debug=True)
And this is the result of what I’ve done with this example.
If you click on Listas:
Unicode
If you have some problems with Unicode using Python 2, here you have a cool solution to include at the beginning of your code:
</pre> <pre class="lang-py prettyprint prettyprinted"><code><span class="kwd">import</span><span class="pln"> sys reload</span><span class="pun">(</span><span class="pln">sys</span><span class="pun">)</span><span class="pln"> sys</span><span class="pun">.</span><span class="pln">setdefaultencoding</span><span class="pun">(</span><span class="str">'utf-8'</span><span class="pun">)</span></code></pre> <pre>
I read the solution here.
I hope this entrance will be useful!