phpbb meets symfony2

77
phpBB4 meets Symfony2 Fabien Potencier

Upload: fabien-potencier

Post on 08-May-2015

8.958 views

Category:

Technology


6 download

TRANSCRIPT

Page 1: PhpBB meets Symfony2

phpBB4 meets Symfony2 Fabien Potencier

Page 2: PhpBB meets Symfony2

symfony 1 vs Symfony2

Page 3: PhpBB meets Symfony2

MVC

Page 4: PhpBB meets Symfony2

namespace Application\HelloBundle\Controller; use Symfony\Bundle\FrameworkBundle\Controller;

class HelloController extends Controller { public function indexAction($name) { // Get things from the Model

return $this->render( 'HelloBundle:Hello:index', array('name' => $name) ); } }

Page 5: PhpBB meets Symfony2

<?php $view->extend('HelloBundle::layout') ?>

Hello <?php echo $name ?>!

Page 6: PhpBB meets Symfony2

<html> <head> <title> <?php $view['slots']->output('title') ?> </title> </head> <body> <?php $view['slots']->output('_content') ?> </body> </html>

Page 7: PhpBB meets Symfony2

Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  In  vel  

Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  In  vel  nulla  arcu,  vitae  cursus  nunc.  Integer  semper  turpis  et  enim  por6tor  iaculis.  Nulla  facilisi.  Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  Mauris  vehicula  ves;bulum  dictum.  Aenean  non  velit  tortor.  Nullam  adipiscing  malesuada  aliquam.  Mauris  dignissim,  urna  quis  iaculis  tempus,  justo  libero  por6tor  est,  nec  eleifend  est  elit  vitae  ante.  Curabitur  interdum  luctus  metus,  in  pulvinar  lectus  rutrum  sit  amet.  Duis  gravida,  metus  in  dictum  eleifend,  dolor  risus  ;ncidunt  ligula,  non  volutpat  nulla  sapien  in  elit.  Nulla  rutrum  erat  id  neque  suscipit  eu  ultricies  odio  sollicitudin.  Aliquam  a  mi  vel  eros  placerat  hendrerit.  Phasellus  por6tor,  augue  sit  amet  vulputate  venena;s,  dui  leo  commodo  odio,  a  euismod  turpis  ligula  in  elit.    

_content

title

layout

slot

Page 8: PhpBB meets Symfony2

{% extends "HelloBundle::layout" %}

{% block content %} Hello {{ name }}! {% endblock %}

Page 9: PhpBB meets Symfony2

<html> <head> <title> {% block title %}{% endblock %} </title> </head> <body> {% block body %}{% endblock %} </body> </html>

Page 10: PhpBB meets Symfony2

Routing

Page 11: PhpBB meets Symfony2

/blog.php?section=symfony&article_id=18475

Page 12: PhpBB meets Symfony2

web/ index.php

Page 13: PhpBB meets Symfony2

/index.php/blog/2010/08/21/symfony2-meets-phpBB4

Page 14: PhpBB meets Symfony2

/blog/2010/08/21/symfony2-meets-phpBB4

Page 15: PhpBB meets Symfony2

/blog/:year/:month/:day/:slug

Page 16: PhpBB meets Symfony2

post: pattern: /blog/:year/:month/:day/:slug defaults: { _controller: BlogBundle:Post:show }

Page 17: PhpBB meets Symfony2

<routes> <route id="post" pattern="/blog/:year/:month/:day/:slug"> <default key="_controller"> BlogBundle:Post:show </default> </route> </routes>

Page 18: PhpBB meets Symfony2

use Symfony\Component\Routing\RouteCollection; use Symfony\Component\Routing\Route;

$collection = new RouteCollection();

$route = new Route( '/blog/:year/:month/:day/:slug', array('_controller' => 'BlogBundle:Post:show'));

$collection->addRoute('post', $route);

return $collection;

Page 19: PhpBB meets Symfony2

$router ->match('/blog/2010/08/21/sf2-meets-phpBB4')

$router ->generate('post', array('slug' => '...'))

Page 20: PhpBB meets Symfony2

post: pattern: /post/:slug defaults: { _controller: BlogBundle:Post:show }

Page 21: PhpBB meets Symfony2

$router ->generate('post', array('slug' => '...'))

Page 22: PhpBB meets Symfony2

Bundles

Page 23: PhpBB meets Symfony2

