SlideShare uma empresa Scribd logo
1 de 29
Baixar para ler offline
Going to production on
a Raspberry Pi with
varnish tags
Who am I?
Jérémy DERUSSÉ
Web Technical Leader
AptusHealth
@jderusse
How to get fast responses
from a Symfony application?
you can't
How to get fast responses
from a Symfony application?your backend
you can't
Solution
using http shared cache
describe in RFC-2616 RFC-7234
Integration in Symfony
use SensioBundleFrameworkExtraBundleConfigurationCache;
/**
* @Cache(smaxage="3600")
*/
public function indexAction()
{
// ...
}
Advanced usage with FriendsOfSymfony/FOSHttpCacheBundle
Issue #1
Unsharable resources
private resources (ie. invoice, shopping cart, ...)
per role representations
Solution
vary cache on user/role/other
see SfLive 2015 Jérôme Vieilledent & David Buchmann
Repousser les limites : HTTP cache et utilisateurs connectés
Issue #2
Cache invalidation
“ There are only two hard things in Computer Science: cache
invalidation and naming things.
Phil Karlton
Cache models
Validation model
etag
last-modified
drawbacks
application is booted
hard to implement
Expiration model
expires
cache-control
drawback
no control on invalidation
cache model
In a real world
Backend can't validate every cache HIT
Life time is not predictable
BUT
Varnish can be requested to partially invalidate responses
Backend knows when resources change
Responses are build on top of resources
curl -I "http://varnish.myapp.com/c"
curl -I "http://varnish.myapp.com/b"
curl -I "http://varnish.myapp.com/a"
HTTP/1.1 200 OK
Cache-Control: public, s-maxage=3600
X-Cache-Tags: Foo,Bar
HTTP/1.1 200 OK
Cache-Control: public, s-maxage=3600
X-Cache-Tags: Foo
Varnish tags
curl 
-X "BAN" 
-H "X-Cache-Tags: Foo" 
"http://varnish.myapp.com"
HTTP/1.1 200 OK
Cache-Control: public, s-maxage=3600
X-Cache-Tags: Bar,Qux
Varnish tags
curl "http://varnish.myapp.com/posts/42"
HTTP/1.1 200 OK
Cache-Control: public, s-maxage=86400
X-Cache-Tags: Post:42,Author:12,Comment:314,Comment:1337
{
"id": 42,
"title": "My blog post.",
"body": "Lorem Ipsum.",
"author": {
"id": 12,
"username": "jderusse"
},
"comments": [
{
"id": 314,
"message": "Wow such post"
},
{
"id": 1337,
"message": "much performance"
}
]
}
Automate Tagging
Tagging Response
1. Collect displayed resources
2. Generate resource identifier
3. Tag response
Automate Tagging
Tagging Response - 1. Collect displayed resources
namespace AppEventListener;
use JMSSerializerEventDispatcherEvents;
use JMSSerializerEventDispatcherEventSubscriberInterface;
use JMSSerializerEventDispatcherObjectEvent;
class SerializationTagListener implements EventSubscriberInterface
{
public function onPostSerialize(ObjectEvent $event)
{
$resource = $event->getObject();
// TODO
}
public static function getSubscribedEvents()
{
return [
[
'event' => Events::POST_SERIALIZE,
'format' => 'json',
'method' => 'onPostSerialize',
],
];
}
}
Automate Tagging
Tagging Response - 2. Generate resource identifier
namespace AppEventListener;
use AppTagTagExtractorInterface;
use FOSHttpCacheBundleHandlerTagHandler;
use JMSSerializerEventDispatcherEventSubscriberInterface;
use JMSSerializerEventDispatcherObjectEvent;
class SerializationTagListener implements EventSubscriberInterface
{
private $tagExtractor;
public function __construct(TagExtractorInterface $tagExtractor)
{
$this->tagExtractor = $tagExtractor;
}
public function onPostSerialize(ObjectEvent $event): void
{
//...
$tags = $this->tagExtractor->extract($event->getObject());
}
//...
}
Automate Tagging
Tagging Response - 3. Tag response
namespace AppEventListener;
use AppTagTagExtractorInterface;
use FOSHttpCacheBundleHandlerTagHandler;
use JMSSerializerEventDispatcherEventSubscriberInterface;
use JMSSerializerEventDispatcherObjectEvent;
class SerializationTagListener implements EventSubscriberInterface
{
private $tagExtractor;
private $tagHandler;
public function __construct(TagExtractorInterface $tagExtractor, TagHandler $tagHandler)
{
$this->tagExtractor = $tagExtractor;
$this->tagHandler = $tagHandler;
}
public function onPostSerialize(ObjectEvent $event): void
{
$tags = $this->tagExtractor->extract($event->getObject());
$this->tagHandler->addTags($tags);
}
//...
}
Automate Tagging
Tagging Response
1. Collect displayed resources
2. Generate resource identifier
3. Tag response
Invalidate cache
1. Listen changes
2. Generate resource identifier
3. Call varnish
Automate Tagging
Invalidate Cache - 1. Listen changes
namespace AppEventListener;
use DoctrineCommonEventSubscriber;
use DoctrineORMEventOnFlushEventArgs;
use DoctrineORMEvents;
class DoctrineInvalidationTagListener implements EventSubscriber
{
public function getSubscribedEvents()
{
return [Events::onFlush];
}
public function onFlush(OnFlushEventArgs $eventArgs)
{
$uow = $eventArgs->getEntityManager()->getUnitOfWork();
foreach ($uow->getScheduledEntityUpdates() as $resource) {
// TODO
}
foreach ($uow->getScheduledEntityDeletions() as $resource) {
// TODO
}
}
}
Automate Tagging
Invalidate Cache - 2. Generate resource identifier
namespace AppEventListener;
use AppTagTagExtractorInterface;
use DoctrineCommonEventSubscriber;
class DoctrineInvalidationTagListener implements EventSubscriber
{
private $tagExtractor;
public function __construct(TagExtractorInterface $tagExtractor)
{
$this->tagExtractor = $tagExtractor;
}
public function onFlush(OnFlushEventArgs $eventArgs)
{
$uow = $eventArgs->getEntityManager()->getUnitOfWork();
$tags = [];
foreach ($uow->getScheduledEntityUpdates() as $resource) {
$tags = array_merge($tags, $this->tagExtractor->extract($resource));
}
foreach ($uow->getScheduledEntityDeletions() as $resource) {
$tags = array_merge($tags, $this->tagExtractor->extract($resource));
}
// TODO
}
}
Automate Tagging
Invalidate Cache - 3. Call varnish
namespace AppEventListener;
use AppTagTagExtractorInterface;
use DoctrineCommonEventSubscriber;
use FOSHttpCacheHandlerTagHandler;
class DoctrineInvalidationTagListener implements EventSubscriber
{
private $tagExtractor;
public function __construct(TagExtractorInterface $tagExtractor, TagHandler $tagHandler)
{
$this->tagExtractor = $tagExtractor;
$this->tagHandler = $tagHandler;
}
public function onFlush(OnFlushEventArgs $eventArgs)
{
// ...
$this->tagHandler->invalidateTags($tags);
}
}
Automate Tagging
Tagging Response
1. Collect displayed resources
2. Generate resource identifier
3. Tag response
Invalidate cache
1. Listen changes
2. Generate resource identifier
3. Call varnish
Enjoy
Silver bullet?
Works well when
HIT >> MISS
Read >> Write
Application knows resources used to build
response
Drawback
Operations are not Atomic
Backend handles writes
Backend knows infrastructure
It slows writes
Demo
Software
- env=dev
- fetch=lazy
symfony/symfony
doctrine/doctrine-bundle
friendsofsymfony/rest-bundle
jms/serializer-bundle
friendsofsymfony/http-cache-bundle
marmelab/admin-on-rest
Demo
Hardware
Raspberry Pi Orange Pi
docker
MySQL
NGINX
PHP7-FPM
Varnish
$9.59
Demo
ab -n 8000 -c 26 192.168.1.17:81/comments/1
This is ApacheBench, Version 2.3 <$Revision: 1757674 $>
Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net
Licensed to The Apache Software Foundation, http://www.apache.org/
Server Software: nginx/1.10.3
Server Hostname: 192.168.1.16
Server Port: 80
Document Path: /comments/1
Document Length: 576 bytes
Concurrency Level: 26
Time taken for tests: 26.912 seconds
Complete requests: 200
Failed requests: 0
Total transferred: 193400 bytes
HTML transferred: 115200 bytes
Requests per second: 7.43 [#/sec] (mean)
Time per request: 3498.553 [ms] (mean)
Time per request: 134.560 [ms] (mean, across all concurrent
Transfer rate: 7.02 [Kbytes/sec] received
Connection Times (ms)
min mean[+/-sd] median max
Connect: 1 2 1.4 1 6
Processing: 546 3342 1156.7 3020 7204
Waiting: 546 3342 1156.7 3020 7204
Total: 550 3344 1156.5 3021 7205
in numbers
ab -n 8000 -c 26 192.168.1.17/comments/1
This is ApacheBench, Version 2.3 <$Revision: 1757674 $>
Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net
Licensed to The Apache Software Foundation, http://www.apache.org/
Server Software: nginx/1.10.3
Server Hostname: 192.168.1.17
Server Port: 80
Document Path: /comments/1
Document Length: 576 bytes
Concurrency Level: 26
Time taken for tests: 2.340 seconds
Complete requests: 8000
Failed requests: 0
Total transferred: 8948504 bytes
HTML transferred: 4608000 bytes
Requests per second: 3418.52 [#/sec] (mean)
Time per request: 7.606 [ms] (mean)
Time per request: 0.293 [ms] (mean, across all concurrent
Transfer rate: 3734.21 [Kbytes/sec] received
Connection Times (ms)
min mean[+/-sd] median max
Connect: 0 2 0.8 2 7
Processing: 2 5 3.3 5 55
Waiting: 2 5 3.3 4 55
Total: 2 8 3.3 7 56
app varnish
Thank You
Questions?
Credits
http://linuxgizmos.com/10-dollar-orange-pi-one-pits-quad-core-cortex-a7-against-pi-zero/
http://toutsurlesbisounours.centerblog.net/rub-bisounours-3eme-generation-.html
https://de.wikipedia.org/wiki/Carambar
https://rcgo.com.br/recursos.html

Mais conteúdo relacionado

Mais procurados

Laravel 5 Annotations: RESTful API routing
Laravel 5 Annotations: RESTful API routingLaravel 5 Annotations: RESTful API routing
Laravel 5 Annotations: RESTful API routingChristopher Pecoraro
 
RESTful API development in Laravel 4 - Christopher Pecoraro
RESTful API development in Laravel 4 - Christopher PecoraroRESTful API development in Laravel 4 - Christopher Pecoraro
RESTful API development in Laravel 4 - Christopher PecoraroChristopher Pecoraro
 
High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014
High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014
High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014Matthias Noback
 
Webpack Encore Symfony Live 2017 San Francisco
Webpack Encore Symfony Live 2017 San FranciscoWebpack Encore Symfony Live 2017 San Francisco
Webpack Encore Symfony Live 2017 San FranciscoRyan Weaver
 
170517 damien gérard framework facebook
170517 damien gérard   framework facebook170517 damien gérard   framework facebook
170517 damien gérard framework facebookGeeks Anonymes
 
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...Ryan Weaver
 
Symfony tips and tricks
Symfony tips and tricksSymfony tips and tricks
Symfony tips and tricksJavier Eguiluz
 
Web service with Laravel
Web service with LaravelWeb service with Laravel
Web service with LaravelAbuzer Firdousi
 
Playing with parse.com
Playing with parse.comPlaying with parse.com
Playing with parse.comJUG Genova
 
Flask RESTful Flask HTTPAuth
Flask RESTful Flask HTTPAuthFlask RESTful Flask HTTPAuth
Flask RESTful Flask HTTPAuthEueung Mulyana
 
Dessi docker kubernetes paas cloud
Dessi docker kubernetes paas cloudDessi docker kubernetes paas cloud
Dessi docker kubernetes paas cloudMassimiliano Dessì
 
Datagrids with Symfony 2, Backbone and Backgrid
Datagrids with Symfony 2, Backbone and BackgridDatagrids with Symfony 2, Backbone and Backgrid
Datagrids with Symfony 2, Backbone and Backgrideugenio pombi
 
Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...
Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...
Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...King Foo
 
Dockerize it! @ Codemotion 2016 in Rome
Dockerize it! @ Codemotion 2016 in RomeDockerize it! @ Codemotion 2016 in Rome
Dockerize it! @ Codemotion 2016 in RomeAlessandro Nadalin
 
Rails vs Web2py
Rails vs Web2pyRails vs Web2py
Rails vs Web2pyjonromero
 
Composable and streamable Play apps
Composable and streamable Play appsComposable and streamable Play apps
Composable and streamable Play appsYevgeniy Brikman
 

Mais procurados (20)

Laravel 5 Annotations: RESTful API routing
Laravel 5 Annotations: RESTful API routingLaravel 5 Annotations: RESTful API routing
Laravel 5 Annotations: RESTful API routing
 
RESTful API development in Laravel 4 - Christopher Pecoraro
RESTful API development in Laravel 4 - Christopher PecoraroRESTful API development in Laravel 4 - Christopher Pecoraro
RESTful API development in Laravel 4 - Christopher Pecoraro
 
High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014
High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014
High Quality Symfony Bundles tutorial - Dutch PHP Conference 2014
 
Webpack Encore Symfony Live 2017 San Francisco
Webpack Encore Symfony Live 2017 San FranciscoWebpack Encore Symfony Live 2017 San Francisco
Webpack Encore Symfony Live 2017 San Francisco
 
170517 damien gérard framework facebook
170517 damien gérard   framework facebook170517 damien gérard   framework facebook
170517 damien gérard framework facebook
 
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
Finally, Professional Frontend Dev with ReactJS, WebPack & Symfony (Symfony C...
 
Symfony tips and tricks
Symfony tips and tricksSymfony tips and tricks
Symfony tips and tricks
 
Web service with Laravel
Web service with LaravelWeb service with Laravel
Web service with Laravel
 
Javascript laravel's friend
Javascript laravel's friendJavascript laravel's friend
Javascript laravel's friend
 
Playing with parse.com
Playing with parse.comPlaying with parse.com
Playing with parse.com
 
Flask RESTful Flask HTTPAuth
Flask RESTful Flask HTTPAuthFlask RESTful Flask HTTPAuth
Flask RESTful Flask HTTPAuth
 
Dessi docker kubernetes paas cloud
Dessi docker kubernetes paas cloudDessi docker kubernetes paas cloud
Dessi docker kubernetes paas cloud
 
Symfony 2
Symfony 2Symfony 2
Symfony 2
 
Datagrids with Symfony 2, Backbone and Backgrid
Datagrids with Symfony 2, Backbone and BackgridDatagrids with Symfony 2, Backbone and Backgrid
Datagrids with Symfony 2, Backbone and Backgrid
 
Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...
Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...
Building Web Services with Zend Framework (PHP Benelux meeting 20100713 Vliss...
 
Dockerize it! @ Codemotion 2016 in Rome
Dockerize it! @ Codemotion 2016 in RomeDockerize it! @ Codemotion 2016 in Rome
Dockerize it! @ Codemotion 2016 in Rome
 
Rails vs Web2py
Rails vs Web2pyRails vs Web2py
Rails vs Web2py
 
Flask Basics
Flask BasicsFlask Basics
Flask Basics
 
Composable and streamable Play apps
Composable and streamable Play appsComposable and streamable Play apps
Composable and streamable Play apps
 
Beyond Phoenix
Beyond PhoenixBeyond Phoenix
Beyond Phoenix
 

Destaque

How to Become a Thought Leader in Your Niche
How to Become a Thought Leader in Your NicheHow to Become a Thought Leader in Your Niche
How to Become a Thought Leader in Your NicheLeslie Samuel
 
Introduction to CQRS and Event Sourcing
Introduction to CQRS and Event SourcingIntroduction to CQRS and Event Sourcing
Introduction to CQRS and Event SourcingSamuel ROZE
 
conservation and rewarding biodiversity conservation Trondheim 05-10-gupta-...
conservation and rewarding biodiversity conservation Trondheim   05-10-gupta-...conservation and rewarding biodiversity conservation Trondheim   05-10-gupta-...
conservation and rewarding biodiversity conservation Trondheim 05-10-gupta-...Dr Anil Gupta
 
How to Create 1000 Sony
How to Create 1000 SonyHow to Create 1000 Sony
How to Create 1000 SonyHAX
 
A Publisher's Survival Guide for the Platform Era
A Publisher's Survival Guide for the Platform EraA Publisher's Survival Guide for the Platform Era
A Publisher's Survival Guide for the Platform EraBloomberg Media
 
FrenchWeb 500, le classement des entreprises de la tech française
FrenchWeb 500, le classement des entreprises de la tech françaiseFrenchWeb 500, le classement des entreprises de la tech française
FrenchWeb 500, le classement des entreprises de la tech françaiseFrenchWeb.fr
 
Construire Des Applications Cloud Natives - SymfonyLive Paris 2016
Construire Des Applications Cloud Natives - SymfonyLive Paris 2016Construire Des Applications Cloud Natives - SymfonyLive Paris 2016
Construire Des Applications Cloud Natives - SymfonyLive Paris 2016Ori Pekelman
 
Fists with Your Toes - Learning to relax as a UX / BA crossbreed
Fists with Your Toes - Learning to relax as a UX / BA crossbreedFists with Your Toes - Learning to relax as a UX / BA crossbreed
Fists with Your Toes - Learning to relax as a UX / BA crossbreedLeo Barnes
 
Bucay, jorge el camino de la autodependencia
Bucay, jorge   el camino de la autodependenciaBucay, jorge   el camino de la autodependencia
Bucay, jorge el camino de la autodependenciasilvianoramirezgomez
 
Entrevista, grupo focal y diario de campo NRC30018
Entrevista, grupo focal y diario de campo NRC30018Entrevista, grupo focal y diario de campo NRC30018
Entrevista, grupo focal y diario de campo NRC30018John Sevastien
 
An introduction to english literature i
An introduction to english literature iAn introduction to english literature i
An introduction to english literature ipuchmuller
 
Surviving in an Async-First Development World
Surviving in an Async-First Development WorldSurviving in an Async-First Development World
Surviving in an Async-First Development WorldMirco Vanini
 
The Mysteries Of Harris Burdickfv
The Mysteries Of Harris BurdickfvThe Mysteries Of Harris Burdickfv
The Mysteries Of Harris Burdickfvaquaglia
 
Cloud in Action
Cloud in Action Cloud in Action
Cloud in Action Franco Ucci
 
Fitness tips for women
Fitness tips for womenFitness tips for women
Fitness tips for womenMedisys Kart
 

Destaque (17)

How to Become a Thought Leader in Your Niche
How to Become a Thought Leader in Your NicheHow to Become a Thought Leader in Your Niche
How to Become a Thought Leader in Your Niche
 
Introduction to CQRS and Event Sourcing
Introduction to CQRS and Event SourcingIntroduction to CQRS and Event Sourcing
Introduction to CQRS and Event Sourcing
 
conservation and rewarding biodiversity conservation Trondheim 05-10-gupta-...
conservation and rewarding biodiversity conservation Trondheim   05-10-gupta-...conservation and rewarding biodiversity conservation Trondheim   05-10-gupta-...
conservation and rewarding biodiversity conservation Trondheim 05-10-gupta-...
 
How to Create 1000 Sony
How to Create 1000 SonyHow to Create 1000 Sony
How to Create 1000 Sony
 
A Publisher's Survival Guide for the Platform Era
A Publisher's Survival Guide for the Platform EraA Publisher's Survival Guide for the Platform Era
A Publisher's Survival Guide for the Platform Era
 
FrenchWeb 500, le classement des entreprises de la tech française
FrenchWeb 500, le classement des entreprises de la tech françaiseFrenchWeb 500, le classement des entreprises de la tech française
FrenchWeb 500, le classement des entreprises de la tech française
 
Construire Des Applications Cloud Natives - SymfonyLive Paris 2016
Construire Des Applications Cloud Natives - SymfonyLive Paris 2016Construire Des Applications Cloud Natives - SymfonyLive Paris 2016
Construire Des Applications Cloud Natives - SymfonyLive Paris 2016
 
Portadas nacionales 30 marzo-17.pdf
Portadas nacionales 30 marzo-17.pdfPortadas nacionales 30 marzo-17.pdf
Portadas nacionales 30 marzo-17.pdf
 
Fists with Your Toes - Learning to relax as a UX / BA crossbreed
Fists with Your Toes - Learning to relax as a UX / BA crossbreedFists with Your Toes - Learning to relax as a UX / BA crossbreed
Fists with Your Toes - Learning to relax as a UX / BA crossbreed
 
Bucay, jorge el camino de la autodependencia
Bucay, jorge   el camino de la autodependenciaBucay, jorge   el camino de la autodependencia
Bucay, jorge el camino de la autodependencia
 
HdE - Spegulo
HdE - SpeguloHdE - Spegulo
HdE - Spegulo
 
Entrevista, grupo focal y diario de campo NRC30018
Entrevista, grupo focal y diario de campo NRC30018Entrevista, grupo focal y diario de campo NRC30018
Entrevista, grupo focal y diario de campo NRC30018
 
An introduction to english literature i
An introduction to english literature iAn introduction to english literature i
An introduction to english literature i
 
Surviving in an Async-First Development World
Surviving in an Async-First Development WorldSurviving in an Async-First Development World
Surviving in an Async-First Development World
 
The Mysteries Of Harris Burdickfv
The Mysteries Of Harris BurdickfvThe Mysteries Of Harris Burdickfv
The Mysteries Of Harris Burdickfv
 
Cloud in Action
Cloud in Action Cloud in Action
Cloud in Action
 
Fitness tips for women
Fitness tips for womenFitness tips for women
Fitness tips for women
 

Semelhante a Getting Fast Responses from Symfony with Varnish Tags

Heavy Web Optimization: Backend
Heavy Web Optimization: BackendHeavy Web Optimization: Backend
Heavy Web Optimization: BackendVõ Duy Tuấn
 
Meetup Performance
Meetup PerformanceMeetup Performance
Meetup PerformanceGreg Whalin
 
Exploring Async PHP (SF Live Berlin 2019)
Exploring Async PHP (SF Live Berlin 2019)Exploring Async PHP (SF Live Berlin 2019)
Exploring Async PHP (SF Live Berlin 2019)dantleech
 
Porting Rails Apps to High Availability Systems
Porting Rails Apps to High Availability SystemsPorting Rails Apps to High Availability Systems
Porting Rails Apps to High Availability SystemsMarcelo Pinheiro
 
Lean Php Presentation
Lean Php PresentationLean Php Presentation
Lean Php PresentationAlan Pinstein
 
Harmonious Development: Via Vagrant and Puppet
Harmonious Development: Via Vagrant and PuppetHarmonious Development: Via Vagrant and Puppet
Harmonious Development: Via Vagrant and PuppetAchieve Internet
 
Rapid java backend and api development for mobile devices
Rapid java backend and api development for mobile devicesRapid java backend and api development for mobile devices
Rapid java backend and api development for mobile devicesciklum_ods
 
Speed up your developments with Symfony2
Speed up your developments with Symfony2Speed up your developments with Symfony2
Speed up your developments with Symfony2Hugo Hamon
 
Build powerfull and smart web applications with Symfony2
Build powerfull and smart web applications with Symfony2Build powerfull and smart web applications with Symfony2
Build powerfull and smart web applications with Symfony2Hugo Hamon
 
Introduction to PowerShell
Introduction to PowerShellIntroduction to PowerShell
Introduction to PowerShellBoulos Dib
 
2019 11-bgphp
2019 11-bgphp2019 11-bgphp
2019 11-bgphpdantleech
 
How to Design a Great API (using flask) [ploneconf2017]
How to Design a Great API (using flask) [ploneconf2017]How to Design a Great API (using flask) [ploneconf2017]
How to Design a Great API (using flask) [ploneconf2017]Devon Bernard
 
Symfony finally swiped right on envvars
Symfony finally swiped right on envvarsSymfony finally swiped right on envvars
Symfony finally swiped right on envvarsSam Marley-Jarrett
 
Art of Web Backdoor - Pichaya Morimoto
Art of Web Backdoor - Pichaya MorimotoArt of Web Backdoor - Pichaya Morimoto
Art of Web Backdoor - Pichaya MorimotoPichaya Morimoto
 
Simplify your professional web development with symfony
Simplify your professional web development with symfonySimplify your professional web development with symfony
Simplify your professional web development with symfonyFrancois Zaninotto
 
Vagrant for real codemotion (moar tips! ;-))
Vagrant for real codemotion (moar tips! ;-))Vagrant for real codemotion (moar tips! ;-))
Vagrant for real codemotion (moar tips! ;-))Michele Orselli
 
Release with confidence
Release with confidenceRelease with confidence
Release with confidenceJohn Congdon
 
SymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years later
SymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years laterSymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years later
SymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years laterHaehnchen
 

Semelhante a Getting Fast Responses from Symfony with Varnish Tags (20)

Heavy Web Optimization: Backend
Heavy Web Optimization: BackendHeavy Web Optimization: Backend
Heavy Web Optimization: Backend
 
Meetup Performance
Meetup PerformanceMeetup Performance
Meetup Performance
 
Meetup Performance
Meetup PerformanceMeetup Performance
Meetup Performance
 
Exploring Async PHP (SF Live Berlin 2019)
Exploring Async PHP (SF Live Berlin 2019)Exploring Async PHP (SF Live Berlin 2019)
Exploring Async PHP (SF Live Berlin 2019)
 
Porting Rails Apps to High Availability Systems
Porting Rails Apps to High Availability SystemsPorting Rails Apps to High Availability Systems
Porting Rails Apps to High Availability Systems
 
Lean Php Presentation
Lean Php PresentationLean Php Presentation
Lean Php Presentation
 
Harmonious Development: Via Vagrant and Puppet
Harmonious Development: Via Vagrant and PuppetHarmonious Development: Via Vagrant and Puppet
Harmonious Development: Via Vagrant and Puppet
 
Rapid java backend and api development for mobile devices
Rapid java backend and api development for mobile devicesRapid java backend and api development for mobile devices
Rapid java backend and api development for mobile devices
 
Speed up your developments with Symfony2
Speed up your developments with Symfony2Speed up your developments with Symfony2
Speed up your developments with Symfony2
 
Build powerfull and smart web applications with Symfony2
Build powerfull and smart web applications with Symfony2Build powerfull and smart web applications with Symfony2
Build powerfull and smart web applications with Symfony2
 
Introduction to PowerShell
Introduction to PowerShellIntroduction to PowerShell
Introduction to PowerShell
 
Symfony2 revealed
Symfony2 revealedSymfony2 revealed
Symfony2 revealed
 
2019 11-bgphp
2019 11-bgphp2019 11-bgphp
2019 11-bgphp
 
How to Design a Great API (using flask) [ploneconf2017]
How to Design a Great API (using flask) [ploneconf2017]How to Design a Great API (using flask) [ploneconf2017]
How to Design a Great API (using flask) [ploneconf2017]
 
Symfony finally swiped right on envvars
Symfony finally swiped right on envvarsSymfony finally swiped right on envvars
Symfony finally swiped right on envvars
 
Art of Web Backdoor - Pichaya Morimoto
Art of Web Backdoor - Pichaya MorimotoArt of Web Backdoor - Pichaya Morimoto
Art of Web Backdoor - Pichaya Morimoto
 
Simplify your professional web development with symfony
Simplify your professional web development with symfonySimplify your professional web development with symfony
Simplify your professional web development with symfony
 
Vagrant for real codemotion (moar tips! ;-))
Vagrant for real codemotion (moar tips! ;-))Vagrant for real codemotion (moar tips! ;-))
Vagrant for real codemotion (moar tips! ;-))
 
