.. _patterns: Patterns in Flask ================= Certain things are common enough that the changes are high you will find them in most web applications. For example quite a lot of applications are using relational databases and user authentication. In that case, changes are they will open a database connection at the beginning of the request and get the information of the currently logged in user. At the end of the request, the database connection is closed again. In Flask you can implement such things with the :meth:`~flask.Flask.before_request` and :meth:`~flask.Flask.after_request` decorators in combination with the special :class:`~flask.g` object. .. _database-pattern: Using SQLite 3 with Flask ------------------------- So here a simple example how you can use SQLite 3 with Flask:: import sqlite3 from flask import g DATABASE = '/path/to/database.db' def connect_db(): return sqlite3.connect(DATABASE) @app.before_request def before_request(): g.db = connect_db() @app.after_request def after_request(response): g.db.close() return response .. _easy-querying: Easy Querying ````````````` Now in each request handling function you can access `g.db` to get the current open database connection. To simplify working with SQLite a helper function can be useful:: def query_db(query, args=(), one=False): cur = g.db.execute(query, args) rv = [dict((cur.description[idx][0], value) for idx, value in enumerate(row)) for row in cur.fetchall()] return (rv[0] if rv else None) if one else rv This handy little function makes working with the database much more pleasant than it is by just using the raw cursor and connection objects. Here is how you can use it:: for user in query_db('select * from users'): print user['username'], 'has the id', user['user_id'] Or if you just want a single result:: user = query_db('select * from users where username = ?', [the_username], one=True) if user is None: print 'No such user' else: print the_username, 'has the id', user['user_id'] To pass variable parts to the SQL statement, use a question mark in the statement and pass in the arguments as a list. Never directly add them to the SQL statement with string formattings because this makes it possible to attack the application using `SQL Injections `_. Initial Schemas ``````````````` Relational databases need schemas, so applications often ship a `schema.sql` file that creates the database. It's a good idea to provide a function that creates the database bases on that schema. This function can do that for you:: from contextlib import closing def init_db(): with closing(connect_db()) as db: with app.open_resource('schema.sql') as f: db.cursor().executescript(f.read()) db.commit() You can then create such a database from the python shell: >>> from yourapplication import init_db >>> init_db() .. _template-inheritance: Template Inheritance -------------------- The most powerful part of Jinja is template inheritance. Template inheritance allows you to build a base "skeleton" template that contains all the common elements of your site and defines **blocks** that child templates can override. Sounds complicated but is very basic. It's easiest to understand it by starting with an example. Base Template ````````````` This template, which we'll call ``layout.html``, defines a simple HTML skeleton document that you might use for a simple two-column page. It's the job of "child" templates to fill the empty blocks with content: .. sourcecode:: html+jinja {% block head %} {% block title %}{% endblock %} - My Webpage {% endblock %}
{% block content %}{% endblock %}
In this example, the ``{% block %}`` tags define four blocks that child templates can fill in. All the `block` tag does is to tell the template engine that a child template may override those portions of the template. Child Template `````````````` A child template might look like this: .. sourcecode:: html+jinja {% extends "layout.html" %} {% block title %}Index{% endblock %} {% block head %} {{ super() }} {% endblock %} {% block content %}

Index

Welcome on my awesome homepage. {% endblock %} The ``{% extends %}`` tag is the key here. It tells the template engine that this template "extends" another template. When the template system evaluates this template, first it locates the parent. The extends tag must be the first tag in the template. To render the contents of a block defined in the parent template, use ``{{ super() }}``. .. _message-flashing-pattern: Message Flashing ---------------- Good applications and user interfaces are all about feedback. If the user does not get enough feedback he will probably end up hating the application. Flask provides a really simple way to give feedback to a user with the flashing system. The flashing system basically makes it possible to record a message at the end of a request and access it next request and only next request. This is usually combined with a layout template that does this. So here a full example:: from flask import flash, redirect, url_for, render_template @app.route('/') def index(): return render_template('index.html') @app.route('/login', methods=['GET', 'POST']) def login(): error = None if request.method == 'POST': if request.form['username'] != 'admin' or \ request.form['password'] != 'secret': error = 'Invalid credentials' else: flash('You were sucessfully logged in') return redirect(url_for('index')) return render_template('login.html', error=error) And here the ``layout.html`` template which does the magic: .. sourcecode:: html+jinja My Application {% with messages = get_flashed_messages() %} {% if messages %}

{% endif %} {% endwith %} {% block body %}{% endblock %} And here the index.html template: .. sourcecode:: html+jinja {% extends "layout.html" %} {% block body %}

Overview

Do you want to log in? {% endblock %} And of course the login template: .. sourcecode:: html+jinja {% extends "layout.html" %} {% block body %}

Login

{% if error %}

Error: {{ error }} {% endif %}

Username:
Password:

{% endblock %}