.../ SomeBundle/ Controller/ Entity/ Resources/ config/ views/ SomeBundle.php Tests/

Page 24: PhpBB meets Symfony2

public function registerBundleDirs() { return array( 'Application' => __DIR__.'/../src/Application', 'Bundle' => __DIR__.'/../src/Bundle', 'Symfony\Bundle' => __DIR__.'/../src/vendor/symfony/src/Symfony/Bundle', ); }

Page 25: PhpBB meets Symfony2

$this->render('SomeBundle:Hello:index', $params)

Page 26: PhpBB meets Symfony2

hello: pattern: /hello/:name defaults: { _controller: SomeBundle:... }

Page 27: PhpBB meets Symfony2

SomeBundle can be any of

Application\SomeBundle Bundle\SomeBundle Symfony\Bundle\SomeBundle

Page 28: PhpBB meets Symfony2

Environments

Page 29: PhpBB meets Symfony2

Developers Customer End Users

Development Environment

Staging Environment

Production Environment

Page 30: PhpBB meets Symfony2

cache cache cache

debug   debug   debug  

logs   logs   logs  

stats stats stats

Development Environment

Staging Environment

Production Environment

Page 31: PhpBB meets Symfony2

# config/config.yml doctrine.dbal: dbname: mydbname user: root password: %doctrine.dbal_password%

swift.mailer: transport: smtp host: localhost

Page 32: PhpBB meets Symfony2

# config/config_dev.yml imports: - { resource: config.yml }

zend.logger: priority: debug path: %kernel.root_dir%/logs/%kernel.environment%.log

doctrine.dbal: password: ~

swift.mailer: transport: gmail username: xxxxxxxx password: xxxxxxxx

Page 33: PhpBB meets Symfony2

# Doctrine Configuration doctrine.dbal: dbname: xxxxxxxx user: xxxxxxxx password: ~

# Swiftmailer Configuration swift.mailer: transport: smtp encryption: ssl auth_mode: login host: smtp.gmail.com username: xxxxxxxx password: xxxxxxxx

Page 34: PhpBB meets Symfony2

<!-- Doctrine Configuration --> <doctrine:dbal dbname="xxxxxxxx" user="xxxxxxxx" password="" /> <doctrine:orm />

<!-- Swiftmailer Configuration --> <swift:mailer transport="smtp" encryption="ssl" auth_mode="login" host="smtp.gmail.com" username="xxxxxxxx" password="xxxxxxxx" />

Page 35: PhpBB meets Symfony2

// Doctrine Configuration $container->loadFromExtension('doctrine', 'dbal', array( 'dbname' => 'xxxxxxxx', 'user' => 'xxxxxxxx', 'password' => '', )); $container->loadFromExtension('doctrine', 'orm');

// Swiftmailer Configuration $container->loadFromExtension('swift', 'mailer', array( 'transport' => "smtp", 'encryption' => "ssl", 'auth_mode' => "login", 'host' => "smtp.gmail.com", 'username' => "xxxxxxxx", 'password' => "xxxxxxxx", ));

Page 36: PhpBB meets Symfony2

Developer Tools

Page 37: PhpBB meets Symfony2

INFO: Matched route "blog_home" (parameters: array ( '_bundle' => 'BlogBundle', '_controller' => 'Post', '_action' => 'index', '_route' => 'blog_home',))

INFO: Using controller "Bundle\BlogBundle\Controller\PostController::indexAction"

INFO: SELECT s0_.id AS id0, s0_.title AS title1, s0_.html_body AS html_body2, s0_.excerpt AS excerpt3, s0_.published_at AS published_at4 FROM sf_weblog_post s0_ ORDER BY s0_.published_at DESC LIMIT 10 (array ())

Page 38: PhpBB meets Symfony2

INFO: Matched route "blog_post" (parameters: array ( '_bundle' => 'BlogBundle', '_controller' => 'Post', '_action' => 'show', '_format' => 'html', 'id' => '3456', '_route' => 'blog_post',))

INFO: Using controller "Bundle\BlogBundle\Controller\PostController::showAction »

INFO: SELECT s0_.id AS id0, s0_.title AS title1, s0_.html_body AS html_body2, s0_.excerpt AS excerpt3, s0_.published_at AS published_at4 FROM sf_weblog_post s0_ WHERE s0_.id = ? (array ( 0 => '3456',)) ERR: Post "3456" not found! (No result was found for query although at least one row was expected.) (uncaught Symfony\Components\RequestHandler\Exception\NotFoundHttpException exception)

