44
Django. Дополнительные темы. Django Views Сергей Лихобабин Техносфера . 2014

Л8 Django. Дополнительные темы

Embed Size (px)

DESCRIPTION

Л8 Django. Дополнительные темы

Citation preview

Page 1: Л8 Django. Дополнительные темы

Django. Дополнительныетемы.

Django Views

Сергей Лихобабин

Техносфера. 2014

Page 2: Л8 Django. Дополнительные темы

Еще несколько слов о manage.py

Middleware

Сессии

Приложение auth

Class Based Views

Расширение фильтров и тэгов в шаблонизаторе

Другие приложения из коробки

Оптимизация производительности

Page 3: Л8 Django. Дополнительные темы

Management командыStandalone скрипты

Задачи для cron'а

Page 4: Л8 Django. Дополнительные темы

Пример команды

class Command(BaseCommand): help = 'Fill database with test data' def handle(self, *args, **options): for i in xrange(USER_COUNT): user = User( name=get_random_string(10), email=get_random_email() ) user.save() self.stdout.write( 'Imported %d users' % USER_COUNT )

Page 5: Л8 Django. Дополнительные темы

Middleware

Page 6: Л8 Django. Дополнительные темы
Page 7: Л8 Django. Дополнительные темы

Сценарии использования

Обработка запроса

Статистика

Аутентификация

Защита от CSRF

Редиректы

Кеширование

Page 8: Л8 Django. Дополнительные темы
Page 9: Л8 Django. Дополнительные темы

CSRF в Django«Небезопасные» методы POST, PUT и DELETE

Установка cookie (csrftoken)

Установка hidden поля (csrfmiddlewaretoken) илизаголовка (X-CSRFToken)

Page 10: Л8 Django. Дополнительные темы

Важные моментыДля установки куки страница должна отдаватьсядинамически

Кука может не ставиться, если передачаконтекста идет через Context вместоRequestContext

Скрытое поле ставится тегом {% csrf_token %},используйте RequestContext (функция render)

Токен в ajax запросах удобнее передаватьзаголовком

Page 11: Л8 Django. Дополнительные темы

СессииСессии в БД

Фаиловые сессии

Сессии в куках

Page 12: Л8 Django. Дополнительные темы

Использование сессий

def login(request): username = request.POST.get('username') try: user = User.objects.get(username=username) except User.DoesNotExist: return HttpResponse("No such user") if user.check_password(request.POST.get('password')): request.session['user_id'] = user.id return HttpResponse("You're logged in.") else: return HttpResponse("Wrong credentials.")

Page 13: Л8 Django. Дополнительные темы

Использование сессий

def logout(request): try: del request.session['user_id'] except KeyError: pass return HttpResponse("You're logged out.")

Page 14: Л8 Django. Дополнительные темы

Декораторы

Page 15: Л8 Django. Дополнительные темы

Пример декоратора

def makebold(fn): def wrapped(): return "<b>" + fn() + "</b>" return wrapped def makeitalic(fn): def wrapped(): return "<i>" + fn() + "</i>" return wrapped

Page 16: Л8 Django. Дополнительные темы

Пример декоратора

@makebold@makeitalicdef hello(): return "hello world" // hello = makebold(makeitalic(hello)) print hello() ## returns <b><i>hello world</i></b>

Page 17: Л8 Django. Дополнительные темы

Декораторы для Djangoviews

@require_POSTdef vote_view(request): # only POST method is allowed pass либо url(r"̂vote/", require_POST(vote)),

Page 18: Л8 Django. Дополнительные темы

Декораторы для Djangoviews

Проверка HTTP-методов

Проверка прав доступа

Кеширование

Page 19: Л8 Django. Дополнительные темы

Django auth

Page 20: Л8 Django. Дополнительные темы

Возможности Django authПользователи

Проверка прав доступа

Обработчики login/logout

Интеграция с админкой

Кастомизация модели пользователя

Page 21: Л8 Django. Дополнительные темы

Проверка авторизации воviews

def my_view(request): if not request.user.is_authenticated(): return redirect( '/login/?next=%s' % request.path ) user = request.user

@login_requireddef my_view(request): ...

Page 22: Л8 Django. Дополнительные темы

Проверка авторизации вшаблонах

{% if user.is_authenticated %} Welcome, {{ user.username }}{% else %} Please log in.{% endif %}

Page 23: Л8 Django. Дополнительные темы

Class based views

Page 24: Л8 Django. Дополнительные темы

Функция-обработчик.Пример 1

