http://traintosymfony.com1
Emanuele Gaspari
TRAIN
TO SYMFONY
Verona, 13•14 Aprile 2013
the frameworkshop
http://traintosymfony.com
@TrainToSymfony
Media partner:
Routing (2/3)
http://traintosymfony.com2
Emanuele Gaspari
about me
creatore di SymfonyBricks
Emanuele Gaspari
ultimo sito pubblicato (copiaincolla): www.ilovesanmartino.it
4 bundles
21 controllers
6 services
9 entities
5 repositories custom
4 estensioni twig
14 macros
10 bundles aggiuntivi
(FOSUserBundle, FOSJsRoutingBundle, KnpPaginatorBundle, CopiaincollaMetaTagsBundle, etc..)
co-sviluppatore di CopiaincollaMetaTagsBundle https://github.com/copiaincolla/MetaTagsBundle
https://symfonybricks.com
inmarelibero@gmail.com @inmarelibero
http://traintosymfony.com3
Emanuele Gaspari
Symfony: teoria e codice
Routing Templating
frameworkshop: il programma
overview
obiettivo della seconda parte:
il sistema di Routing in Symfony
http://traintosymfony.com4
Emanuele Gaspari
Routing
il Routing è il meccanismo di associazione tra url e controllers
http://traintosymfony.com5
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com6
Emanuele Gaspari
Controller
SymfonyBundleFrameworkBundleControllerController
●
riceve i parametri
●
esegue delle operazioni e restituisce una risposta
in Symfony un Controller è una classe PHP che estende la classe
task comuni: passaggio di variabili ai templates,
accesso a “servizi”, comunicazione con database, redirect
http://traintosymfony.com7
Emanuele Gaspari
●
funzione definita all'interno di un controller
●
la firma ha la sintassi public function ...Action()
nel Controller vengono definite le
actions (azioni)
Action
http://traintosymfony.com8
Emanuele Gaspari
actions: esempi
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class DefaultController extends Controller
{
public function homepageAction()
{
[...]
}
public function contattiAction()
{
[...]
}
public function chiSiamoAction()
{
[...]
}
}
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class DefaultController extends Controller
{
public function homepageAction()
{
[...]
}
public function contattiAction()
{
[...]
}
public function chiSiamoAction()
{
[...]
}
}
http://traintosymfony.com9
Emanuele Gaspari
scopo di un'azione
lo scopo di un'azione è di preparare i dati
che verranno mostrati nel template
le azioni non dovrebbero essere molto estese
se un'azione lo è, chiediti se la logica debba essere
ridistribuita in altri servizi, repository, entities
http://traintosymfony.com10
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com11
Emanuele Gaspari
una Route è un'associazione tra url e controller che specifico:
Route: tra url e Controller
●
in app/config/routing.yml
●
in un altro file yml
●
nel controller
http://traintosymfony.com12
Emanuele Gaspari
# app/config/routing.yml
homepage:
path: /
defaults: { _controller: TtsDemoBundle:Default:homepage }
# app/config/routing.yml
homepage:
path: /
defaults: { _controller: TtsDemoBundle:Default:homepage }
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class DefaultController extends Controller
{
public function homepageAction()
{
return $this->render(
'TtsDemoBundle:Default:homepage.html.twig'
);
}
}
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class DefaultController extends Controller
{
public function homepageAction()
{
return $this->render(
'TtsDemoBundle:Default:homepage.html.twig'
);
}
}
/
http://traintosymfony.com13
Emanuele Gaspari
# app/config/routing.yml
index_catalogo:
path: /catalogo
defaults: { _controller: TtsDemoBundle:Catalogo:index }
# app/config/routing.yml
index_catalogo:
path: /catalogo
defaults: { _controller: TtsDemoBundle:Catalogo:index }
# src/Tts/DemoBundle/Controller/CatalogoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class CatalogoController extends Controller
{
public function indexAction()
{
[...]
}
}
# src/Tts/DemoBundle/Controller/CatalogoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class CatalogoController extends Controller
{
public function indexAction()
{
[...]
}
}
/catalogo
http://traintosymfony.com14
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com15
Emanuele Gaspari
stabilisco che una parte del path è variabile
Routes {parametriche}
le parti variabili sono comprese tra { } e vengono passate
all'azione come argomenti
http://traintosymfony.com16
Emanuele Gaspari
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
namespace TtsDemoBundleController;
use SmfonyBundleFrameworkBundleControllerController;
class ProdottoController extends Controller
{
public function showAction($codice)
{
$em = $this->getDoctrine()->getManager();
$entity = $em->getRepository('TtsDemoBundle:Prodotto')->find($codice);
[...]
}
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
namespace TtsDemoBundleController;
use SmfonyBundleFrameworkBundleControllerController;
class ProdottoController extends Controller
{
public function showAction($codice)
{
$em = $this->getDoctrine()->getManager();
$entity = $em->getRepository('TtsDemoBundle:Prodotto')->find($codice);
[...]
}
}
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
/prodotto/{codice}
http://traintosymfony.com17
Emanuele Gaspari
# app/config/routing.yml
prodotto_show:
path: /prodotto/{categoria}/{codice}/{slug}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
# app/config/routing.yml
prodotto_show:
path: /prodotto/{categoria}/{codice}/{slug}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
/prodotto/{categoria}/{codice}/{slug}
http://traintosymfony.com18
Emanuele Gaspari
GET /prodotto/147?mobile_layout=trueGET /prodotto/147?mobile_layout=true
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
<?php
public function showAction($codice)
{
$request = $this->getRequest();
$mobileLayout = $request->get('mobile_layout');
// oppure, più estesamente
$mobileLayout = $request->query->get('mobile_layout', 'false');
[…]
}
<?php
public function showAction($codice)
{
$request = $this->getRequest();
$mobileLayout = $request->get('mobile_layout');
// oppure, più estesamente
$mobileLayout = $request->query->get('mobile_layout', 'false');
[…]
}
passaggio di parametri $_GET
http://traintosymfony.com19
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com20
Emanuele Gaspari
al posto di definire una Route per ogni (sintassi di) url in un file yml
posso usare l'annotazione @Route direttamente nel controller
http://traintosymfony.com21
Emanuele Gaspari
=
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class DefaultController extends Controller
{
/**
* @Route("/", name=”homepage”)
*/
public function homepageAction() {
[...]
}
}
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class DefaultController extends Controller
{
/**
* @Route("/", name=”homepage”)
*/
public function homepageAction() {
[...]
}
}
# app/config/routing.yml
homepage:
path: /
defaults: { _controller: TtsDemoBundle:Default:homepage }
http://traintosymfony.com22
Emanuele Gaspari
# app/config/routing.yml
index_catalogo:
path: /catalogo
defaults: { _controller: TtsDemoBundle:Catalogo:index }
# src/Tts/DemoBundle/Controller/CatalogoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class CatalogoController extends Controller
{
/**
* @Route("/catalogo", name=”index_catalogo”)
*/
public function indexAction() {
[...]
}
}
# src/Tts/DemoBundle/Controller/CatalogoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class CatalogoController extends Controller
{
/**
* @Route("/catalogo", name=”index_catalogo”)
*/
public function indexAction() {
[...]
}
}
=
http://traintosymfony.com23
Emanuele Gaspari
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{codice}", name=”prodotto_show”)
*/
public function showAction($codice) {
[...]
}
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{codice}", name=”prodotto_show”)
*/
public function showAction($codice) {
[...]
}
}
=
http://traintosymfony.com24
Emanuele Gaspari
# app/config/routing.yml
prodotto_show:
path: /prodotto/{categoria}/{codice}/{slug}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($categoria, $codice, $slug) {
[...]
}
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($categoria, $codice, $slug) {
[...]
}
}
=
http://traintosymfony.com25
Emanuele Gaspari
definisco in app/config/routing.yml quali controller caricare
http://traintosymfony.com26
Emanuele Gaspari
type: annotation
# app/config/config.yml
# TtsDemoBundle Default controller
default:
resource: “@TtsDemoBundle/Controller/DefaultController.php”
type: annotation
# TtsDemoBundle Catalogo controller
catalogo:
resource: “@TtsDemoBundle/Controller/CatalogoController.php”
type: annotation
# TtsDemoBundle Prodotto controller
prodotto:
resource: “@TtsDemoBundle/Controller/ProdottoController.php”
type: annotation
# app/config/config.yml
# TtsDemoBundle Default controller
default:
resource: “@TtsDemoBundle/Controller/DefaultController.php”
type: annotation
# TtsDemoBundle Catalogo controller
catalogo:
resource: “@TtsDemoBundle/Controller/CatalogoController.php”
type: annotation
# TtsDemoBundle Prodotto controller
prodotto:
resource: “@TtsDemoBundle/Controller/ProdottoController.php”
type: annotation
http://traintosymfony.com27
Emanuele Gaspari
type: annotation (2)
# app/config/config.yml
# TtsDemoBundle
tts_demo:
resource: “@TtsDemoBundle/Controller/”
type: annotation
# app/config/config.yml
# TtsDemoBundle
tts_demo:
resource: “@TtsDemoBundle/Controller/”
type: annotation
o, semplicemente, specifico la cartella che li contiene tutti
http://traintosymfony.com28
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com29
Emanuele Gaspari
best practice
far corrispondere ad ogni url una sola route
http://traintosymfony.com30
Emanuele Gaspari
GET /prodotto/EG-124 => prodotto_show
GET /prodotto/index => prodotto_show, prodotto_index
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
prodotto_index:
path: /prodotto/index
defaults: { _controller: TtsDemoBundle:Prodotto:index }
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
defaults: { _controller: TtsDemoBundle:Prodotto:show }
prodotto_index:
path: /prodotto/index
defaults: { _controller: TtsDemoBundle:Prodotto:index }
collisione di urls
http://traintosymfony.com31
Emanuele Gaspari
sfrutto l'ordine con cui vengono definite le Routes
il controller si ferma alla prima Route abbinata all'url
è sufficiente definire prima la Route che non contiene parametri
GET /prodotto/index
GET /prodotto/EG-124
# app/config/routing.yml
prodotto_index:
path: /prodotto/index
prodotto_show:
path: /prodotto/{codice}
# app/config/routing.yml
prodotto_index:
path: /prodotto/index
prodotto_show:
path: /prodotto/{codice}
soluzione 1, ordine delle Routes
http://traintosymfony.com32
Emanuele Gaspari
rimane ancora il problema della collisione di urls verso più di una Route
basarsi sull'ordine con cui vengono esaminate le Routes non è sufficiente:
dopo un anno che il sito è in produzione, mi ricordo che la
posizione di quella specifica Route è vitale?
anche usando l'annotazione @Route, posso non volere che
all'interno di un Controller una funzione venga spostata
in alto solo perché la Route venga esaminata prima
l'ordine non basta
http://traintosymfony.com33
Emanuele Gaspari
sfrutto il parametro requirements
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
requirements:
codice: [A-Z]{2}-[0-9]+
prodotto_index:
path: /prodotto/index
# app/config/routing.yml
prodotto_show:
path: /prodotto/{codice}
requirements:
codice: [A-Z]{2}-[0-9]+
prodotto_index:
path: /prodotto/index
GET /prodotto/index
GET /prodotto/EG-124
non c'è più collisione tra Routes
non mi affido più all'ordine di caricamento
soluzione 2, parametro requirements
pongo dei vincoli sul formato di un parametro di una Route
http://traintosymfony.com34
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com35
Emanuele Gaspari
Symfony associa il nome logico ad una
specifica classe e metodo (Controller e Action)
bundle:controller:action
nome logico di un Controller
sintassi per riferirsi ad un'azione da qualunque punto dell'applicazione
Controller Naming Pattern
http://traintosymfony.com36
Emanuele Gaspari
TtsDemoBundle:Default:homepage
Bundle Controller Metodo
TtsDemoBundleTtsDemoBundle DefaultControllerDefaultController homepageAction()homepageAction()
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class DefaultController extends Controller
{
public function homepageAction()
{
[…]
}
}
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
namespace TtsDemoBundleController;
use SymfonyBundleFrameworkBundleControllerController;
class DefaultController extends Controller
{
public function homepageAction()
{
[…]
}
}
Controller Naming Pattern
http://traintosymfony.com37
Emanuele Gaspari
# template twig
{{ render(controller(“TtsDemoBundle:Blog:latestPosts”, {“max”: 5})) }}
# template twig
{{ render(controller(“TtsDemoBundle:Blog:latestPosts”, {“max”: 5})) }}
esempio
http://traintosymfony.com38
Emanuele Gaspari
$ php app/console router:debug$ php app/console router:debug
$ php app/console router:match /prodotto/EG-124$ php app/console router:match /prodotto/EG-124
tips
stampare a console l'elenco di tutte le Routes caricate
verificare se un path è associato da Symfony ad una Route
http://traintosymfony.com39
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com40
Emanuele Gaspari
oggetto Request
SymfonyComponentHttpFoundationRequest
oggetto che ho a disposizione all'interno di ogni azione
per gestire tutti i parametri della richiesta
Symfony utilizza un oggetto Request per modellare una richiesta HTTP
http://traintosymfony.com41
Emanuele Gaspari
accedere ad un oggetto Request
<?php
public function homepageAction()
{
$request = $this->getRequest();
}
<?php
public function homepageAction()
{
$request = $this->getRequest();
}
use SymfonyComponentHttpFoundationRequest;
$request = Request::createFromGlobals();
use SymfonyComponentHttpFoundationRequest;
$request = Request::createFromGlobals();
accedere a Request in una Action:
accedere a Request da qualunque punto dell'applicazione (in PHP):
$this->getRequest() => 0.04 Kb
Request::createFromGlobals() => 7.07 Kb
{{ app.request }}{{ app.request }}
accedere a Request da twig:
http://traintosymfony.com42
Emanuele Gaspari
panoramica
$_GET
$request->query
$_POST
$request->request
$_COOKIE
$request->cookies
$_FILE
$request->files
$_SERVER
$request->server
http://api.symfony.com/master/Symfony/Component/HttpFoundation/Request.html
$request
->getPathInfo() ->getMethod() ->getLanguages()
->getRequestUri() ->getClientIp() ->getPreferredLanguage()
->getScriptName() ->getSession() ->isXmlHttpRequest()
http://traintosymfony.com43
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com44
Emanuele Gaspari
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
[...]
}
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
[...]
}
url con parametri
200 GET /prodotto/nuovi/EG-124/eg-124-new-hammer
non importa l'ordine
possono non essere specificati tutti
l'ordine è importante, per associare i parametri dell'url
404 GET /prodotto/nuovi/EG-124
404 GET /prodotto/nuovi/EG-124/
http://traintosymfony.com45
Emanuele Gaspari
defaults (1)
200 GET /prodotto/nuovi/EG-124/eg-124-new-hammer
200 GET /prodotto/nuovi/EG-124
404 GET /prodotto/nuovi/EG-124/
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”,
defaults={“slug”: “-”})
*/
public function showAction($codice, $categoria, $slug) { [...] }
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”,
defaults={“slug”: “-”})
*/
public function showAction($codice, $categoria) { [...] }
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $categoria, $slug = “-”) { [...] }
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”,
defaults={“slug”: “-”})
*/
public function showAction($codice, $categoria, $slug) { [...] }
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”,
defaults={“slug”: “-”})
*/
public function showAction($codice, $categoria) { [...] }
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $categoria, $slug = “-”) { [...] }
http://traintosymfony.com46
Emanuele Gaspari
accesso ai parametri
200 GET /prodotto/nuovi/EG-124/eg-124-new-hammer?color=red
200 GET /prodotto/nuovi/EG-124?color=red
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug = “-”, $categoria)
{
$request = $this->getRequest();
// nell'url
$codice;
$codice = $request->get(“codice”);
// in $_GET
$color = $request->get(“color”);
$color = $request->query->get(“color”);
[...]
}
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug = “-”, $categoria)
{
$request = $this->getRequest();
// nell'url
$codice;
$codice = $request->get(“codice”);
// in $_GET
$color = $request->get(“color”);
$color = $request->query->get(“color”);
[...]
}
http://traintosymfony.com47
Emanuele Gaspari
?get= o /{param}
●
parametro essenziale?
●
eleganza degli url
●
cambio successivo degli url
●
indicizzazione dei motori di ricerca
●
multilingua
quando passare un parametro come
?get=
e quando come
/{param}
http://traintosymfony.com48
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com49
Emanuele Gaspari
Response
ogni Action restituisce sempre un oggetto Response
real life: molte volte la Action che implementerai restituirà
semplicemente un array di variabili, utilizzabili
in un template che viene scelto più o meno “automaticamente”
http://traintosymfony.com50
Emanuele Gaspari
return array
la situazione più semplice è quella in cui utilizzo
l'annotation @Template e la mia Action restituisce
semplicemente un array
http://traintosymfony.com51
Emanuele Gaspari
return array
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
use SensioBundleFrameworkExtraBundleConfigurationTemplate;
class ProdottoController extends Controller
{
/**
* @Route(“/prodotto/{categoria}/{codice}/{slug}”, name=”prodotto_show”)
* @Template()
*/
public function showAction($codice, $slug, $categoria)
{
$entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy(
array(“codice” => $codice)
);
return array('entity' => $entity);
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyBundleFrameworkBundleControllerController;
use SensioBundleFrameworkExtraBundleConfigurationRoute;
use SensioBundleFrameworkExtraBundleConfigurationTemplate;
class ProdottoController extends Controller
{
/**
* @Route(“/prodotto/{categoria}/{codice}/{slug}”, name=”prodotto_show”)
* @Template()
*/
public function showAction($codice, $slug, $categoria)
{
$entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy(
array(“codice” => $codice)
);
return array('entity' => $entity);
}
http://traintosymfony.com52
Emanuele Gaspari
render()
posso fare in modo che l'azione restituisca un template TWIG compilato,
ad esempio perché è diverso in base alla logica interna dell'azione
utlizzo la funzione $this->render() specificando il template
http://traintosymfony.com53
Emanuele Gaspari
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
$entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy(
array(“codice” => $codice)
);
return $this->render('TtsDemoBundle:Prodotto:show_offer.html.twig', array(
'entity' => $entity
));
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
$entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy(
array(“codice” => $codice)
);
return $this->render('TtsDemoBundle:Prodotto:show_offer.html.twig', array(
'entity' => $entity
));
}
$this->render()
http://traintosymfony.com54
Emanuele Gaspari
costruire una Response
è possibile anche costruire un oggetto Response
utile nel caso in cui abbia necessità di costruire la risposta
in più passaggi a seconda di variabili
o di effettuare delle operazioni successivamente
http://traintosymfony.com55
Emanuele Gaspari
costruire una Response
utilizzo la funzione $this->renderView() per memorizzare
un contenuto HTML in una variabile
creo un oggetto Response con quella variabile come primo
argomentoimpostando
http://traintosymfony.com56
Emanuele Gaspari
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyComponentHttpFoundationResponse;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
$entity = [...]
$content = $this->renderView('TtsDemoBundle:Prodotto:show.html.twig', array(
'entity' => $entity
));
[...]
return new Response($content);
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyComponentHttpFoundationResponse;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
$entity = [...]
$content = $this->renderView('TtsDemoBundle:Prodotto:show.html.twig', array(
'entity' => $entity
));
[...]
return new Response($content);
}
http://traintosymfony.com57
Emanuele Gaspari
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyComponentHttpFoundationResponse;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
$entity = [...]
$response = new Response($entity->getCodice(), 200, array(
'content-type' => 'text/html'
));
$response->prepare($this->getRequest());
$response->send();
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyComponentHttpFoundationResponse;
class ProdottoController extends Controller
{
/**
* @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”)
*/
public function showAction($codice, $slug, $categoria)
{
$entity = [...]
$response = new Response($entity->getCodice(), 200, array(
'content-type' => 'text/html'
));
$response->prepare($this->getRequest());
$response->send();
}
http://traintosymfony.com58
Emanuele Gaspari
json
anche restituire una risposta in formato json è semplice
http://traintosymfony.com59
Emanuele Gaspari
json Response
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyComponentHttpFoundationResponse;
use SymfonyComponentHttpFoundationJsonResponse;
public function jsonAction($codice, $slug, $categoria)
{
$entity = [...]
$jsonResponse = array(“codice” => $entity->getCodice(), [...]);
// crea una risposta JSON
$response = new Response(json_encode($jsonResponse));
$response->headers->set('Content-Type', 'application/json');
return $response;
// crea una risposta JSON utilizzando la classe JsonResponse (Symfony >= 2.1)
$response = new JsonResponse();
$response->setData($jsonResponse);
return $response;
}
# src/Tts/DemoBundle/Controller/ProdottoController.php
<?php
use SymfonyComponentHttpFoundationResponse;
use SymfonyComponentHttpFoundationJsonResponse;
public function jsonAction($codice, $slug, $categoria)
{
$entity = [...]
$jsonResponse = array(“codice” => $entity->getCodice(), [...]);
// crea una risposta JSON
$response = new Response(json_encode($jsonResponse));
$response->headers->set('Content-Type', 'application/json');
return $response;
// crea una risposta JSON utilizzando la classe JsonResponse (Symfony >= 2.1)
$response = new JsonResponse();
$response->setData($jsonResponse);
return $response;
}
http://traintosymfony.com60
Emanuele Gaspari
riassunto
●
un array
●
$this->render()
●
$this->renderView()
●
un oggetto Response
●
un oggetto JsonResponse
abbiamo visto che un'azione può utilizzare:
...e può fare molto altro!
http://traintosymfony.com61
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com62
Emanuele Gaspari
redirect
il redirect è un messaggio al browser
cambia l'url perché è effettivamente una nuova richiesta
in caso di:
●
redirect temporaneo (302, default) o permanente (301)
●
invio corretto di un form: redirezione ad una pagina di conferma
●
se il sito è multilingua, si può effettuare un redirect dopo aver scelto la lingua
in base al browser
http://traintosymfony.com63
Emanuele Gaspari
redirect temporaneo
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
class DefaultController extends Controller
{
/**
* @Route("/", name=”homepage”)
*/
public function homepageAction()
{
return $this->redirect($this->generateUrl('homepage_natale'));
}
}
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
class DefaultController extends Controller
{
/**
* @Route("/", name=”homepage”)
*/
public function homepageAction()
{
return $this->redirect($this->generateUrl('homepage_natale'));
}
}
redirect temporaneo ad un altro url
http://traintosymfony.com64
Emanuele Gaspari
RedirectResponse
c'è un oggetto dedicato (che sorpresa!) che la Action può
restituire in caso di redirect: RedirectResponse
http://traintosymfony.com65
Emanuele Gaspari
RedirectResponse
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
use SymfonyComponentHttpFoundationRedirectResponse
class DefaultController extends Controller
{
/**
* @Route(“/”, name=”homepage”)
*/
public function homepageAction()
{
$respose = new RedirectResponse($this->generateUrl('homepage_natale'));
[..]
return $response;
}
}
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
use SymfonyComponentHttpFoundationRedirectResponse
class DefaultController extends Controller
{
/**
* @Route(“/”, name=”homepage”)
*/
public function homepageAction()
{
$respose = new RedirectResponse($this->generateUrl('homepage_natale'));
[..]
return $response;
}
}
http://traintosymfony.com66
Emanuele Gaspari
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
class DefaultController extends Controller
{
/**
* @Route("/chisiamo", name=”chisiamo”)
*/
public function chisiamoAction()
{
return $this->redirect($this->generateUrl('homepage_contatti'), 301);
}
}
# src/Tts/DemoBundle/Controller/DefaultController.php
<?php
class DefaultController extends Controller
{
/**
* @Route("/chisiamo", name=”chisiamo”)
*/
public function chisiamoAction()
{
return $this->redirect($this->generateUrl('homepage_contatti'), 301);
}
}
redirect permanente
redirect permanente con codice di stato HTTP 301
http://traintosymfony.com67
Emanuele Gaspari
Routes
Controller e Action
specificare una Route
Routes parametriche
annotation @Route
collisione di urls
Controller Naming Pattern
Request
oggetto Request
i parametri
Response
oggetto Response
redirect
parametri per il template
ROUTING
http://traintosymfony.com68
Emanuele Gaspari
l'azione può passare delle variabili al template restituendo un array
public function showAction($codice)
{
[...]
return array(
'entity' => $entity,
'show_extended_version' => true
);
}
public function showAction($codice)
{
[...]
return array(
'entity' => $entity,
'show_extended_version' => true
);
}
utilizzabili nel template twig
{% if show_extended_version %}
[...]
{% else %}
<a href=”...”>
{{ entity.codice }}
</a>
{% endif %}
{% if show_extended_version %}
[...]
{% else %}
<a href=”...”>
{{ entity.codice }}
</a>
{% endif %}
TRAIN
TO SYMFONY
Verona, 13•14 Aprile 2013
the frameworkshop
http://traintosymfony.com
@TrainToSymfony
Media partner:©Copyright Emanuele Gaspari Castelletti

More Related Content

PDF
Symfony (1/3) | Train to Symfony
PDF
Templating (3/3) | Train to Symfony
PDF
(My) Best Practices in Symfony
PDF
GAE python GDG Milano L04
PDF
Introduzione ai componenti in Angular 4
PDF
Introduzione ad angular 7/8
PDF
Acadevmy - Angular Overview
PDF
Come portare il profiler di symfony2 in drupal8
Symfony (1/3) | Train to Symfony
Templating (3/3) | Train to Symfony
(My) Best Practices in Symfony
GAE python GDG Milano L04
Introduzione ai componenti in Angular 4
Introduzione ad angular 7/8
Acadevmy - Angular Overview
Come portare il profiler di symfony2 in drupal8

Similar to Routing (2/3) | Train to Symfony (20)

PDF
TYPO3 Versione 10.2 - Le novita
PPT
eZ publish - Extension
PDF
TYPO3 CMS 8.2 e TYPO3 CMS 8.3 - Le novità
PDF
Mageploy presentato al Mage::day() 2013
PDF
Gae python gdg milano L03
PDF
introduzione a symfony 2
PDF
Enterprise Applications - Angular Day 2018
PPT
Primo Incontro Con Scala
ODP
Django: utilizzo avanzato e nuove funzionalità
PDF
Qt Lezione3: un visualizzatore di immagini
PPT
A static Analyzer for Finding Dynamic Programming Errors
PDF
Sviluppare un plugin WordPress da zero - WordCamp Bologna 2018
PDF
PHP Template Engine (introduzione)
ODP
Sviluppare estensioni per google chrome
PPT
Aumentiamo la sicurezza in TYPO3
PDF
Topog presentation
PDF
TYPO3 CMS 9.1 - Le novità
ODP
Matteo baccan raspberry pi - linox 2015 - corso parte 2
ODP
Web Performance Optimization
PDF
Openmoko
TYPO3 Versione 10.2 - Le novita
eZ publish - Extension
TYPO3 CMS 8.2 e TYPO3 CMS 8.3 - Le novità
Mageploy presentato al Mage::day() 2013
Gae python gdg milano L03
introduzione a symfony 2
Enterprise Applications - Angular Day 2018
Primo Incontro Con Scala
Django: utilizzo avanzato e nuove funzionalità
Qt Lezione3: un visualizzatore di immagini
A static Analyzer for Finding Dynamic Programming Errors
Sviluppare un plugin WordPress da zero - WordCamp Bologna 2018
PHP Template Engine (introduzione)
Sviluppare estensioni per google chrome
Aumentiamo la sicurezza in TYPO3
Topog presentation
TYPO3 CMS 9.1 - Le novità
Matteo baccan raspberry pi - linox 2015 - corso parte 2
Web Performance Optimization
Openmoko
Ad

Routing (2/3) | Train to Symfony