Release with confidence
Release with confidenceRelease with confidence
Release with confidence
 
SymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years later
SymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years laterSymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years later
SymfonyCon Berlin 2016 - Symfony Plugin for PhpStorm - 3 years later
 

Último

MYjobs Presentation Django-based project
MYjobs Presentation Django-based projectMYjobs Presentation Django-based project
MYjobs Presentation Django-based projectAnoyGreter
 
Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024Andreas Granig
 
KnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptx
KnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptxKnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptx
KnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptxTier1 app
 
Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...
Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...
Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...Matt Ray
 
Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...
Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...
Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...Angel Borroy López
 
Powering Real-Time Decisions with Continuous Data Streams
Powering Real-Time Decisions with Continuous Data StreamsPowering Real-Time Decisions with Continuous Data Streams
Powering Real-Time Decisions with Continuous Data StreamsSafe Software
 
CRM Contender Series: HubSpot vs. Salesforce
CRM Contender Series: HubSpot vs. SalesforceCRM Contender Series: HubSpot vs. Salesforce
CRM Contender Series: HubSpot vs. SalesforceBrainSell Technologies
 
Cloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEECloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEEVICTOR MAESTRE RAMIREZ
 
Ahmed Motair CV April 2024 (Senior SW Developer)
Ahmed Motair CV April 2024 (Senior SW Developer)Ahmed Motair CV April 2024 (Senior SW Developer)
Ahmed Motair CV April 2024 (Senior SW Developer)Ahmed Mater
 