INFO: Using controller "Symfony\Framework\WebBundle\Controller\ExceptionController::exceptionAction"

Page 39: PhpBB meets Symfony2

DEBUG: Notifying (until) event "core.request" to listener "(Symfony\Framework\WebBundle\Listener\RequestParser, resolve)" INFO: Matched route "blog_post" (parameters: array ( '_bundle' => 'BlogBundle', '_controller' => 'Post', '_action' => 'show', '_format' => 'html', 'id' => '3456', '_route' => 'blog_post',)) DEBUG: Notifying (until) event "core.load_controller" to listener "(Symfony\Framework\WebBundle\Listener\ControllerLoader, resolve)" INFO: Using controller "Bundle\BlogBundle\Controller\PostController::showAction" DEBUG: Listener "(Symfony\Framework\WebBundle\Listener\ControllerLoader, resolve)" processed the event "core.load_controller" INFO: Trying to get post "3456" from database INFO: SELECT s0_.id AS id0, s0_.title AS title1, s0_.html_body AS html_body2, s0_.excerpt AS excerpt3, s0_.published_at AS published_at4 FROM sf_weblog_post s0_ WHERE s0_.id = ? (array ( 0 => '3456',)) DEBUG: Notifying (until) event "core.exception" to listener "(Symfony\Framework\WebBundle\Listener\ExceptionHandler, handle)" ERR: Post "3456" not found! (No result was found for query although at least one row was expected.) (uncaught Symfony\Components\RequestHandler\Exception\NotFoundHttpException exception) DEBUG: Notifying (until) event "core.request" to listener "(Symfony\Framework\WebBundle\Listener\RequestParser, resolve)" DEBUG: Notifying (until) event "core.load_controller" to listener "(Symfony\Framework\WebBundle\Listener\ControllerLoader, resolve)" INFO: Using controller "Symfony\Framework\WebBundle\Controller\ExceptionController::exceptionAction" DEBUG: Listener "(Symfony\Framework\WebBundle\Listener\ControllerLoader, resolve)" processed the event "core.load_controller" DEBUG: Notifying (filter) event "core.response" to listener "(Symfony\Framework\WebBundle\Listener\ResponseFilter, filter)" DEBUG: Notifying (filter) event "core.response" to listener "(Symfony\Framework\WebBundle\Debug\DataCollector\DataCollectorManager, handle)" DEBUG: Notifying (filter) event "core.response" to listener "(Symfony\Framework\WebBundle\Debug\WebDebugToolbar, handle)" DEBUG: Listener "(Symfony\Framework\WebBundle\Listener\ExceptionHandler, handle)" processed the event "core.exception" DEBUG: Notifying (filter) event "core.response" to listener "(Symfony\Framework\WebBundle\Listener\ResponseFilter, filter)" DEBUG: Notifying (filter) event "core.response" to listener "(Symfony\Framework\WebBundle\Debug\DataCollector\DataCollectorManager, handle)" DEBUG: Notifying (filter) event "core.response" to listener "(Symfony\Framework\WebBundle\Debug\WebDebugToolbar, handle)"

Page 40: PhpBB meets Symfony2
Page 41: PhpBB meets Symfony2
Page 42: PhpBB meets Symfony2

Security

Page 43: PhpBB meets Symfony2

XSS / CSRF / SQL Injection

Page 44: PhpBB meets Symfony2

<doctrine:dbal dbname="sfweb" username="root" password="SuperSecretPasswordThatAnyoneCanSee" />

Page 45: PhpBB meets Symfony2

SetEnv SYMFONY__DOCTRINE__DBAL__PASSWORD "foobar"

in a .htaccess or httpd.conf file

%doctrine.dbal.password%

Page 46: PhpBB meets Symfony2

<doctrine:dbal dbname="sfweb" username="root" password="%doctrine.dbal.password%" />

Page 47: PhpBB meets Symfony2

Functional Tests

Page 48: PhpBB meets Symfony2

$client = $this->createClient();

$crawler = $client->request( 'GET', '/hello/Fabien');

$this->assertTrue($crawler->filter( 'html:contains("Hello Fabien")')->count());

Page 49: PhpBB meets Symfony2

