Лекция 5 Серверная разработка

Preview:

DESCRIPTION

Лекция 5 Серверная разработка

Citation preview

Серверная разработка

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

Техносфера 2014

Что мы научимся делатьОбработка GET и POST запросов

Генерация HTML при помощи шаблонов

Знакомство с Django

Типичные задачисерверной разработкиОтображение и изменение(CRUD) объектов насервере

Предоставление API и взаимодействие c APIдругих сервисов

Языки сервернойразработки

Компилируемые

C/C++ модули к Web серверам

Java

C#

Языки сервернойразработки

Интерпретируемые

Perl

PHP

Ruby

Python

Javascript (NodeJS)

Lua (скриптование веб-серверов)

Языки сервернойразработки

Новая волна

Go

Erlang

Scala

Groovy

ТенденцииФункциональный подход

Асинхронность

Распределенность

Real-Time

Взаимодействие веб-сервера с приложением

CGI

FastCGI

WSGI

Веб-сервер встроенный в приложение

CGI #!/usr/bin/python

import osimport sys

print "Content-type: text/html"print "Status: 200"print ""print "<h1>Hello, world!</h1>"

for k, v in os.environ.items(): print "%s = %s<br>" % (k, v)

print >> sys.stderr, "Nice to meet you"

Заголовки ответаBooking.com HTTP/1.1 200 OK Server: nginx Date: Sun, 27 Oct 2013 10:08:40 GMT Content-Type: text/html; charset=UTF-8 Content-Length: 42510 Connection: keep-alive Cache-Control: private Vary: User-Agent, Accept-Encoding Content-Encoding: gzip X-Recruiting: Like HTTP headers? Come write ours: booking.com/jobs

Заголовки ответаReddit.com HTTP/1.1 200 OKContent-Type: text/html; charset=UTF-8Vary: accept-encodingContent-Encoding: gzipContent-Length: 19879Server: '; DROP TABLE servertypes; --Date: Sun, 27 Oct 2013 10:10:10 GMTConnection: keep-alive

GET параметрыГиперссылка <a href="‘/hello.cgi?name=me&greeting=hello’">Hello!</a>

Переменная окружения QUERY_STRING=name=me&greeting=hello

CGI-скрипт import urlparseparams = urlparse.parse_qs('name=me&greeting=hello')

POST параметрыФорма <form method="”post”" action="”/hello.cgi”"> <input name="”name”" value="”me”/"> <input name="”greeting”" value="”hi”/"> <input type="”submit”/"></form>

CGI скрипт qs = sys.stdin.read()

или cgi.FieldStorage()

Фаилы в POST и Non-ASCII символыMultipart/form-data <form method="”post”" action="”/hello.cgi”" enctype= <input name="”name”" value="”me”/"> <input name="”pic”" type="”file”/"> <input type="”submit”/"></form>

URI encoding <a href="”/hello.cgi?name=%D0%B8%D0%BC%D1%8F”">привет</a>

Обработка параметров import cgiform = cgi.FieldStorage()

# Наличие параметровif not 'name' in form: raise ValidationError('panic')# Валидацияif not re.match('[a-z]+', form['name']): raise ValidationError('panic')# Очисткаstory = re.sub('<[̂>]+>', ' ', form['story'])# Экранированиеstory = form['story']story = story.replace('<', '&lt;')story = story.replace('>', '&gt;')

Переменные окружения HTTP_COOKIEHTTP_USER_AGENTPATH_INFOQUERY_STRINGREMOTE_ADDRREQUEST_METHODSCRIPT_FILENAMESCRIPT_NAME…

WSGI def application(environ, start_response): status = '200 OK' output = 'Hello World!'

response_headers = [ ('Content-type', 'text/plain'), ('Content-Length', str(len(output))) ] start_response(status, response_headers)

return [output]

Gunicorn

Как запустить gunicorn myproject.wsgi:application

АльтернативыuWSGI

Tornado

Werkzeug

Решаемыезадачи