Software Coding for software engineering
Software Coding for software engineeringSoftware Coding for software engineering
Software Coding for software engineeringssuserb3a23b
 
SensoDat: Simulation-based Sensor Dataset of Self-driving Cars
SensoDat: Simulation-based Sensor Dataset of Self-driving CarsSensoDat: Simulation-based Sensor Dataset of Self-driving Cars
SensoDat: Simulation-based Sensor Dataset of Self-driving CarsChristian Birchler
 
Odoo 14 - eLearning Module In Odoo 14 Enterprise
Odoo 14 - eLearning Module In Odoo 14 EnterpriseOdoo 14 - eLearning Module In Odoo 14 Enterprise
Odoo 14 - eLearning Module In Odoo 14 Enterprisepreethippts
 
Precise and Complete Requirements? An Elusive Goal
Precise and Complete Requirements? An Elusive GoalPrecise and Complete Requirements? An Elusive Goal
Precise and Complete Requirements? An Elusive GoalLionel Briand
 
Recruitment Management Software Benefits (Infographic)
Recruitment Management Software Benefits (Infographic)Recruitment Management Software Benefits (Infographic)
Recruitment Management Software Benefits (Infographic)Hr365.us smith
 
Machine Learning Software Engineering Patterns and Their Engineering
Machine Learning Software Engineering Patterns and Their EngineeringMachine Learning Software Engineering Patterns and Their Engineering
Machine Learning Software Engineering Patterns and Their EngineeringHironori Washizaki
 
