Хостинг Django от «Джино»
Table of contents

Простая проверка данных

Наш пример с поиском всё ещё остаётся достаточно простым, особенно с точки зрения проверки передаваемых данных. Мы просто проверяем наличие информации в запросе. Множество HTML форм включают в себя значительно более сложные проверки. Все мы видели такие сообщения об ошибках на сайтах:

  • «Пожалуйста, введите верный адрес электронной почты. 'foo' не является адресом электронной почты.»

  • «Пожалуйста, введите верный шестизначный код почтового отделения. '123' не является почтовым кодом.»

  • «Пожалуйста, введите верную дату в формате DD-MM-YYYY.»

  • «Пожалуйста, введите пароль, который содержит как минимум 8 символов и содержит хотя бы одну цифру.»

Об использовании JavaScript для проверки данных

Хотя мы не рассказываем об этом, но вы можете использовать JavaScript для проверки данных на стороне клиента, прямо в браузере. Но помните, даже если вы это делаете, вы обязаны сделать проверку и на стороне сервера. Некоторые пользователи не включают JavaScript, а «злобные хакеры» могут передавать самостоятельно сформированные данные, которые не доступны JavaScript коду.

И вы ничего не можете с этим поделать, остаётся только всегда проверять данные, переданные пользователями, на стороне сервера (т.е., в ваших представлениях). Проверку с помощью JavaScript следует рассматривать как дополнительную удобную функциональность сайта, но не как замену основного механизма проверки.

Давайте доработаем наше представление search() так, чтобы оно проверяло переданную строку на превышение её длины в 20 символов. (Предположим для этого примера, что передача более длинной строки значительно замедлит скорость выполнения поиска.) Как мы можем это сделать? Самым простым способом будет внедрение логики прямо в представление, вот так:

def search(request):
    error = False
    if 'q' in request.GET:
        q = request.GET['q']
        if not q:
            error = True
        elif len(q) > 20:
            error = True
        else:
            books = Book.objects.filter(title__icontains=q)
            return render_to_response('search_results.html',
                {'books': books, 'query': q})
    return render_to_response('search_form.html',
        {'error': error})

Теперь, при попытке отослать запрос с длиной строки более 20 символов, вы получите сообщение об ошибке. Но это сообщение в search_form.html пока говорит «Please submit a search term.» и нам потребуется изменить его так, чтобы оно учитывало оба случая:

<html>
<head>
    <title>Search</title>
</head>
<body>
    {% if error %}
        <p style="color: red;">Please submit a search term 20 characters or shorter.</p>
    {% endif %}
    <form action="/search/" method="get">
        <input type="text" name="q">
        <input type="submit" value="Search">
    </form>
</body>
</html>

Есть что-то некрасивое в этом. Наше «универсальное» сообщение об ошибке может запутать. Как может сообщение для пустого запроса упоминать об ограничении размера строки запроса 20-ю символами? Сообщение об ошибке должно быть точное.

Проблема заключается в том, что мы используем обычное булево значение для error, а надо использовать список строк с сообщениями об ошибке. Вот так мы можем изменить код:

def search(request):
    errors = []
    if 'q' in request.GET:
        q = request.GET['q']
        if not q:
            errors.append('Enter a search term.')
        elif len(q) > 20:
            errors.append('Please enter at most 20 characters.')
        else:
            books = Book.objects.filter(title__icontains=q)
            return render_to_response('search_results.html',
                {'books': books, 'query': q})
    return render_to_response('search_form.html',
        {'errors': errors})

Затем, надо сделать небольшое исправление в search_form.html для того, чтобы учесть изменения в коде — в шаблон передаётся список error, а не булево значение:

<html>
<head>
    <title>Search</title>
</head>
<body>
    {% if errors %}
        <ul>
            {% for error in errors %}
            <li>{{ error }}</li>
            {% endfor %}
        </ul>
    {% endif %}
    <form action="/search/" method="get">
        <input type="text" name="q">
        <input type="submit" value="Search">
    </form>
</body>
</html>

rad 3 days, 19 hours ago
Answer Link

Не согласен.

А вот подкорректировать последний абзац надо, там должно быть errors, а не error.

sskajn 6 days, 5 hours ago
Answer Link

в предпоследнем листинге ошибка в название переменной: не errors, а error, то есть, вот так должно быть:

def search(request):
error = []
if 'q' in request.GET:
q = request.GET['q']
if not q:
error.append('Enter a search term.')
elif len(q) > 20:
error.append('Please enter at most 20 charecters.')
else:
books = Book.objects.filter(title__icontains=q)
return render_to_response('search_form.html',
{'books': books, 'query': q})
return render_to_response('search_form.html', {'errors': error})


Ищем Python программистов

Found misprint?
Select it with the mouse and hit Enter
Ctrl-Enter
Processed:
33 1 199 25


The full repository of DjangoBook translation you can get on GitHub.
We appreciate your patches!

We are glad to hear your questions, comments or suggestions!
(Open in new tab)

Users number: 601

Русская группа

на поддержку перевода
Яндекс Яндекс.Деньги Хочу такую же кнопку
Ускорить процесс перевода!
ЯМ:41001223475816


© 2008-2012 Ruslan Popov @ gmail.com Powered by Django 1.2.5