  • 1. http://traintosymfony.com1 Emanuele Gaspari TRAIN TO SYMFONY Verona, 13•14 Aprile 2013 the frameworkshop http://traintosymfony.com @TrainToSymfony Media partner: Routing (2/3)
  • 2. http://traintosymfony.com2 Emanuele Gaspari about me creatore di SymfonyBricks Emanuele Gaspari ultimo sito pubblicato (copiaincolla): www.ilovesanmartino.it 4 bundles 21 controllers 6 services 9 entities 5 repositories custom 4 estensioni twig 14 macros 10 bundles aggiuntivi (FOSUserBundle, FOSJsRoutingBundle, KnpPaginatorBundle, CopiaincollaMetaTagsBundle, etc..) co-sviluppatore di CopiaincollaMetaTagsBundle https://github.com/copiaincolla/MetaTagsBundle https://symfonybricks.com inmarelibero@gmail.com @inmarelibero
  • 3. http://traintosymfony.com3 Emanuele Gaspari Symfony: teoria e codice Routing Templating frameworkshop: il programma overview obiettivo della seconda parte: il sistema di Routing in Symfony
  • 4. http://traintosymfony.com4 Emanuele Gaspari Routing il Routing è il meccanismo di associazione tra url e controllers
  • 5. http://traintosymfony.com5 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 6. http://traintosymfony.com6 Emanuele Gaspari Controller SymfonyBundleFrameworkBundleControllerController ● riceve i parametri ● esegue delle operazioni e restituisce una risposta in Symfony un Controller è una classe PHP che estende la classe task comuni: passaggio di variabili ai templates, accesso a “servizi”, comunicazione con database, redirect
  • 7. http://traintosymfony.com7 Emanuele Gaspari ● funzione definita all'interno di un controller ● la firma ha la sintassi public function ...Action() nel Controller vengono definite le actions (azioni) Action
  • 8. http://traintosymfony.com8 Emanuele Gaspari actions: esempi # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class DefaultController extends Controller { public function homepageAction() { [...] } public function contattiAction() { [...] } public function chiSiamoAction() { [...] } } # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class DefaultController extends Controller { public function homepageAction() { [...] } public function contattiAction() { [...] } public function chiSiamoAction() { [...] } }
  • 9. http://traintosymfony.com9 Emanuele Gaspari scopo di un'azione lo scopo di un'azione è di preparare i dati che verranno mostrati nel template le azioni non dovrebbero essere molto estese se un'azione lo è, chiediti se la logica debba essere ridistribuita in altri servizi, repository, entities
  • 10. http://traintosymfony.com10 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 11. http://traintosymfony.com11 Emanuele Gaspari una Route è un'associazione tra url e controller che specifico: Route: tra url e Controller ● in app/config/routing.yml ● in un altro file yml ● nel controller
  • 12. http://traintosymfony.com12 Emanuele Gaspari # app/config/routing.yml homepage: path: / defaults: { _controller: TtsDemoBundle:Default:homepage } # app/config/routing.yml homepage: path: / defaults: { _controller: TtsDemoBundle:Default:homepage } # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class DefaultController extends Controller { public function homepageAction() { return $this->render( 'TtsDemoBundle:Default:homepage.html.twig' ); } } # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class DefaultController extends Controller { public function homepageAction() { return $this->render( 'TtsDemoBundle:Default:homepage.html.twig' ); } } /
  • 13. http://traintosymfony.com13 Emanuele Gaspari # app/config/routing.yml index_catalogo: path: /catalogo defaults: { _controller: TtsDemoBundle:Catalogo:index } # app/config/routing.yml index_catalogo: path: /catalogo defaults: { _controller: TtsDemoBundle:Catalogo:index } # src/Tts/DemoBundle/Controller/CatalogoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class CatalogoController extends Controller { public function indexAction() { [...] } } # src/Tts/DemoBundle/Controller/CatalogoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class CatalogoController extends Controller { public function indexAction() { [...] } } /catalogo
  • 14. http://traintosymfony.com14 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 15. http://traintosymfony.com15 Emanuele Gaspari stabilisco che una parte del path è variabile Routes {parametriche} le parti variabili sono comprese tra { } e vengono passate all'azione come argomenti
  • 16. http://traintosymfony.com16 Emanuele Gaspari # src/Tts/DemoBundle/Controller/ProdottoController.php <?php namespace TtsDemoBundleController; use SmfonyBundleFrameworkBundleControllerController; class ProdottoController extends Controller { public function showAction($codice) { $em = $this->getDoctrine()->getManager(); $entity = $em->getRepository('TtsDemoBundle:Prodotto')->find($codice); [...] } } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php namespace TtsDemoBundleController; use SmfonyBundleFrameworkBundleControllerController; class ProdottoController extends Controller { public function showAction($codice) { $em = $this->getDoctrine()->getManager(); $entity = $em->getRepository('TtsDemoBundle:Prodotto')->find($codice); [...] } } # app/config/routing.yml prodotto_show: path: /prodotto/{codice} defaults: { _controller: TtsDemoBundle:Prodotto:show } # app/config/routing.yml prodotto_show: path: /prodotto/{codice} defaults: { _controller: TtsDemoBundle:Prodotto:show } /prodotto/{codice}
  • 17. http://traintosymfony.com17 Emanuele Gaspari # app/config/routing.yml prodotto_show: path: /prodotto/{categoria}/{codice}/{slug} defaults: { _controller: TtsDemoBundle:Prodotto:show } # app/config/routing.yml prodotto_show: path: /prodotto/{categoria}/{codice}/{slug} defaults: { _controller: TtsDemoBundle:Prodotto:show } /prodotto/{categoria}/{codice}/{slug}
  • 18. http://traintosymfony.com18 Emanuele Gaspari GET /prodotto/147?mobile_layout=trueGET /prodotto/147?mobile_layout=true # app/config/routing.yml prodotto_show: path: /prodotto/{codice} defaults: { _controller: TtsDemoBundle:Prodotto:show } # app/config/routing.yml prodotto_show: path: /prodotto/{codice} defaults: { _controller: TtsDemoBundle:Prodotto:show } <?php public function showAction($codice) { $request = $this->getRequest(); $mobileLayout = $request->get('mobile_layout'); // oppure, più estesamente $mobileLayout = $request->query->get('mobile_layout', 'false'); […] } <?php public function showAction($codice) { $request = $this->getRequest(); $mobileLayout = $request->get('mobile_layout'); // oppure, più estesamente $mobileLayout = $request->query->get('mobile_layout', 'false'); […] } passaggio di parametri $_GET
  • 19. http://traintosymfony.com19 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 20. http://traintosymfony.com20 Emanuele Gaspari al posto di definire una Route per ogni (sintassi di) url in un file yml posso usare l'annotazione @Route direttamente nel controller
  • 21. http://traintosymfony.com21 Emanuele Gaspari = # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class DefaultController extends Controller { /** * @Route("/", name=”homepage”) */ public function homepageAction() { [...] } } # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class DefaultController extends Controller { /** * @Route("/", name=”homepage”) */ public function homepageAction() { [...] } } # app/config/routing.yml homepage: path: / defaults: { _controller: TtsDemoBundle:Default:homepage }
  • 22. http://traintosymfony.com22 Emanuele Gaspari # app/config/routing.yml index_catalogo: path: /catalogo defaults: { _controller: TtsDemoBundle:Catalogo:index } # src/Tts/DemoBundle/Controller/CatalogoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class CatalogoController extends Controller { /** * @Route("/catalogo", name=”index_catalogo”) */ public function indexAction() { [...] } } # src/Tts/DemoBundle/Controller/CatalogoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class CatalogoController extends Controller { /** * @Route("/catalogo", name=”index_catalogo”) */ public function indexAction() { [...] } } =
  • 23. http://traintosymfony.com23 Emanuele Gaspari # app/config/routing.yml prodotto_show: path: /prodotto/{codice} defaults: { _controller: TtsDemoBundle:Prodotto:show } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class ProdottoController extends Controller { /** * @Route("/prodotto/{codice}", name=”prodotto_show”) */ public function showAction($codice) { [...] } } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class ProdottoController extends Controller { /** * @Route("/prodotto/{codice}", name=”prodotto_show”) */ public function showAction($codice) { [...] } } =
  • 24. http://traintosymfony.com24 Emanuele Gaspari # app/config/routing.yml prodotto_show: path: /prodotto/{categoria}/{codice}/{slug} defaults: { _controller: TtsDemoBundle:Prodotto:show } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($categoria, $codice, $slug) { [...] } } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($categoria, $codice, $slug) { [...] } } =
  • 25. http://traintosymfony.com25 Emanuele Gaspari definisco in app/config/routing.yml quali controller caricare
  • 26. http://traintosymfony.com26 Emanuele Gaspari type: annotation # app/config/config.yml # TtsDemoBundle Default controller default: resource: “@TtsDemoBundle/Controller/DefaultController.php” type: annotation # TtsDemoBundle Catalogo controller catalogo: resource: “@TtsDemoBundle/Controller/CatalogoController.php” type: annotation # TtsDemoBundle Prodotto controller prodotto: resource: “@TtsDemoBundle/Controller/ProdottoController.php” type: annotation # app/config/config.yml # TtsDemoBundle Default controller default: resource: “@TtsDemoBundle/Controller/DefaultController.php” type: annotation # TtsDemoBundle Catalogo controller catalogo: resource: “@TtsDemoBundle/Controller/CatalogoController.php” type: annotation # TtsDemoBundle Prodotto controller prodotto: resource: “@TtsDemoBundle/Controller/ProdottoController.php” type: annotation
  • 27. http://traintosymfony.com27 Emanuele Gaspari type: annotation (2) # app/config/config.yml # TtsDemoBundle tts_demo: resource: “@TtsDemoBundle/Controller/” type: annotation # app/config/config.yml # TtsDemoBundle tts_demo: resource: “@TtsDemoBundle/Controller/” type: annotation o, semplicemente, specifico la cartella che li contiene tutti
  • 28. http://traintosymfony.com28 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 30. http://traintosymfony.com30 Emanuele Gaspari GET /prodotto/EG-124 => prodotto_show GET /prodotto/index => prodotto_show, prodotto_index # app/config/routing.yml prodotto_show: path: /prodotto/{codice} defaults: { _controller: TtsDemoBundle:Prodotto:show } prodotto_index: path: /prodotto/index defaults: { _controller: TtsDemoBundle:Prodotto:index } # app/config/routing.yml prodotto_show: path: /prodotto/{codice} defaults: { _controller: TtsDemoBundle:Prodotto:show } prodotto_index: path: /prodotto/index defaults: { _controller: TtsDemoBundle:Prodotto:index } collisione di urls
  • 31. http://traintosymfony.com31 Emanuele Gaspari sfrutto l'ordine con cui vengono definite le Routes il controller si ferma alla prima Route abbinata all'url è sufficiente definire prima la Route che non contiene parametri GET /prodotto/index GET /prodotto/EG-124 # app/config/routing.yml prodotto_index: path: /prodotto/index prodotto_show: path: /prodotto/{codice} # app/config/routing.yml prodotto_index: path: /prodotto/index prodotto_show: path: /prodotto/{codice} soluzione 1, ordine delle Routes
  • 32. http://traintosymfony.com32 Emanuele Gaspari rimane ancora il problema della collisione di urls verso più di una Route basarsi sull'ordine con cui vengono esaminate le Routes non è sufficiente: dopo un anno che il sito è in produzione, mi ricordo che la posizione di quella specifica Route è vitale? anche usando l'annotazione @Route, posso non volere che all'interno di un Controller una funzione venga spostata in alto solo perché la Route venga esaminata prima l'ordine non basta
  • 33. http://traintosymfony.com33 Emanuele Gaspari sfrutto il parametro requirements # app/config/routing.yml prodotto_show: path: /prodotto/{codice} requirements: codice: [A-Z]{2}-[0-9]+ prodotto_index: path: /prodotto/index # app/config/routing.yml prodotto_show: path: /prodotto/{codice} requirements: codice: [A-Z]{2}-[0-9]+ prodotto_index: path: /prodotto/index GET /prodotto/index GET /prodotto/EG-124 non c'è più collisione tra Routes non mi affido più all'ordine di caricamento soluzione 2, parametro requirements pongo dei vincoli sul formato di un parametro di una Route
  • 34. http://traintosymfony.com34 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 35. http://traintosymfony.com35 Emanuele Gaspari Symfony associa il nome logico ad una specifica classe e metodo (Controller e Action) bundle:controller:action nome logico di un Controller sintassi per riferirsi ad un'azione da qualunque punto dell'applicazione Controller Naming Pattern
  • 36. http://traintosymfony.com36 Emanuele Gaspari TtsDemoBundle:Default:homepage Bundle Controller Metodo TtsDemoBundleTtsDemoBundle DefaultControllerDefaultController homepageAction()homepageAction() # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class DefaultController extends Controller { public function homepageAction() { […] } } # src/Tts/DemoBundle/Controller/DefaultController.php <?php namespace TtsDemoBundleController; use SymfonyBundleFrameworkBundleControllerController; class DefaultController extends Controller { public function homepageAction() { […] } } Controller Naming Pattern
  • 37. http://traintosymfony.com37 Emanuele Gaspari # template twig {{ render(controller(“TtsDemoBundle:Blog:latestPosts”, {“max”: 5})) }} # template twig {{ render(controller(“TtsDemoBundle:Blog:latestPosts”, {“max”: 5})) }} esempio
  • 38. http://traintosymfony.com38 Emanuele Gaspari $ php app/console router:debug$ php app/console router:debug $ php app/console router:match /prodotto/EG-124$ php app/console router:match /prodotto/EG-124 tips stampare a console l'elenco di tutte le Routes caricate verificare se un path è associato da Symfony ad una Route
  • 39. http://traintosymfony.com39 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 40. http://traintosymfony.com40 Emanuele Gaspari oggetto Request SymfonyComponentHttpFoundationRequest oggetto che ho a disposizione all'interno di ogni azione per gestire tutti i parametri della richiesta Symfony utilizza un oggetto Request per modellare una richiesta HTTP
  • 41. http://traintosymfony.com41 Emanuele Gaspari accedere ad un oggetto Request <?php public function homepageAction() { $request = $this->getRequest(); } <?php public function homepageAction() { $request = $this->getRequest(); } use SymfonyComponentHttpFoundationRequest; $request = Request::createFromGlobals(); use SymfonyComponentHttpFoundationRequest; $request = Request::createFromGlobals(); accedere a Request in una Action: accedere a Request da qualunque punto dell'applicazione (in PHP): $this->getRequest() => 0.04 Kb Request::createFromGlobals() => 7.07 Kb {{ app.request }}{{ app.request }} accedere a Request da twig:
  • 43. http://traintosymfony.com43 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 44. http://traintosymfony.com44 Emanuele Gaspari /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { [...] } /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { [...] } url con parametri 200 GET /prodotto/nuovi/EG-124/eg-124-new-hammer non importa l'ordine possono non essere specificati tutti l'ordine è importante, per associare i parametri dell'url 404 GET /prodotto/nuovi/EG-124 404 GET /prodotto/nuovi/EG-124/
  • 45. http://traintosymfony.com45 Emanuele Gaspari defaults (1) 200 GET /prodotto/nuovi/EG-124/eg-124-new-hammer 200 GET /prodotto/nuovi/EG-124 404 GET /prodotto/nuovi/EG-124/ /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”, defaults={“slug”: “-”}) */ public function showAction($codice, $categoria, $slug) { [...] } /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”, defaults={“slug”: “-”}) */ public function showAction($codice, $categoria) { [...] } /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $categoria, $slug = “-”) { [...] } /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”, defaults={“slug”: “-”}) */ public function showAction($codice, $categoria, $slug) { [...] } /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”, defaults={“slug”: “-”}) */ public function showAction($codice, $categoria) { [...] } /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $categoria, $slug = “-”) { [...] }
  • 46. http://traintosymfony.com46 Emanuele Gaspari accesso ai parametri 200 GET /prodotto/nuovi/EG-124/eg-124-new-hammer?color=red 200 GET /prodotto/nuovi/EG-124?color=red /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug = “-”, $categoria) { $request = $this->getRequest(); // nell'url $codice; $codice = $request->get(“codice”); // in $_GET $color = $request->get(“color”); $color = $request->query->get(“color”); [...] } /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug = “-”, $categoria) { $request = $this->getRequest(); // nell'url $codice; $codice = $request->get(“codice”); // in $_GET $color = $request->get(“color”); $color = $request->query->get(“color”); [...] }
  • 47. http://traintosymfony.com47 Emanuele Gaspari ?get= o /{param} ● parametro essenziale? ● eleganza degli url ● cambio successivo degli url ● indicizzazione dei motori di ricerca ● multilingua quando passare un parametro come ?get= e quando come /{param}
  • 48. http://traintosymfony.com48 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 49. http://traintosymfony.com49 Emanuele Gaspari Response ogni Action restituisce sempre un oggetto Response real life: molte volte la Action che implementerai restituirà semplicemente un array di variabili, utilizzabili in un template che viene scelto più o meno “automaticamente”
  • 50. http://traintosymfony.com50 Emanuele Gaspari return array la situazione più semplice è quella in cui utilizzo l'annotation @Template e la mia Action restituisce semplicemente un array
  • 51. http://traintosymfony.com51 Emanuele Gaspari return array # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; use SensioBundleFrameworkExtraBundleConfigurationTemplate; class ProdottoController extends Controller { /** * @Route(“/prodotto/{categoria}/{codice}/{slug}”, name=”prodotto_show”) * @Template() */ public function showAction($codice, $slug, $categoria) { $entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy( array(“codice” => $codice) ); return array('entity' => $entity); } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyBundleFrameworkBundleControllerController; use SensioBundleFrameworkExtraBundleConfigurationRoute; use SensioBundleFrameworkExtraBundleConfigurationTemplate; class ProdottoController extends Controller { /** * @Route(“/prodotto/{categoria}/{codice}/{slug}”, name=”prodotto_show”) * @Template() */ public function showAction($codice, $slug, $categoria) { $entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy( array(“codice” => $codice) ); return array('entity' => $entity); }
  • 52. http://traintosymfony.com52 Emanuele Gaspari render() posso fare in modo che l'azione restituisca un template TWIG compilato, ad esempio perché è diverso in base alla logica interna dell'azione utlizzo la funzione $this->render() specificando il template
  • 53. http://traintosymfony.com53 Emanuele Gaspari # src/Tts/DemoBundle/Controller/ProdottoController.php <?php class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { $entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy( array(“codice” => $codice) ); return $this->render('TtsDemoBundle:Prodotto:show_offer.html.twig', array( 'entity' => $entity )); } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { $entity = $this->getRepository('TtsDemoBundle:Prodotto')->findOneBy( array(“codice” => $codice) ); return $this->render('TtsDemoBundle:Prodotto:show_offer.html.twig', array( 'entity' => $entity )); } $this->render()
  • 54. http://traintosymfony.com54 Emanuele Gaspari costruire una Response è possibile anche costruire un oggetto Response utile nel caso in cui abbia necessità di costruire la risposta in più passaggi a seconda di variabili o di effettuare delle operazioni successivamente
  • 55. http://traintosymfony.com55 Emanuele Gaspari costruire una Response utilizzo la funzione $this->renderView() per memorizzare un contenuto HTML in una variabile creo un oggetto Response con quella variabile come primo argomentoimpostando
  • 56. http://traintosymfony.com56 Emanuele Gaspari # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyComponentHttpFoundationResponse; class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { $entity = [...] $content = $this->renderView('TtsDemoBundle:Prodotto:show.html.twig', array( 'entity' => $entity )); [...] return new Response($content); } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyComponentHttpFoundationResponse; class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { $entity = [...] $content = $this->renderView('TtsDemoBundle:Prodotto:show.html.twig', array( 'entity' => $entity )); [...] return new Response($content); }
  • 57. http://traintosymfony.com57 Emanuele Gaspari # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyComponentHttpFoundationResponse; class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { $entity = [...] $response = new Response($entity->getCodice(), 200, array( 'content-type' => 'text/html' )); $response->prepare($this->getRequest()); $response->send(); } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyComponentHttpFoundationResponse; class ProdottoController extends Controller { /** * @Route("/prodotto/{categoria}/{codice}/{slug}", name=”prodotto_show”) */ public function showAction($codice, $slug, $categoria) { $entity = [...] $response = new Response($entity->getCodice(), 200, array( 'content-type' => 'text/html' )); $response->prepare($this->getRequest()); $response->send(); }
  • 59. http://traintosymfony.com59 Emanuele Gaspari json Response # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyComponentHttpFoundationResponse; use SymfonyComponentHttpFoundationJsonResponse; public function jsonAction($codice, $slug, $categoria) { $entity = [...] $jsonResponse = array(“codice” => $entity->getCodice(), [...]); // crea una risposta JSON $response = new Response(json_encode($jsonResponse)); $response->headers->set('Content-Type', 'application/json'); return $response; // crea una risposta JSON utilizzando la classe JsonResponse (Symfony >= 2.1) $response = new JsonResponse(); $response->setData($jsonResponse); return $response; } # src/Tts/DemoBundle/Controller/ProdottoController.php <?php use SymfonyComponentHttpFoundationResponse; use SymfonyComponentHttpFoundationJsonResponse; public function jsonAction($codice, $slug, $categoria) { $entity = [...] $jsonResponse = array(“codice” => $entity->getCodice(), [...]); // crea una risposta JSON $response = new Response(json_encode($jsonResponse)); $response->headers->set('Content-Type', 'application/json'); return $response; // crea una risposta JSON utilizzando la classe JsonResponse (Symfony >= 2.1) $response = new JsonResponse(); $response->setData($jsonResponse); return $response; }
  • 60. http://traintosymfony.com60 Emanuele Gaspari riassunto ● un array ● $this->render() ● $this->renderView() ● un oggetto Response ● un oggetto JsonResponse abbiamo visto che un'azione può utilizzare: ...e può fare molto altro!
  • 61. http://traintosymfony.com61 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 62. http://traintosymfony.com62 Emanuele Gaspari redirect il redirect è un messaggio al browser cambia l'url perché è effettivamente una nuova richiesta in caso di: ● redirect temporaneo (302, default) o permanente (301) ● invio corretto di un form: redirezione ad una pagina di conferma ● se il sito è multilingua, si può effettuare un redirect dopo aver scelto la lingua in base al browser
  • 63. http://traintosymfony.com63 Emanuele Gaspari redirect temporaneo # src/Tts/DemoBundle/Controller/DefaultController.php <?php class DefaultController extends Controller { /** * @Route("/", name=”homepage”) */ public function homepageAction() { return $this->redirect($this->generateUrl('homepage_natale')); } } # src/Tts/DemoBundle/Controller/DefaultController.php <?php class DefaultController extends Controller { /** * @Route("/", name=”homepage”) */ public function homepageAction() { return $this->redirect($this->generateUrl('homepage_natale')); } } redirect temporaneo ad un altro url
  • 64. http://traintosymfony.com64 Emanuele Gaspari RedirectResponse c'è un oggetto dedicato (che sorpresa!) che la Action può restituire in caso di redirect: RedirectResponse
  • 65. http://traintosymfony.com65 Emanuele Gaspari RedirectResponse # src/Tts/DemoBundle/Controller/DefaultController.php <?php use SymfonyComponentHttpFoundationRedirectResponse class DefaultController extends Controller { /** * @Route(“/”, name=”homepage”) */ public function homepageAction() { $respose = new RedirectResponse($this->generateUrl('homepage_natale')); [..] return $response; } } # src/Tts/DemoBundle/Controller/DefaultController.php <?php use SymfonyComponentHttpFoundationRedirectResponse class DefaultController extends Controller { /** * @Route(“/”, name=”homepage”) */ public function homepageAction() { $respose = new RedirectResponse($this->generateUrl('homepage_natale')); [..] return $response; } }
  • 66. http://traintosymfony.com66 Emanuele Gaspari # src/Tts/DemoBundle/Controller/DefaultController.php <?php class DefaultController extends Controller { /** * @Route("/chisiamo", name=”chisiamo”) */ public function chisiamoAction() { return $this->redirect($this->generateUrl('homepage_contatti'), 301); } } # src/Tts/DemoBundle/Controller/DefaultController.php <?php class DefaultController extends Controller { /** * @Route("/chisiamo", name=”chisiamo”) */ public function chisiamoAction() { return $this->redirect($this->generateUrl('homepage_contatti'), 301); } } redirect permanente redirect permanente con codice di stato HTTP 301
  • 67. http://traintosymfony.com67 Emanuele Gaspari Routes Controller e Action specificare una Route Routes parametriche annotation @Route collisione di urls Controller Naming Pattern Request oggetto Request i parametri Response oggetto Response redirect parametri per il template ROUTING
  • 68. http://traintosymfony.com68 Emanuele Gaspari l'azione può passare delle variabili al template restituendo un array public function showAction($codice) { [...] return array( 'entity' => $entity, 'show_extended_version' => true ); } public function showAction($codice) { [...] return array( 'entity' => $entity, 'show_extended_version' => true ); } utilizzabili nel template twig {% if show_extended_version %} [...] {% else %} <a href=”...”> {{ entity.codice }} </a> {% endif %} {% if show_extended_version %} [...] {% else %} <a href=”...”> {{ entity.codice }} </a> {% endif %}
  • 69. TRAIN TO SYMFONY Verona, 13•14 Aprile 2013 the frameworkshop http://traintosymfony.com @TrainToSymfony Media partner:©Copyright Emanuele Gaspari Castelletti