def post_detail(request, pk): try: object = Post.objects.get(pk=pk) except Post.DoesNotExist: raise Http404 return render( request, 'blog/post_detail.html', {'object': object} ) urlpatterns = patterns('', url( r'̂post/(?P<pk>\d+)/$', post_detail, name= 'post_detail' ),)

Page 25: Л8 Django. Дополнительные темы

Класс-обработчик. Пример 1

class PostDetail(generic.DetailView): model=Post

urlpatterns = patterns('', url( r'̂post/(?P<pk>\d+)/$', PostDetail.as_view(), name= 'post_detail' ),)

Page 26: Л8 Django. Дополнительные темы

Функция-обработчик.Пример 2

def post_list(request): paginator = Paginator(Post.objects.all(), 25) page = request.GET.get('page') try: posts = paginator.page(page) except PageNotAnInteger: posts = paginator.page(1) except EmptyPage: posts = paginator.page(paginator.num_pages) return render( request, 'blog/post_list.html', {'object_list': posts} )

Page 27: Л8 Django. Дополнительные темы

Класс-обработчик. Пример2

class PostList(generic.ListView): model = Post paginate_by = 25

Page 28: Л8 Django. Дополнительные темы

Функция-обработчик.Пример 3

@login_requireddef category(request, pk): cat = get_object_or_404(Category, pk=pk) post_list = Post.objects.filter(category=cat) return render(request, 'blog/category.html', { 'category': cat, 'post_list' : post_list })

Page 29: Л8 Django. Дополнительные темы

Класс-обработчик. Пример3

class CategoryListView(generic.ListView): template_name = 'blog/category.html'

def get_queryset(self): self.cat = get_object_or_404( Category, pk=self.kwargs['pk'] ) return Post.objects.filter(category=self.cat)

@method_decorator(login_required) def dispatch(self, *args, **kwargs): return super(CategoryListView, self).dispatch(*args, **kwargs)

def get_context_data(self, **kwargs): context = super(CategoryListView, self).get_context_data(**kwargs) context['category'] = self.cat

Page 30: Л8 Django. Дополнительные темы

Полезный справочник поCBV

http://ccbv.co.uk/

Page 31: Л8 Django. Дополнительные темы

Фильтры и теги вшаблонизаторе

Page 32: Л8 Django. Дополнительные темы

Построение урлов

class Post(models.Model): @models.permalink def get_absolute_url(self): return ('post_detail', (self.pk,)) # либо def get_absolute_url(self): return reverse('post_detail', args=(self.pk,))

Page 33: Л8 Django. Дополнительные темы

Построение урлов

<a href="{{ post.get_absolute_url }}">{{ post }}</a>

<a href="{% url 'post_detail' post.pk %}">{{ post }}</a>

Page 34: Л8 Django. Дополнительные темы

Фильтры и теги

Page 35: Л8 Django. Дополнительные темы

Фильтры и тегиТэг присваивания

Блочный тэг

{% get_current_time "%Y-%m-%d %I:%M %p" as the_time %}

{% switch %} {% endswitch %}

Page 36: Л8 Django. Дополнительные темы

Пример регистрации тэга

from django import templatefrom blog.models import Post

register = template.Library() @register.inclusion_tag('blog/tags/lastposts.html')def last_posts(): return {'post_list': Post.objects.all()[:5]}

Page 37: Л8 Django. Дополнительные темы

Использование в шаблонах

{% load blog_tags %}{% last_posts %}

<ul>{% for object in post_list %} <li> <a href="{{ object.get_absolute_url}}"> {{ object }} </a> </li>{% endfor %}</ul>

Page 38: Л8 Django. Дополнительные темы

Оптимизацияпроизводительности

Page 39: Л8 Django. Дополнительные темы

Особенности кэшаБыстрый доступ к кешу

Высокая вероятность использования кеша

Временное хранилище

Page 40: Л8 Django. Дополнительные темы

Кэш-бэкенды в DjangoMemcached

База данных

Файловая система

Локальная память

Dummy (для разработки)

Page 41: Л8 Django. Дополнительные темы

Уровни кэшированияВесь сайт

Контроллер

Часть шаблона

Часть данных (ручное управление)

Page 42: Л8 Django. Дополнительные темы

Performance Best-practiceПрофилируйте страницы с Django Debug Toolbar

Используйте правильные индексы (db_index)

Делайте выборки по тем полям, которые вамнужны (методы only, values and values_list)

Доставайте только те объекты, которые будутиспользованы

Не делайте лишних запросов к БД

Python не должен делать работу за БД (методыcount, exist)

Page 43: Л8 Django. Дополнительные темы

DRY

KISS

Page 44: Л8 Django. Дополнительные темы

Спасибо за внимание

Сергей Лихобабин

[email protected]