Psgi Plack Sfpm
Upcoming SlideShare
Loading in...5
×
 

Psgi Plack Sfpm

on

  • 2,978 views

 

Statistics

Views

Total Views
2,978
Views on SlideShare
2,962
Embed Views
16

Actions

Likes
2
Downloads
8
Comments
0

2 Embeds 16

http://www.techgig.com 12
http://www.slideshare.net 4

Accessibility

Categories

Upload Details

Uploaded via as Apple Keynote

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

Psgi Plack Sfpm Psgi Plack Sfpm Presentation Transcript

  • PSGI and Plack Tatsuhiko Miyagawa San Francsico.pm Nov. 24, 2009
  • Background
  • Web Frameworks
  • Maypole Mason Mojo Sledge Catalyst Spoon PageKit AxKit Egg Gantry Continuity Solstice Mojolicious Tripletail Konstrukt Reaction Jifty Cyclone3 WebGUI OpenInteract Squatting Dancer CGI::Application Nanoa Ark Angelos Noe Schenker Tatsumaki Web::Simple Apache2::REST SweetPea Hydrant
  • Most of them run on mod_perl and CGI
  • Some run on FastCGI
  • Some run standalone
  • Very few supports non-blocking
  • Because:
  • No common server environment layers
  • CGI.pm
  • Runs “fine” on: CGI, FastCGI, mod_perl (1 & 2) Standalone (with HTTP::Server::Simple)
  • CGI.pm = LCD It’s also Perl core
  • Catalyst The most popular framework as of today
  • Catalyst::Engine::* Server abstractions. Well supported Apache, FCGI and Standalone No CGI.pm
  • CGI.pm Jifty, CGI::Application, Spoon mod_perl centric Mason, Sledge, PageKit, WebGUI Adapters Catalyst, Maypole, Squatting
  • Problems: Duplicated efforts No fair performance evaluations
  • Question: Can we share those adapters?
  • Answer: HTTP::Engine
  • HTTP::Engine Lots of adapters (FCGI, Apache2, POE) Clean Request/Response API Written by Yappo, tokuhirom and others
  • Problems
  • Mo[ou]se everywhere Mouse is light but still overspec for some env.
  • Monolithic All implementations share HTTP::Engine roles and builders, which is sometimes hard to adapt and has less place for optimizations.
  • APIs everywhere Most frameworks have their request/response API Sometimes there are gaps. Annoying to write bridges and wrappers
  • Solution
  • Steal good stuff from Python/Ruby
  • WSGI (Python) Rack
  • WSGI (PEP-333) mod_wsgi, Tornado, Paste, GAE Django, CherryPy, Pylons
  • Rack Passenger, Thin, rack, Heroku Rails, Merb, Sinatra
  • WSGI/Rack Completely separate interface from the actual implementation
  • Approach Split HTTP::Engine into three parts
  • Interface Implementations Utilities
  • PSGI (interface) Plack::Server (implementations) Plack::* (utilities)
  • Who’s on board Benjamin Trott, Yuval Kogman, Stevan Little, Shawn M Moore, Mark Stosberg, Matt S Trout, Jesse Vincent, Chia-liang Kao, Dave Rolsky, John Beppu ...
  • Who’s on board Authors of: Movable Type, WebGUI, Catalyst, Jifty, Moose, DateTime, DBIx::Class, CGI::Application, Squatting, SVK, Dancer
  • PSGI Perl Web Server Gateway Interface
  • Interface
  • WARNING You DON’T need to care about these interface details as an app developer.
  • my $app = sub { my $env = shift; # ... return [ $status, $header, $body ]; };
  • PSGI application code reference $app = sub {...};
  • my $app = sub { my $env = shift; # ... return [ $status, $header, $body ]; };
  • environment hash $env: CGI-like env variables + psgi.input, psgi.errors etc.
  • my $app = sub { my $env = shift; # ... return [ $status, $header, $body ]; };
  • Response array ref with three elements status code, headers (array ref) and body (IO-like or array ref)
  • my $app = sub { my $env = shift; # ... return [ $status, $header, $body ]; };
  • $body IO::Handle-like getline() and close()
  • IO::Handle-like We really envy Python/Ruby for built-in iterators (Perl’s filehandle is also an object, but it really sucks)
  • WARNING You DON’T need to care about these interface details as an app developer. Becuase ...
  • Frameworks Write an adapter to return PSGI application code ref. (and forget about servers!)
  • Framework Adapters CGI::Application, Catalyst, Maypole Mason, Squatting, Mojo, HTTP::Engine etc.
  • Applications MT::App, WebGUI
  • use Foo; # is a Catalyst application Foo->setup_engine(‘PSGI’); my $app = sub { Foo->run };
  • Servers Set up $env, run the app and emits response out of $res
  • Plack namespace for servers and utilities
  • Plack::Server reference server implementations Standalone, FCGI, Apache2, CGI Standalone, Prefork, AnyEvent, Coro
  • Very fast 5000 QPS on standalone 15000 QPS with prefork :)
  • Utilities
  • Plackup Run PSGI app instantly from CLI (inspired by rackup)
  • DEMO
  • Middlewares
  • my $app = sub { my $env = shift; return [ $status, $header, $body ]; }; my $mw = sub { my $env = shift; # do something with $env my $res = $app->($env); # do something with $res; return $res; };
  • Middlewares Static, AccessLog, ConditionalGET ErrorDocument, StackTrace etc.
  • Plack::Middleware reusable and extensible Middleware framework Plack::Builder DSL in .psgi
  • my $app = sub { return [ $status, $header, $body ]; }; use Plack::Builder; builder { enable “Static”, root => “/htdocs”, path => qr!^/static/!; enable “Deflater”; # gzip/deflate $app; }
  • Plack::App::URLMap Multiplex multiple apps Integrated with Builder DSL
  • use CatApp; use CGIApp; my $c1 = sub { CatApp->run }; my $c2 = sub { CGIApp->run_psgi }; use Plack::Builder; builder { mount “/cat” => $c1; mount “/cgi-app” => builder { enable “StackTrace”; $c2; }; }
  • CGI::PSGI Easy migration from CGI.pm
  • Plack::Request like libapreq (Apache::Request) wrapper APIs for framework developers
  • use Plack::Request; my $app = sub { my $req = Plack::Request->new(shift); my $body = “Hello “ . $req->param(‘n’); my $res = $req->new_response(200); $res->content_type(‘text/plain’); $res->body($body); return $res->finalize; };
  • Plack::Test Unified interface to write tests with Mock HTTP and Live HTTP
  • use Plack::Test; use HTTP::Request::Common; my $app = sub { my $env = shift; return [ $status, $header, $body ]; }; test_psgi app => $app, client => sub { my $cb = shift; my $req = GET “http://localhost/foo”; my $res = $cb->($req); # test $res; };
  • use Plack::Test; use HTTP::Request::Common; $Plack::Test::Impl = “Server”; my $app = sub { my $env = shift; return [ $status, $header, $body ]; }; test_psgi app => $app, client => sub { my $cb = shift; my $req = GET “http://localhost/foo”; my $res = $cb->($req); # test $res; };
  • Streaming event loop / long-poll
  • # Pull streaming for blocking server use IO::Handle::Util qw(io_from_getline); my $app = sub { my $env = shift; my $io = io_from_getline sub { return $chunk; # undef when done }; return [ $status, $header, $io ]; };
  • # Push streaming for non-blocking server use AnyEvent; use JSON; my $app = sub { my $env = shift; return sub { my $respond = shift; my $w = $respond->([ 200, $headers ]); AnyEvent::Example->fetch(sub { $w->write(JSON::encode_json($_[0])); $w->close; }); }; };
  • Non-blocking servers AnyEvent, Coro, POE, Danga::Socket
  • Non-blocking framework Tatsumaki (Demo later)
  • Other Servers
  • nginx embedded perl http://github.com/yappo/nginx-psgi-patchs
  • mod_psgi http://github.com/spiritloose/mod_psgi
  • evpsgi http://github.com/sekimura/evpsgi
  • Perlbal plugin http://github.com/miyagawa/Perlbal-Plugin-PSGI
  • Cloud
  • WSGI (PEP-333) mod_wsgi, Tornado, Paste, GAE Django, CherryPy, Pylons
  • Rack Passenger, Thin, rack, Heroku Rails, Merb, Sinatra
  • What if GAE Perl comes with PSGI ...
  • Summary • PSGI is an interface, Plack is the code. • We have many (pretty fast) servers. • We have adapters and tools for most web frameworks. • Use it!
  • http://github.com/miyagawa/Plack http://plackperl.org/
  • Questions?