$this->assertEquals( 10, $crawler->filter('div.hentry')->count());

$this->assertTrue( $client->getResponse()->isSuccessful());

Page 50: PhpBB meets Symfony2

$crawler = $client->request( 'GET', 'hello/Lucas' );

Page 51: PhpBB meets Symfony2

$link = $crawler->selectLink("Greet Lucas");

$client->click($link);

Page 52: PhpBB meets Symfony2

$form = $crawler->selectButton('submit');

$client->submit($form, array( 'name' => 'Lucas', 'country' => 'France', 'like_symfony' => true, 'photo' => '/path/to/lucas.jpg', ));

Page 53: PhpBB meets Symfony2

$harry = $this->createClient(); $sally = $this->createClient();

$harry->request('POST', '/say/sally/Hello'); $sally->request('GET', '/messages');

$this->assertEquals(201, $harry->getResponse()->getStatusCode());

$this->assertRegExp('/Hello/', $sally->getResponse()->getContent());

Page 54: PhpBB meets Symfony2

$harry = $this->createClient(); $sally = $this->createClient();

$harry->insulate(); $sally->insulate();

$harry->request('POST', '/say/sally/Hello'); $sally->request('GET', '/messages');

$this->assertEquals(201, $harry->getResponse()->getStatusCode()); $this->assertRegExp('/Hello/', $sally->getResponse()->getContent());

Page 55: PhpBB meets Symfony2

Caching

Page 56: PhpBB meets Symfony2

Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  In  vel  nulla  arcu,  vitae  cursus  nunc.  Integer  semper  turpis  et  enim  por6tor  iaculis.  Nulla  facilisi.  Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  Mauris  vehicula  ves;bulum  dictum.  Aenean  non  velit  tortor.  Nullam  adipiscing  malesuada  aliquam.  Mauris  dignissim,  urna  quis  iaculis  tempus,  justo  libero  por6tor  est,  nec  eleifend  est  elit  vitae  ante.  Curabitur  interdum  luctus  metus.  

Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  In  vel  nulla  arcu,  vitae  cursus  nunc.  Integer  semper  turpis  et  enim  por6tor  iaculis.  Nulla  facilisi.  Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  Mauris  vehicula  ves;bulum  dictum.  Aenean  non  velit  tortor.  Nullam  adipiscing  malesuada  aliquam.  Mauris  dignissim,  urna  quis  iaculis  tempus,  justo  libero  por6tor  est,  nec  eleifend  est  elit  vitae  ante.  Curabitur  interdum  luctus  metus,  in  pulvinar  lectus  rutrum  sit  amet.  Duis  gravida,  metus  in  dictum  eleifend,  dolor  risus  ;ncidunt  ligula,  non  volutpat  nulla  sapien  in  elit.  Nulla  rutrum  erat  id  neque  suscipit  eu  ultricies  odio  sollicitudin.  Aliquam  a  mi  vel  eros  placerat  hendrerit.  Phasellus  por6tor,  augue  sit  amet  vulputate  venena;s,  dui  leo  commodo  odio,  a  euismod  turpis  ligula  in  elit.    

cacheable for 10 seconds cacheable for 5 seconds

main controller

embedded controller

layout

Page 57: PhpBB meets Symfony2

<?php $view->extend('...:layout') ?>

<?php $view['slots']->start('sidebar') ?>

<?php echo $view['actions']->render('...:list') ?>

<?php $view['slots']->stop() ?>

cacheable for 10 seconds

cacheable for 5 seconds

Page 58: PhpBB meets Symfony2

$view['actions']->render('...:list', array( 'standalone' => true, ))

