92
Mojolicious. Веб в коробке! Perl Mova + YAPC::Russia 2010

Mojolicious. Веб в коробке!

Embed Size (px)

DESCRIPTION

Perl Mova + YAPC::Russia 2010

Citation preview

Page 1: Mojolicious. Веб в коробке!

Mojolicious.Веб в коробке!

Perl Mova + YAPC::Russia 2010

Page 2: Mojolicious. Веб в коробке!
Page 3: Mojolicious. Веб в коробке!

Что такое Mojolicious?

Page 4: Mojolicious. Веб в коробке!

Что такое Mojolicious?

• Веб-фреймворки: Mojolicious::Lite, Mojolicious, Mojo

• Объектно-ориентированное API, без скрытой магии и зависимостей, написанное на чистом Perl

• Полный стек HTTP 1.1 и WebSocket #76(клиент-сервер), а также IPv6, SSL и IDNA

Page 5: Mojolicious. Веб в коробке!

Что такое Mojolicious?

• Асинхронный ввод-вывод, prefork-веб сервер с поддержкой epoll и kqueue, unix-сокетов и «горячей» разработки

• CGI, FastCGI и PSGI

• RESTful-роутеры, плагины, сессии, Perl-ish шаблонизатор, поддержка I18N, JSON и XML DOM с CSS3-селекторами

Page 6: Mojolicious. Веб в коробке!

«Свежий» код, основанный на опыте разработке Catalyst

Page 7: Mojolicious. Веб в коробке!

«Весёлая ферма» Mojolicious

Page 8: Mojolicious. Веб в коробке!

CGI FastCGI PSGI HTTP 1.1 WebSocket

Mojo

Mojolicious

Mojolicious::Lite

Код

Удовольствие!

Код

Page 9: Mojolicious. Веб в коробке!

Mojolicious::LiteMVC веб-фреймворк

~ sinatra

Page 10: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

get '/hello' => sub { shift->render_text( 'Привет Киев!' );};

app->start;

Page 11: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

post '/hello' => sub { shift->render_text( 'Привет Киев!' );};

app->start;

Page 12: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

any '/hello' => sub { shift->render_text( 'Привет Киев!' );};

app->start;

Page 13: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

get '/hello' => (agent => qr/Firefox/) => sub { shift->render_text( 'Привет Киев!' );};

app->start;

Page 14: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

post '/:name' => sub { # /* my $self = shift; my $name = $self->param('name');

$self->render_text( "Привет $name!" );};

app->start;

Page 15: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

post '/:name' => sub { # /* my $self = shift; my $name = $self->stash('name');

$self->render_text( "Привет $name!" );};

app->start;

Page 16: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

