context processor の使い方

以下の内容は、 Django 1.3.1 での動作を想定しています。


メニューの有効/無効ですが、モノによってはその属性の class を書き換えて
切り替えているものがあります。
名前付きの URL を設定している場合、名前に合っていた場合
表示する内容を変更するなど出来れば嬉しいですね。


じゃあ、どうするかというと、書くページ表示時に Template 変数として
URL名があれば良いです。こんな時のために Django では context processor
という仕組みがあります。


context processor とは、request を受け取って辞書を返す関数で、
settings にて Django に登録してあげればページ表示時に辞書の
内容が template 変数にマージされる機能です。


利用する際は以下の 3ステップを踏みます。
1. context processor を作成する。
2. settings に記載する。
3. template で利用する。

1. context processor を作成する。

上記でも記載したように、request を受け取って辞書を返す
関数です。今回は URL名を返したいので以下の内容で作成します。


関数は最終的にアプリから呼べる場所に記載します。


app/hoge/context_processors.py

# -*- coding: utf-8 -*-                                                                                                                         
from django.core.urlresolvers import resolve


def url_name(request):
    'Returns context variables helpful for url_name.'
    urlname = resolve(request.path_info).url_name
    return dict(URL_NAME=urlname)

2. settings に記載する。

context processor は作成したら settings の
TEMPLATE_CONTEXT_PROCESSORS に登録します。


settings を以下の内容で修正します。

# -*- coding: utf-8 -*-
import os
# Django 標準の設定を読み込む
from django.conf.global_settings import TEMPLATE_CONTEXT_PROCESSORS                                                                             

...

# 今回は、app/hoge/context_processors.py に
# url_name 関数を記載したため以下の内容となります。
TEMPLATE_CONTEXT_PROCESSORS += (                                                                                                                
    'app.hoge.context_processors.url_name',
)

3. template で利用する。

以下の内容のように、URL_NAME を template で利用できるようになります。

    <ul class="nav">
      <li{% ifequal URL_NAME 'index' %} class="active"{% endifequal %}>
        <a href="{% url idx %}">Home</a>
      </li>
      <li{% ifequal URL_NAME 'hoge' %} class="active"{% endifequal %}>
        <a href="{%  url tl %}">hoge</a>
      </li>
    </ul>

参考になった資料

検索しても参考になりそうな情報がなく、
ソースコードがとても参考になりました。
パスとしては以下のパスのソースを参考にしました。

lib/python2.7/site-packages/django/core/context_processors.py