Comparing Linux OS Image Update Models - EOSS 2024.pdf
Comparing Linux OS Image Update Models - EOSS 2024.pdfComparing Linux OS Image Update Models - EOSS 2024.pdf
Comparing Linux OS Image Update Models - EOSS 2024.pdfDrew Moseley
 
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样umasea
 
What is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need ItWhat is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need ItWave PLM
 
英国UN学位证,北安普顿大学毕业证书1:1制作
英国UN学位证,北安普顿大学毕业证书1:1制作英国UN学位证,北安普顿大学毕业证书1:1制作
英国UN学位证,北安普顿大学毕业证书1:1制作qr0udbr0
 

Último (20)

MYjobs Presentation Django-based project
MYjobs Presentation Django-based projectMYjobs Presentation Django-based project
MYjobs Presentation Django-based project
 
Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024Automate your Kamailio Test Calls - Kamailio World 2024
Automate your Kamailio Test Calls - Kamailio World 2024
 
KnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptx
KnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptxKnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptx
KnowAPIs-UnknownPerf-jaxMainz-2024 (1).pptx
 
Odoo Development Company in India | Devintelle Consulting Service
Odoo Development Company in India | Devintelle Consulting ServiceOdoo Development Company in India | Devintelle Consulting Service
Odoo Development Company in India | Devintelle Consulting Service
 
Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...
Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...
Open Source Summit NA 2024: Open Source Cloud Costs - OpenCost's Impact on En...
 
Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...
Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...
Alfresco TTL#157 - Troubleshooting Made Easy: Deciphering Alfresco mTLS Confi...
 
