Создание модуля для Django с нуля

Для тех, кто знаком с Django, эта часть может показаться скучной, поэтому смело пролистывайте её. Я пишу для тех, кто только интересуется, что за зверь такой Django.

Я подразумеваю, что вы знакомы с python и прочитали вводную инструкцию для Django, а ваша операционная система - Ubuntu. Я же не учебник пишу. Почему Ubuntu? На сегодняшний день эта ОС очень активно развивается, а debian-подобная ОС весьма удобна для веб-разработчика.

Итак, установите Django в качестве системной библиотеки. Это не обязательно [1], но тогда у вас в консоли появится команда django-admin. С помощью этой команды можно создавать шаблоны проектов и модулей, этим сейчас и займемся.

Создание проекта

Прежде всего нужен проект, для которого мы бы написали модуль. Создадим пустой проект с помощью django-admin

$ django-admin startproject myproject

Создался пустой Django проект в папке myproject

$ ls myproject/
    __init__.py  manage.py  settings.py  urls.py

Настроим проект с минимальным функционалом, нам нужно будет лишь проверить работу тэга для шаблонов. В settings.py мы прописали настройки базы данных и путь к папке с шаблонами

from os.path import abspath, dirname, join
...
DATABASE_ENGINE = 'sqlite3'
...
TEMPLATE_DIRS = (
    join(dirname(abspath(__file__)), 'templates')
)

Создание модуля

Мы будем писать модуль обратной связи. Работа модуля будет состоять в отображении формы обратной связи с настраиваемыми полями. Форма отправляет сообщения прямиком менеджерам на электропочту. Откровенно говоря, мы его уже написали, но будем честно выполнять все шаги вместе с читателем.

В папке myproject запустите ещё раз django-admin, чтобы создать шаблон модуля

$ cd myproject
$ django-admin startapp feedback

Выполненная команда должна создать папку feedback.

$ ls feedback/
    __init__.py  models.py  tests.py  views.py

Моделей мы делать не будем, т.к. наша форма будет только отправлять электропочту с сайта. В модуле будет одноа вьюха (представление) [2], которая обрабатывает POST запросы из формы, сама форма и немного javascript.

Начнем с формы:

# -*- coding: utf-8 -*-
from django import forms
from django.conf import settings
from django.template.loader import render_to_string


class FeedbackForm(forms.Form):
    email = forms.CharField(label=u'Email', max_length=200)
    topic = forms.CharField(label=u'Topic', max_length=200)
    response = forms.CharField(label=u'Response text', max_length=500,
        widget=forms.Textarea(attrs={'rows': 5, 'cols': 30}))

Напишем вьюху:

# -*- coding: utf-8 -*-
from django.core.urlresolvers import reverse
from django.shortcuts import render_to_response
from feedback.forms import FeedbackForm


def show_feedback_form(request):
    # Обработка POST запроса
    if request.method == 'POST':
        form = FeedbackForm(request.POST)
        if form.is_valid():
            # Если форма прошла валидацию, благодарим пользователя за отзыв
            return render_to_response('thankyou.html', {'form': form})
    else:
    # Если не было POST, рисуем пустую форму
        form = FeedbackForm()
    return render_to_response('index.html', {'form': form})

Создадим шаблон index.html

<h1>Hello!</h1>

<form action="." method="post">
{{ form.as_ul }}
<input type="submit" />
</form>

... и thankyou.html

<h1>Thank you for reply!</h1>

Установка модуля

Теперь модуль нужно установить в проект (в дальнейших статьях описано, в чем разница между подключаемым модулем и модулем в проекте). Для этого пропишите модуль в settings.py INSTALLED_APPS

INSTALLED_APPS = (
    ...
    'feedback',
)

и пропишите адрес вьюхи в urls.py

urlpatterns = patterns('',
    (r'^$', 'feedback.views.show_feedback_form'),
)

Отправка почты

Теперь мы хотим, чтобы форма отправляла почту. Сделаем ей метод mail

from django.core.mail import mail_managers

class FeedbackForm(forms.Form):

    def send_mail(self):
        # готовим контекст для сообщения
        context = {'fields': {}}
        for name, field in self.fields.iteritems():
            context['fields'][name] = self.cleaned_data.get(name, None)
        message = render_to_string('feedback_message.txt', context)

        # тему генерируем с учётом переменной EMAIL_SUBJECT_PREFIX
        subject = settings.EMAIL_SUBJECT_PREFIX + u'feedback'

        mail_managers(subject, message, fail_silently=False)

Во вьюхе добавим после валидации отправку почты [3]

def show_feedback_form(request):
    if request.method == 'POST':
        form = FeedbackForm(request.POST)
        if form.is_valid():
            form.send_mail()  # * Вот здесь
            return render_to_response('thankyou.html', {'form': form})
    else:
        form = FeedbackForm()
    return render_to_response('index.html', {'form': form})

На этом всё, у нас есть форма для обратной связи, которой даже можно пользоваться.

Дальнейшее развитие

Само собой, в этом модуле есть, что улучшить.

  • мы сделали шаблонный тэг для отображения формы обратной связи;
  • страница с благодарностью за отзыв загружается с помощью AJAX;
  • в форму обратной связи можно добавить свои поля.

Я попытался написать про все эти улучшения, но статья получилась слишком большой для новичков и слишком скучной для хайлевелов. Поэтому, кому интересно - смотрите репозиторий на гитхабе: https://github.com/redsolution/django-simple-feedback

Комментарии

[1]Мы используем фреймворк Buildout, знание которого, возможно, снимет многие вопросы по поводу установки Django в систему.
[2]Я называю представления вьюхами, т.к. мне ближе английское model-view-controller, прошу меня простить за эту языковую вольность
[3]У вас всё заработает, если вы действительно можете отправлять почту и у вас настроен почтовый сервер. В противном случае вам нужно установить Django 1.2 и старше, она умеет печатать почту в консоль в debug режиме.