Page 59: PhpBB meets Symfony2

Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  In  vel  nulla  arcu,  vitae  cursus  nunc.  Integer  semper  turpis  et  enim  por6tor  iaculis.  Nulla  facilisi.  Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  Mauris  vehicula  ves;bulum  dictum.  Aenean  non  velit  tortor.  Nullam  adipiscing  malesuada  aliquam.  Mauris  dignissim,  urna  quis  iaculis  tempus,  justo  libero  por6tor  est,  nec  eleifend  est  elit  vitae  ante.  Curabitur  interdum  luctus  metus.  

Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  In  vel  nulla  arcu,  vitae  cursus  nunc.  Integer  semper  turpis  et  enim  por6tor  iaculis.  Nulla  facilisi.  Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  Mauris  vehicula  ves;bulum  dictum.  Aenean  non  velit  tortor.  Nullam  adipiscing  malesuada  aliquam.  Mauris  dignissim,  urna  quis  iaculis  tempus,  justo  libero  por6tor  est,  nec  eleifend  est  elit  vitae  ante.  Curabitur  interdum  luctus  metus,  in  pulvinar  lectus  rutrum  sit  amet.  Duis  gravida,  metus  in  dictum  eleifend,  dolor  risus  ;ncidunt  ligula,  non  volutpat  nulla  sapien  in  elit.  Nulla  rutrum  erat  id  neque  suscipit  eu  ultricies  odio  sollicitudin.  Aliquam  a  mi  vel  eros  placerat  hendrerit.  Phasellus  por6tor,  augue  sit  amet  vulputate  venena;s,  dui  leo  commodo  odio,  a  euismod  turpis  ligula  in  elit.    

Page 60: PhpBB meets Symfony2

Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  In  vel  nulla  arcu,  vitae  cursus  nunc.  Integer  semper  turpis  et  enim  por6tor  iaculis.  Nulla  facilisi.  Lorem  ipsum  dolor  sit  amet,  consectetur  adipiscing  elit.  Mauris  vehicula  ves;bulum  dictum.  Aenean  non  velit  tortor.  Nullam  adipiscing  malesuada  aliquam.  Mauris  dignissim,  urna  quis  iaculis  tempus,  justo  libero  por6tor  est,  nec  eleifend  est  elit  vitae  ante.  Curabitur  interdum  luctus  metus,  in  pulvinar  lectus  rutrum  sit  amet.  Duis  gravida,  metus  in  dictum  eleifend,  dolor  risus  ;ncidunt  ligula,  non  volutpat  nulla  sapien  in  elit.  Nulla  rutrum  erat  id  neque  suscipit  eu  ultricies  odio  sollicitudin.  Aliquam  a  mi  vel  eros  placerat  hendrerit.  Phasellus  por6tor,  augue  sit  amet  vulputate  venena;s,  dui  leo  commodo  odio,  a  euismod  turpis  ligula  in  elit.    

<esi:include src="..." />

Page 61: PhpBB meets Symfony2

ESI… or Edge Side Includes

Page 62: PhpBB meets Symfony2

Symf

ony2

Appli

catio

n

Reve

rse Pr

oxy

Clien

t Lorem  ipsum  dolor  sit  amet,    

Lorem  ipsum  dolor  

Lorem  ipsum  dolor  sit  amet,    

Lorem  ipsum  dolor  

1

2

3

4

Page 63: PhpBB meets Symfony2

Symfony2 app

Web Server

Requests

Response

Page 64: PhpBB meets Symfony2

Symfony2 app

Symfony2 HTTP proxy

Web Server

Requests

Response

Page 65: PhpBB meets Symfony2

Symfony2 app

Web Server

Reverse proxy

Requests

Response

Page 66: PhpBB meets Symfony2

HttpKernel: The framework construction kit

Page 67: PhpBB meets Symfony2

namespace Symfony\Component\HttpKernel;

interface HttpKernelInterface { const MASTER_REQUEST = 1; const SUB_REQUEST = 2;

public function handle( Request $request = null, $type = self::MASTER_REQUEST, $raw = false); }

Page 68: PhpBB meets Symfony2

Request

Response

core.controller

core.response

core.view

core.request

getController()

getArguments()

Page 69: PhpBB meets Symfony2

Request

Response

core.controller

core.response

core.view

core.request

getController()

getArguments()

Page 70: PhpBB meets Symfony2

Request

Response

core.controller

core.response

core.view

core.request

getController()

getArguments()

core.exception

Page 71: PhpBB meets Symfony2

HttpFoundation

HttpKernel

Framework

FrameworkBundle

Routing

Console

SwiftmailerBundle

TwigBundle

DependencyInjection

...

...

Components

Bundles

Event Dispatcher

Templating

DoctrineBundle

ZendBundle

Page 72: PhpBB meets Symfony2

MOD author

Page 73: PhpBB meets Symfony2

Theme author

Page 74: PhpBB meets Symfony2

Core Developer

Page 75: PhpBB meets Symfony2

End Users

Page 76: PhpBB meets Symfony2

Everybody

Page 77: PhpBB meets Symfony2

Questions?