Powering Real-Time Decisions with Continuous Data Streams
Powering Real-Time Decisions with Continuous Data StreamsPowering Real-Time Decisions with Continuous Data Streams
Powering Real-Time Decisions with Continuous Data Streams
 
CRM Contender Series: HubSpot vs. Salesforce
CRM Contender Series: HubSpot vs. SalesforceCRM Contender Series: HubSpot vs. Salesforce
CRM Contender Series: HubSpot vs. Salesforce
 
Cloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEECloud Data Center Network Construction - IEEE
Cloud Data Center Network Construction - IEEE
 
Ahmed Motair CV April 2024 (Senior SW Developer)
Ahmed Motair CV April 2024 (Senior SW Developer)Ahmed Motair CV April 2024 (Senior SW Developer)
Ahmed Motair CV April 2024 (Senior SW Developer)
 
Software Coding for software engineering
Software Coding for software engineeringSoftware Coding for software engineering
Software Coding for software engineering
 
SensoDat: Simulation-based Sensor Dataset of Self-driving Cars
SensoDat: Simulation-based Sensor Dataset of Self-driving CarsSensoDat: Simulation-based Sensor Dataset of Self-driving Cars
SensoDat: Simulation-based Sensor Dataset of Self-driving Cars
 
Odoo 14 - eLearning Module In Odoo 14 Enterprise
Odoo 14 - eLearning Module In Odoo 14 EnterpriseOdoo 14 - eLearning Module In Odoo 14 Enterprise
Odoo 14 - eLearning Module In Odoo 14 Enterprise
 