post '/:name' => { id => 42 } => sub { # /* my $self = shift; my $name = $self->param('name'); warn $self->param( 'id' ); $self->render_text( "Привет $name!" );};

app->start;

Page 17: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

any '/time' => 'clock';

app->start;

__DATA__

@@ clock.html.ep% my ($sec, $min, $hour) = (localtime)[0, 1, 2];Текущее время <%= $hour %>:<%= $min %>:<%= $sec %>

Page 18: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

websocket '/echo' => sub { my $self = shift; $self->receive_message( sub { my ($self, $msg) = @_; $self->send_message( "тук-тук: $msg" ); } );};

Page 19: Mojolicious. Веб в коробке!

Примеры Mojolicious WebSocket

@xantus, @vtiИнтересный пример IRC-клиент

Page 20: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

get '/fetch' => sub { my $self = shift; $self->render_data( $self->client ->get( 'http://2010.yapcrussia.org' ) ->res ->body );};

Page 21: Mojolicious. Веб в коробке!

use Mojolicious::Lite;

plugin charset => { charset => 'UTF-8' };

#

under sub { my $self = shift;

# проверка авторизации };get '/foo' => sub { ... };

Page 22: Mojolicious. Веб в коробке!

Cписок всех роутеров приложения

script/lite.pl routes/hello (?-xism:^/hello)/time (?-xism:^/time)/echo (?-xism:^/echo)/fetch (?-xism:^/fetch)/:name (?-xism:^/((?-xism:\d+)))

Page 23: Mojolicious. Веб в коробке!

Если много шаблонов в секции __DATA__script/lite.pl inflate

/templates//templates/clock.html.ep

Page 24: Mojolicious. Веб в коробке!

Сокращатель ссылокна Mojolicious::Lite

100 строк кода (5 обработчиков)130 строк шаблонов (4 шаблона)

1 файл

Page 25: Mojolicious. Веб в коробке!
Page 26: Mojolicious. Веб в коробке!

MojoliciousMVC веб-фреймворк

~ Ruby on Rails

Page 27: Mojolicious. Веб в коробке!

package App;use base 'Mojolicious';

sub startup { my $self = shift; my $r = $self->routes; $r->route('/:controller/:action/:id') ->to('example#welcome', id => 1);}

1;

Page 28: Mojolicious. Веб в коробке!

package App;use base 'Mojolicious';

sub startup { my $self = shift; my $r = $self->routes; $r->route('/:controller/:action/:id') ->to('example#welcome', id => 1);}

1;

Page 29: Mojolicious. Веб в коробке!

package App;use base 'Mojolicious';

sub startup { my $self = shift; my $r = $self->routes; $r->route('/:controller/:action/:id') ->to('example#welcome', id => 1);}

1;

Page 30: Mojolicious. Веб в коробке!

package App;use base 'Mojolicious';

sub startup { my $self = shift; my $r = $self->routes; $r->route('/:controller/:action/:id') ->to('example#welcome', id => 1);}

1;

Page 31: Mojolicious. Веб в коробке!

package App;use base 'Mojolicious';

sub startup { my $self = shift; my $r = $self->routes; my $b = $r->bridge->to('auth#check); $b->route('/admin')->to('admin#welcome');}

Page 32: Mojolicious. Веб в коробке!

package App;use base 'Mojolicious';

sub startup { my $self = shift; $self->plugin(charset => { ... }); $self->types->type(json => 'text/plain'); $self->renderer->root( ... );}

1;

Page 33: Mojolicious. Веб в коробке!

package App;use base 'Mojolicious';

sub startup { my $self = shift; my $r = $self->routes; $r->route('/:controller/:action/:id') ->to('example#welcome', id => 1);}

1;

Page 34: Mojolicious. Веб в коробке!

package App::Example;use base 'Mojolicious::Controller';

sub welcome { my $self = shift; warn $self->param( ‘id’ ); $self->render( message => 'Привет Киев!' );}

1;

Page 35: Mojolicious. Веб в коробке!

package App::Example;use base 'Mojolicious::Controller';

sub welcome { my $self = shift; warn $self->stash( ‘id’ ); $self->render( message => 'Привет Киев!' );}

1;

Page 36: Mojolicious. Веб в коробке!

Шаблонexample/welcome.html.ep

controller / action . format . handler

Page 37: Mojolicious. Веб в коробке!

Шаблонexample/welcome.xml.ep

controller / action . format . handler

Page 38: Mojolicious. Веб в коробке!

Шаблонexample/welcome.rss.ep

controller / action . format . handler

Page 39: Mojolicious. Веб в коробке!

Шаблонexample/welcome.mail.ep

controller / action . format . handler

Page 40: Mojolicious. Веб в коробке!

Шаблонexample/welcome.html.ep

controller / action . format . handler

Page 41: Mojolicious. Веб в коробке!

Шаблонexample/welcome.html.ep

controller / action . format . handler

Page 42: Mojolicious. Веб в коробке!

Шаблонexample/welcome.html.tt

controller / action . format . handler

Page 43: Mojolicious. Веб в коробке!

Шаблонexample/welcome.html.cttp2

controller / action . format . handler

Page 44: Mojolicious. Веб в коробке!

Шаблонexample/welcome.html.ep

controller / action . format . handler

Page 45: Mojolicious. Веб в коробке!

% layout 'default';

<h2><%= $message %></h2>

<a href="<%== url_for %>">click here</a>

Page 46: Mojolicious. Веб в коробке!

% layout 'default';

<h2><%= $message %></h2>

<a href="<%== url_for %>">click here</a>

Page 47: Mojolicious. Веб в коробке!

% layout 'default';

<h2><%= stash 'message' %></h2>

<a href="<%== url_for %>">click here</a>

Page 48: Mojolicious. Веб в коробке!

% layout 'default';

<h2><%= $self->stash('message') %></h2>

<a href="<%== url_for %>">click here</a>

Page 49: Mojolicious. Веб в коробке!

% layout 'default';

<h2><%= $message2 %></h2>

<a href="<%== url_for %>">click here</a>

Page 50: Mojolicious. Веб в коробке!

Global symbol "$message2" requires explicit package name at (eval 280) line 2.

1: % layout 'default';2: <h2><%= $message2 %></h2>3: ...

{ 'status' => 500, 'message' => ‘Привет Киев!’, ...

Page 51: Mojolicious. Веб в коробке!

% layout 'default';

<h2><%= $message if is_iphone %></h2>

<a href="<%== url_for %>">click here</a>

Page 52: Mojolicious. Веб в коробке!

sub startup { ... $self->renderer->add_helper( is_iphone => sub { shift->tx->req->headers ->user_agent =~ /iphone|cfnetwork/i ? 1 : 0 });

Page 53: Mojolicious. Веб в коробке!

Шаблонlayouts/default.html.epпуть к layout-шаблонам / имя . format . handler

Page 54: Mojolicious. Веб в коробке!

<!doctype html><html> <head><title> Привет! </title></head> <body> <%== content %> </body></html>

Page 55: Mojolicious. Веб в коробке!

Около 20 проектовна Mojolicious

Page 56: Mojolicious. Веб в коробке!
Page 57: Mojolicious. Веб в коробке!

MojoБазовый веб-фреймворк

Page 58: Mojolicious. Веб в коробке!

package App;use base 'Mojo';

sub handler { my ($self, $tx) = @_; warn $tx->req; warn $tx->req->url; $tx->res->headers ->content_type( 'text/plain' ); $tx->res->body( 'Привет Киев!' );}

Page 59: Mojolicious. Веб в коробке!

package App;use base 'Mojo';

sub handler { my ($self, $tx) = @_; warn $tx->req; warn $tx->req->url; $tx->res->headers ->content_type( 'text/plain' ); $tx->res->body( 'Привет Киев!' );}

Page 60: Mojolicious. Веб в коробке!

GET / HTTP/1.1Connection: keep-aliveAccept: text/html, application/xhtml, ....Accept-Charset: windows-1251, utf-8; ...Accept-Encoding: gzip,deflateAccept-Language: ru,en-us;q=0.7,en;q=0.3Host: localhost:3000User-Agent: Mozilla/5.0 (Macintosh; ...Content-Length: 0Keep-Alive: 300

Page 61: Mojolicious. Веб в коробке!

package App;use base 'Mojo';

sub handler { my ($self, $tx) = @_; warn $tx->req; warn $tx->req->url; $tx->res->headers ->content_type( 'text/plain' ); $tx->res->body( 'Привет Киев!' );}

Page 62: Mojolicious. Веб в коробке!
Page 63: Mojolicious. Веб в коробке!

Mojo::ClientHTTP 1.1 и WebSocket клиент

Page 64: Mojolicious. Веб в коробке!

my $client = Mojo::Client->new;

$client->get( ‘http://2010.yapcrussia.org’ => sub { my ($self, $tx) = @_; say $tx->res; })->process;

Page 65: Mojolicious. Веб в коробке!

my $client = Mojo::Client->new;

$client->get( ‘http://2010.yapcrussia.org’ => sub { ... },);$client->post( ‘http://2010.yapcrussia.ru’ => sub { ... },);

$client->process;

Page 66: Mojolicious. Веб в коробке!

my $client = Mojo::Client->new;

$client->get(‘http://goo.gl’)->res->code;

$client->get( 'http://search.twitter.com/trends.json')->success->json->{trends}->[0]->{name}

$client->get( ... )->dom->success ->search('body > #container > div p[id]')

Page 67: Mojolicious. Веб в коробке!

Mojo::IOLoopTCP клиент-сервер

Page 68: Mojolicious. Веб в коробке!

my $loop = Mojo::IOLoop->new;

$loop->listen(port => 3000, cb => sub { my ($self, $id) = @_; $self->read_cb ($id => sub { ... });

$self->write_cb($id => sub { ... }););

my $id = $loop->connect(port => 3000, ...);

$loop->start; $loop->stop;

Page 69: Mojolicious. Веб в коробке!

Test::MojoФреймворк для тестирования

Page 70: Mojolicious. Веб в коробке!

my $t = Test::Mojo->new( app => 'App' );

$t->get_ok( '/hello' ) ->status_is( 200 ) ->header_is( 'X-Powered-By' => 'Mojolicious (Perl)' ) ->content_is( 'Привет Киев!' );

$t->post_ok( '/42' ) ->content_like(qr/Привет/, 'тест пройден!');

Page 71: Mojolicious. Веб в коробке!

Всё, что нужно – есть!Mojolicious – веб в коробке!

Page 72: Mojolicious. Веб в коробке!

Если нет, то есть на CPAN

или github.com :)

Page 73: Mojolicious. Веб в коробке!

Mojolicious на CPAN• Mojolicious

• Mojo::Server::FCGI

• AnyEvent::Mojo

• Apache::Mojo

Apache2::Mojo

• Catalyst::Engine::MojoSquatting::On::Mojo

• MojoX::Log::*

• MojoX::Renderer::*

• TT

• CTTP2, HTP

• XSLT

• Mail

Page 74: Mojolicious. Веб в коробке!

Модель, где же модель данных?А говорите всё есть :)

Page 75: Mojolicious. Веб в коробке!

Любая модель данных может быть использована

в MojoliciousDBI, DBIx::Class, Fey::ORM, CouchDB, MongoDB, ...

Page 76: Mojolicious. Веб в коробке!

Документация

• Пока мало документации, зато очень хороший фидбек :)

• Mojolicious::Lite и Mojolicious::Guides

• Mojolicious Handbook @kvorg

• Mojolicious FAQ @vti

Page 78: Mojolicious. Веб в коробке!

«Making hard things possible and everything fun!»

Девиз Mojolicious

Page 79: Mojolicious. Веб в коробке!

«Duct tape for the HTML5 Web»

Девиз Mojolicious #2

Page 80: Mojolicious. Веб в коробке!

«Viva la revolution!»

Девиз Mojolicious #3

Page 81: Mojolicious. Веб в коробке!

Mojolicious::Lite vs.

DancerСоревнование

Page 82: Mojolicious. Веб в коробке!

Mojoliciousvs.

CatalystЧто выбрать?

Page 83: Mojolicious. Веб в коробке!

«Особая разновидность современного программиста – программист, изучающий

фреймворки»Алекс Капранов

Page 84: Mojolicious. Веб в коробке!

Анатолий Шарифулин

«Каждый программист должен сделать 3 вещи: фреймворк, шаблонизатор и событийную машину»

Page 85: Mojolicious. Веб в коробке!

use Mojoliciousor die

Page 86: Mojolicious. Веб в коробке!

Viva la revolution!

Page 87: Mojolicious. Веб в коробке!

use Perlor die

Page 88: Mojolicious. Веб в коробке!

JFDI

Page 89: Mojolicious. Веб в коробке!

Посмотрите, какие у меня крутые часы :)

Page 90: Mojolicious. Веб в коробке!
Page 91: Mojolicious. Веб в коробке!

Спасибо за внимание!Анатолий Шарифулин

sharifulin

Page 92: Mojolicious. Веб в коробке!

any ‘/questions’ => sub { shift->render( answer => ‘sharifulin’ ); };