Обработка форм request = Request(environ)error = Noneurl = ''if request.method == 'POST': url = request.form.get('url') if not is_valid_url(url): error = 'Please enter a valid URL' else: short_id = insert_url(url) return redirect('/%s' % short_id)return render_template('new_url.html', error=error, url=url)

Обработка формОтображение формы и изменение через одинобработчик

Сообщение об ошибке и успехе

Проверка данных на сервере и клиенте

Ajax Frontend var request = $.ajax({ url: ”/like/", type: "POST", data: {id : itemId}, dataType: "json"}); request.done(function(result) { if (result.status) { $("#log").html( result.msg ); }}); request.fail(function(jqXHR, textStatus) { alert("Request failed: " + textStatus);})

Ajax Backend import json

request = Request(environ)

json_data = json.dumps({ 'status': True, 'msg': u'Лайк!'})

response = Response(json_data, mimetype='text/plain')return response(environ, start_response)

Хранение данных наклиенте

Что нужно хранить о пользователе

Авторизацию

Временную информацию

Cookie и сессии

Cookie передаются вместе запросом

Сессии хранятся на сервере (в файлах, в базе),идентификатор сессии передаются в куках

Cookie ЗаголовкиSet-Cookie: name=val; path=/; domain=domain.ru; expires=Tue, 20 Mar 2012 11:52:54 GMTCookie: name=val;name2=val2;is_visited=2011-13-15

Установкаimport Cookiecookie = Cookie.SimpleCookie()cookie['name'] = 'val'cookie['name']['path'] = '/path'

Получениеcookie.load('a=b;c=d')for name in cookie: print '%s => %s' % (name, cookie[name])

Шаблонизаторы '''<html><body> <h1>%s</h1></body></html>’’ % name

VS context = { 'user' : get_user(form['name']), 'friends' : get_friends(form['name']) }

render('tpl/home.html', context)

Шаблонизаторы

ШаблонизаторыDjango, Jinja2 {% extends "layout.html" %}{% block body %} <ul> {% for user in users %} <li> {% include helper %}</li> {% endfor %} </ul>{% endblock %}

SSI <!--# echo var=”Email" default="" -->

<!--# include virtual="/remote/body.php?argument=value" -->

<!--# if expr="$name = /(.+)@(?P<domain>.+)/" --> <!--# echo var="1" --> <!--# echo var="domain" --> <!--# endif -->

ФреймворкиГотовая архитектура проекта

Решения для часто-встречающихся задач

Все их используют

Flask app = Flask(__name__)

@app.route('/')def index_page(): db = get_db() cur = db.execute('select title, text from entries order by id desc' entries = cur.fetchall() return render_template('show_entries.html', entries=entries)

@app.route('/contact/')def contact_page(): return render_template('contact_page.html')

MVC

ПримерыPHP - CodeIgniter, Yii

ASP.Net MVC Framework

Perl - Catalyst

Python - Django, Pyramid

Ruby - Ruby on Rails

Почему Django?

Почему Django?

Почему Django?Instagram

40+ миллионов пользователей

100+ виртуальных серверов

1 миллион регистраций за 12 часов послезапуска Android версии

5 разработчиков

Почему Django?Pinterest

3 миллиона посетителей в день

4 по популярности в США после Facebook,Twitter, LinkedIn

410 ТБ пользовательских данных

Почему Django?Disqus

500 миллионов уникальных посетителей вмесяц

750 тысяч сайтов используют Disqus

165 тысяч сообщений в секунду

8 инженеров-разработчиков

Django

Возможности фреймворкаГибкая ORM

Интерфейс администрирования

Диспетчер URL на основе регулярныхвыражений

Шаблонизатор

Кэширующий фреймворк

Интернационализация

Обширное комьюнити

Структура проектаПроект состоит из приложений

Приложения могут находиться где угодно вPython path

Pluggable-приложения

Полезные ссылкиhttp://docs.djangoproject.com/

http://www.djangosites.org/with-source/

https://github.com/django/django

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

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

s.lihobabin@corp.mail.ru

Recommended