Precise and Complete Requirements? An Elusive Goal
Precise and Complete Requirements? An Elusive GoalPrecise and Complete Requirements? An Elusive Goal
Precise and Complete Requirements? An Elusive Goal
 
Recruitment Management Software Benefits (Infographic)
Recruitment Management Software Benefits (Infographic)Recruitment Management Software Benefits (Infographic)
Recruitment Management Software Benefits (Infographic)
 
Machine Learning Software Engineering Patterns and Their Engineering
Machine Learning Software Engineering Patterns and Their EngineeringMachine Learning Software Engineering Patterns and Their Engineering
Machine Learning Software Engineering Patterns and Their Engineering
 
Comparing Linux OS Image Update Models - EOSS 2024.pdf
Comparing Linux OS Image Update Models - EOSS 2024.pdfComparing Linux OS Image Update Models - EOSS 2024.pdf
Comparing Linux OS Image Update Models - EOSS 2024.pdf
 
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
办理学位证(UQ文凭证书)昆士兰大学毕业证成绩单原版一模一样
 
What is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need ItWhat is Fashion PLM and Why Do You Need It
What is Fashion PLM and Why Do You Need It
 
英国UN学位证,北安普顿大学毕业证书1:1制作
英国UN学位证,北安普顿大学毕业证书1:1制作英国UN学位证,北安普顿大学毕业证书1:1制作
英国UN学位证,北安普顿大学毕业证书1:1制作
 

Getting Fast Responses from Symfony with Varnish Tags

  • 1. Going to production on a Raspberry Pi with varnish tags
  • 2. Who am I? Jérémy DERUSSÉ Web Technical Leader AptusHealth @jderusse
  • 3. How to get fast responses from a Symfony application? you can't
  • 4. How to get fast responses from a Symfony application?your backend you can't
  • 5. Solution using http shared cache describe in RFC-2616 RFC-7234
  • 6. Integration in Symfony use SensioBundleFrameworkExtraBundleConfigurationCache; /** * @Cache(smaxage="3600") */ public function indexAction() { // ... } Advanced usage with FriendsOfSymfony/FOSHttpCacheBundle
  • 7. Issue #1 Unsharable resources private resources (ie. invoice, shopping cart, ...) per role representations Solution vary cache on user/role/other see SfLive 2015 Jérôme Vieilledent & David Buchmann Repousser les limites : HTTP cache et utilisateurs connectés
  • 8. Issue #2 Cache invalidation “ There are only two hard things in Computer Science: cache invalidation and naming things. Phil Karlton
  • 9. Cache models Validation model etag last-modified drawbacks application is booted hard to implement Expiration model expires cache-control drawback no control on invalidation
  • 10. cache model In a real world Backend can't validate every cache HIT Life time is not predictable BUT Varnish can be requested to partially invalidate responses Backend knows when resources change Responses are build on top of resources
  • 11. curl -I "http://varnish.myapp.com/c" curl -I "http://varnish.myapp.com/b" curl -I "http://varnish.myapp.com/a" HTTP/1.1 200 OK Cache-Control: public, s-maxage=3600 X-Cache-Tags: Foo,Bar HTTP/1.1 200 OK Cache-Control: public, s-maxage=3600 X-Cache-Tags: Foo Varnish tags curl -X "BAN" -H "X-Cache-Tags: Foo" "http://varnish.myapp.com" HTTP/1.1 200 OK Cache-Control: public, s-maxage=3600 X-Cache-Tags: Bar,Qux
  • 12. Varnish tags curl "http://varnish.myapp.com/posts/42" HTTP/1.1 200 OK Cache-Control: public, s-maxage=86400 X-Cache-Tags: Post:42,Author:12,Comment:314,Comment:1337 { "id": 42, "title": "My blog post.", "body": "Lorem Ipsum.", "author": { "id": 12, "username": "jderusse" }, "comments": [ { "id": 314, "message": "Wow such post" }, { "id": 1337, "message": "much performance" } ] }
  • 13. Automate Tagging Tagging Response 1. Collect displayed resources 2. Generate resource identifier 3. Tag response
  • 14. Automate Tagging Tagging Response - 1. Collect displayed resources namespace AppEventListener; use JMSSerializerEventDispatcherEvents; use JMSSerializerEventDispatcherEventSubscriberInterface; use JMSSerializerEventDispatcherObjectEvent; class SerializationTagListener implements EventSubscriberInterface { public function onPostSerialize(ObjectEvent $event) { $resource = $event->getObject(); // TODO } public static function getSubscribedEvents() { return [ [ 'event' => Events::POST_SERIALIZE, 'format' => 'json', 'method' => 'onPostSerialize', ], ]; } }
  • 15. Automate Tagging Tagging Response - 2. Generate resource identifier namespace AppEventListener; use AppTagTagExtractorInterface; use FOSHttpCacheBundleHandlerTagHandler; use JMSSerializerEventDispatcherEventSubscriberInterface; use JMSSerializerEventDispatcherObjectEvent; class SerializationTagListener implements EventSubscriberInterface { private $tagExtractor; public function __construct(TagExtractorInterface $tagExtractor) { $this->tagExtractor = $tagExtractor; } public function onPostSerialize(ObjectEvent $event): void { //... $tags = $this->tagExtractor->extract($event->getObject()); } //... }
  • 16. Automate Tagging Tagging Response - 3. Tag response namespace AppEventListener; use AppTagTagExtractorInterface; use FOSHttpCacheBundleHandlerTagHandler; use JMSSerializerEventDispatcherEventSubscriberInterface; use JMSSerializerEventDispatcherObjectEvent; class SerializationTagListener implements EventSubscriberInterface { private $tagExtractor; private $tagHandler; public function __construct(TagExtractorInterface $tagExtractor, TagHandler $tagHandler) { $this->tagExtractor = $tagExtractor; $this->tagHandler = $tagHandler; } public function onPostSerialize(ObjectEvent $event): void { $tags = $this->tagExtractor->extract($event->getObject()); $this->tagHandler->addTags($tags); } //... }
  • 17. Automate Tagging Tagging Response 1. Collect displayed resources 2. Generate resource identifier 3. Tag response Invalidate cache 1. Listen changes 2. Generate resource identifier 3. Call varnish
  • 18. Automate Tagging Invalidate Cache - 1. Listen changes namespace AppEventListener; use DoctrineCommonEventSubscriber; use DoctrineORMEventOnFlushEventArgs; use DoctrineORMEvents; class DoctrineInvalidationTagListener implements EventSubscriber { public function getSubscribedEvents() { return [Events::onFlush]; } public function onFlush(OnFlushEventArgs $eventArgs) { $uow = $eventArgs->getEntityManager()->getUnitOfWork(); foreach ($uow->getScheduledEntityUpdates() as $resource) { // TODO } foreach ($uow->getScheduledEntityDeletions() as $resource) { // TODO } } }
  • 19. Automate Tagging Invalidate Cache - 2. Generate resource identifier namespace AppEventListener; use AppTagTagExtractorInterface; use DoctrineCommonEventSubscriber; class DoctrineInvalidationTagListener implements EventSubscriber { private $tagExtractor; public function __construct(TagExtractorInterface $tagExtractor) { $this->tagExtractor = $tagExtractor; } public function onFlush(OnFlushEventArgs $eventArgs) { $uow = $eventArgs->getEntityManager()->getUnitOfWork(); $tags = []; foreach ($uow->getScheduledEntityUpdates() as $resource) { $tags = array_merge($tags, $this->tagExtractor->extract($resource)); } foreach ($uow->getScheduledEntityDeletions() as $resource) { $tags = array_merge($tags, $this->tagExtractor->extract($resource)); } // TODO } }
  • 20. Automate Tagging Invalidate Cache - 3. Call varnish namespace AppEventListener; use AppTagTagExtractorInterface; use DoctrineCommonEventSubscriber; use FOSHttpCacheHandlerTagHandler; class DoctrineInvalidationTagListener implements EventSubscriber { private $tagExtractor; public function __construct(TagExtractorInterface $tagExtractor, TagHandler $tagHandler) { $this->tagExtractor = $tagExtractor; $this->tagHandler = $tagHandler; } public function onFlush(OnFlushEventArgs $eventArgs) { // ... $this->tagHandler->invalidateTags($tags); } }
  • 21. Automate Tagging Tagging Response 1. Collect displayed resources 2. Generate resource identifier 3. Tag response Invalidate cache 1. Listen changes 2. Generate resource identifier 3. Call varnish Enjoy
  • 22. Silver bullet? Works well when HIT >> MISS Read >> Write Application knows resources used to build response Drawback Operations are not Atomic Backend handles writes Backend knows infrastructure It slows writes
  • 24. Demo Hardware Raspberry Pi Orange Pi docker MySQL NGINX PHP7-FPM Varnish $9.59
  • 25. Demo
  • 26. ab -n 8000 -c 26 192.168.1.17:81/comments/1 This is ApacheBench, Version 2.3 <$Revision: 1757674 $> Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net Licensed to The Apache Software Foundation, http://www.apache.org/ Server Software: nginx/1.10.3 Server Hostname: 192.168.1.16 Server Port: 80 Document Path: /comments/1 Document Length: 576 bytes Concurrency Level: 26 Time taken for tests: 26.912 seconds Complete requests: 200 Failed requests: 0 Total transferred: 193400 bytes HTML transferred: 115200 bytes Requests per second: 7.43 [#/sec] (mean) Time per request: 3498.553 [ms] (mean) Time per request: 134.560 [ms] (mean, across all concurrent Transfer rate: 7.02 [Kbytes/sec] received Connection Times (ms) min mean[+/-sd] median max Connect: 1 2 1.4 1 6 Processing: 546 3342 1156.7 3020 7204 Waiting: 546 3342 1156.7 3020 7204 Total: 550 3344 1156.5 3021 7205 in numbers ab -n 8000 -c 26 192.168.1.17/comments/1 This is ApacheBench, Version 2.3 <$Revision: 1757674 $> Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net Licensed to The Apache Software Foundation, http://www.apache.org/ Server Software: nginx/1.10.3 Server Hostname: 192.168.1.17 Server Port: 80 Document Path: /comments/1 Document Length: 576 bytes Concurrency Level: 26 Time taken for tests: 2.340 seconds Complete requests: 8000 Failed requests: 0 Total transferred: 8948504 bytes HTML transferred: 4608000 bytes Requests per second: 3418.52 [#/sec] (mean) Time per request: 7.606 [ms] (mean) Time per request: 0.293 [ms] (mean, across all concurrent Transfer rate: 3734.21 [Kbytes/sec] received Connection Times (ms) min mean[+/-sd] median max Connect: 0 2 0.8 2 7 Processing: 2 5 3.3 5 55 Waiting: 2 5 3.3 4 55 Total: 2 8 3.3 7 56 app varnish