www.drupaleurope.org Building high-performance Thunder sites by - - PowerPoint PPT Presentation

drupaleurope org building high performance thunder sites
SMART_READER_LITE
LIVE PREVIEW

www.drupaleurope.org Building high-performance Thunder sites by - - PowerPoint PPT Presentation

www.drupaleurope.org Building high-performance Thunder sites by Wolfgang Ziegler Wolfgang Ziegler img CEO/CTO drunomics GmbH @the_real_fago Typed data API maintainer, past Form API & Entty API Creator of many modules like Rules,


slide-1
SLIDE 1

www.drupaleurope.org

slide-2
SLIDE 2

Building high-performance Thunder sites

by Wolfgang Ziegler

slide-3
SLIDE 3

Wolfgang Ziegler

CEO/CTO drunomics GmbH @the_real_fago

img

  • Typed data API maintainer,

past Form API & Entty API

  • Creator of many modules like

Rules, Entty API, Field collecton, …

  • Track chair Drupal + Technology
slide-4
SLIDE 4

B a c k g r

  • u

n d

  • Thunder-based mult-site project
  • Typical publishing project:

Editors publish content (artcles, recipes, …)

Paragraphs, Media, Related content, Listngs, Mega-Menu, Search with autocompleton and facets

  • With interactve elements:

Votng, Comments

slide-5
SLIDE 5

G

  • a

l s

  • Fast responses for logged-out site visitors via cached pages
  • Long-lived caches by default

Keep some caches when nodes are edited

Allow editors to purge cache per page

  • Good (cached) performance & UX for logged-in users

(commentng, votes)

  • Reasonable performance for uncached responses
slide-6
SLIDE 6

Architecture

slide-7
SLIDE 7

F a s t , c a c h e d p a g e l

  • a

d s !

  • CDN (Cloudfare) → Varnish → Drupal (Page cache)
  • Ensure cached responses → Warm caches afer editng
  • Enhance cached pages via Javascript
slide-8
SLIDE 8

U n c a c h e d p a g e r e n d e r p e r f

  • r

m a n c e ?

  • Without caches, rendering easily can get slow
  • Can decoupling help us to obtain beter performance?

→ Evaluate performance of two possible architectures:

Traditonal approach

Decoupled approach

slide-9
SLIDE 9

D e c

  • u

p l e d a r c h i t e c t u r e

  • SSR for SEO and fast page loads
  • Nuxt.js (Ready-to-go universal Vue.js)
  • Backend:

Drupal + JSON API + Subrequests module

slide-10
SLIDE 10

A p r

  • t
  • t

y p e f

  • r

c

  • m

p a r i s

  • n
  • Contenta CMS example
  • Recipe page

Main recipe node

4 related repices by category

A main menu block

slide-11
SLIDE 11

P r

  • t
  • t

y p e s : D e c

  • u

p l e d v s . T r a d i t i

  • n

a l

  • Decoupled:

Nuxt/vue.js example

Improved with Subrequests Main-Menu added as subrequest

  • Contenta CMS frontend (material theme) of a recipe page

("node view page"), unstyled.

slide-12
SLIDE 12

S i m p l e b e n c h m a r k

  • Non-scientfc approach on notebook
  • Measure page generaton tme in multple scenarios
  • Repeated each scenarios multple tmes, take best result
  • Goal: Get an idea on performance diferences
slide-13
SLIDE 13

C

  • m

p a r i s

  • n

r e s u l t s : C a c h e d r e s p

  • n

s e

Request tme [ms]

5 10 15 20 25 30 35 40

Traditonal Decoupled → Decoupled system stll renders, Drupal not.

slide-14
SLIDE 14

C

  • m

p a r i s

  • n

r e s u l t s : Wa r m e d s i t e , n

  • p

a g e

  • c

a c h e

Request tme [ms]

100 200 300 400 500 600

Traditonal Decoupled → API requests are all uncached, Drupal has internal caches.

slide-15
SLIDE 15

C

  • m

p a r i s

  • n

r e s u l t s : A f t e r e d i t i n g t h e p a g e

Request tme [ms]

50 100 150 200 250 300 350 400 450

Traditonal Decoupled → Drupal invalidates render cache

slide-16
SLIDE 16

C

  • m

p a r i s

  • n

r e s u l t s : A f t e r e d i t i n g , l

  • a

d i n g a n

  • t

h e r p a g e

Request tme [ms]

50 100 150 200 250

Traditonal Decoupled → Decoupled can keep page caches, Drupal not.

slide-17
SLIDE 17

C

  • m

p a r i s

  • n

: R e n d e r i n g p a r t i a l l y c a c h e d p a g e s

Request tme [ms]

10 20 30 40 50 60 70 80 90 100

Traditonal with render cache dynamic page cache Decoupled with page cache → Decoupled is fasted when combining cached chunks

slide-18
SLIDE 18

P e r f

  • r

m a n c e c

  • m

p a r i s

  • n

t a k e a w a y s

  • Vue.js is faster rendering cached responses than Drupal

delivering cached elements

  • Unoptmized JSON API requests are rather slow with

embedded enttes (~200ms)

JSON API without embedded enttes ~70ms

comparable request including embedded enttes with Views REST plugin: ~110ms → Optmizaton needed

slide-19
SLIDE 19

T r a d i t i

  • n

a l v s d e c

  • u

p l e d

  • Decoupled setup misses cache of rendered pages
  • Decoupled setup has performance advantages due to beter re-

use of partally cached pages, but..

performance gains are not huge compared to dynamic page cache

decoupled system requires more complex hostng & development

  • Young projects pose a maintenance risk, future updates?

→ Go with traditonal approach & use dynamic page cache!

slide-20
SLIDE 20

Caching with Drupal

slide-21
SLIDE 21

T h e f

  • u

n d a t i

  • n

: D r u p a l c a c h e m e t a d a t a

  • Everywhere in the APIs
  • Every rendered element provides it
  • Metadata is aggregated during rendering
  • Cache metadata:

Cache context (by-user, by-path, …)

Cache tags (“dependencies” - invalidate when X changes)

Max-Age – 0 (no-cache), permanent

slide-22
SLIDE 22

C a c h e d p a g e s i n D r u p a l

  • (Internal) Page cache: ~20ms
  • Dynamic page cache: ~80ms
  • Render cache

Typically blocks & rendered enttes (view-modes)

slide-23
SLIDE 23

I n t e r n a l p a g e c a c h e

  • Keeps an internal copy of cached pages (afer CDN, Varnish)
  • Defaults to database backend, pluggable
  • Invalidated based upon cache tags

Possible with CDNs – but not on cheap plans

Possible with Varnish – but not yet stable

Risk of too frequent updates & bad cache usage

→ Need to avoid high-frequent cache invalidaton

slide-24
SLIDE 24

I n t e r n a l p a g e c a c h e : K e e p i t !

  • Customize it to cache 7 days / 1h depending on page
  • Do not invalidate automatcally

except node/{ id }

  • → Module: drupal.org/project/preserve_page_cache
  • Custom purger for editors to invalidate by URL

Invalidates page cache, varnish, CDN

  • Database based for storage
slide-25
SLIDE 25

Wa r m c a c h e s a f t e r e d i t i n g

  • drupal.org/project/prefetcher
  • Run regularly on cron to warm caches
  • Keeps track of pages and their cache lifetme
  • Warms a certain number of pages per run
slide-26
SLIDE 26

D y n a m i c p a g e c a c h e

  • Caches authentcated + anonymous pages
  • Caches pages minus personalized parts

lazy-builders render un-cached bits

  • Auto-placeholdering auto-creates lazy-builders for high-

cardinality cache-contexts

user, session

slide-27
SLIDE 27

A u t

  • m

a t i c p l a c e h

  • l

d e r i n g

  • Confgurable via service parameter in services.yml
  • Dynamic page cache only applies to elements which are

excluded by this confguraton!

renderer.config auto_placeholder_conditionsg max-aieg 0 contextsg ['session', 'user'] taisg []

slide-28
SLIDE 28

D y n a m i c p a g e c a c h e – R

  • m

f

  • r

i m p r

  • v

e m e n t

  • If auto-placeholdering fails, dynamic page cache fails!
  • And it happened all the tme for editors!

#2949457: Toolbar's renderPlain() is incompatble with dynamic page cache [needs review]

#2899392: user_hook_toolbar() makes all pages uncacheable [done, 8.5]

#2914110: Shortcut hook_toolbar implementaton makes all pages uncacheable [needs work]

  • Can happen when adding features → Add tests!
slide-29
SLIDE 29

D y n a m i c p a g e c a c h e – R

  • m

f

  • r

i m p r

  • v

e m e n t s ( 2 )

  • Automatc per-permission-hash cache context

Helps preventng permission issues

But – it’s bad for cache-reuse across roles

Doubles page cache of anonymous pages

  • Idea:

Remove permission cache-context (& take care!) → Beter cache-usage → Anonymous page loads warms cache for authentcated pages

slide-30
SLIDE 30

R e n d e r c a c h e

  • Typically blocks & rendered enttes (view-modes)
  • Mostly

Dynamic page cache is already by URL

Render cache elements duplicate dynamic page cache!

  • Stll it’s useful

For lazy-built elements

For speeding up “uncached” page generaton tme

slide-31
SLIDE 31

R e n d e r c a c h e : T u n e i t !

  • Ofen many, many items end up in the cache

Per user, per URL (query), per role

Usually does not ft into memcache/Redis

Since 8.4.x – limited to 5.000 items in database → See htps:/ /www.drupal.org/node/2891281

→ Inspect your cache items → Disable unwanted items via d.o./project/cache_split → Remove all per-URL caches

slide-32
SLIDE 32

C a c h e i n v a l i d a t i

  • n

v i a c a c h e t a g s

  • Drupal’s cache metadata is a sensible default
  • But the default is ofen to generic

list_node, list_taxonomy

  • Every page depends on list_node

→ every edit, invalidates dynamic page cache of every page!

slide-33
SLIDE 33

C u s t

  • m

i z e c a c h e m e t a d a t a

  • n

r e n d e r e d e l e m e n t s

  • Remove too generic cache tags (list_node) & context
  • Add new cache tags ftng to use-cases

node.feld_channel

  • cache_tools – Sanitze cache metadata of blocks & Views

Strip cache contexts (route, url.query_args)

  • htps:/

/www.drupal.org/project/cache_tools

slide-34
SLIDE 34

T e s t c

  • v

e r a g e f

  • r

c a c h e m e t a d a t a !

  • Actvate X-Drupal-Cache-Contexts for testng
  • Add a test per page to verify cache metadata

Test unwanted tags, context are not set

Test changes appear as required

  • Module “region_renderer” to render regions and test output

drupal.org/project/region_renderer

Take care of headers and footer to be cached!

Avoid useless cache context like url, route.menu_actve_trails

slide-35
SLIDE 35

Per-user pages & caching

slide-36
SLIDE 36

G

  • a

l : L e v e r a g e c a c h e s a s f a r a s p

  • s

s i b l e

  • Pages are mostly same for all users
  • Some elements (votng, comments, …) difer

→ Fetch cached pages & adapt! → Use Javascript to enhance cached responses.

slide-37
SLIDE 37

H

  • w

t

  • f

e t c h u s e r

  • d

e p e n d e n t e l e m e n t s ?

  • Leverage BigPipe & streamed responses
  • Lazy-load content via ajax requests
slide-38
SLIDE 38

B i g P i p e – T h e s

  • l

u t i

  • n

?

  • Drupal delivers the cached response frst
  • HTTP response is streamed
  • Lazy-builders render the rest & replace the elements in the

dom

slide-39
SLIDE 39

P r

  • b

l e m s w i t h B i g P i p e

  • It’s hard to control what’s streamed

Cache metadata & available lazy-builders decide

Not obvious and hard to inspect why something is streamed or not

  • Frontend developers are not in control
  • Depends on jQuery
  • Does not work with externally cached pages
slide-40
SLIDE 40

L a z y

  • l
  • a

d v i a A j a x r e q u e s t s – u s e D r u p a l . a j a x ?

  • Again: Frontend developers cannot control the process
  • No caching by default (POST)
  • Ajax assets plus solves caching
  • Rather complex, hard-to introspect
slide-41
SLIDE 41

L a z y

  • l
  • a

d v i a c u s t

  • m

A j a x r e q u e s t s

  • Frontend issues custom Ajax requests as needed

→ Developers can easily improve UX

  • Backend developers provide API responses

→ Easy to control caching

  • Clear interface, easy to control & debug
slide-42
SLIDE 42

A p p l y p r

  • g

r e s s i v e d e c

  • u

p l i n g

  • Use Vue.js to render elements
  • Fetch necessary data from custom API endpoints
  • Apply custom caching to custom API endpoints that can vary

→ Faster inital render tme → Improve cache usage!

slide-43
SLIDE 43

I m p r

  • v

e c a c h e l i f e t i m e !

  • Keep main pages as long cache-able as possible
  • Identfy high-frequent changing elements that can be lazy-

loaded → Mega-Menu content (Latest artcles, …) → Comments → Social media counts, Latest prices from amazon products, ...

slide-44
SLIDE 44

Frontend performance

slide-45
SLIDE 45

F r

  • n

t e n d p r i n c i p l e s

  • Optmize on frst render tme (beter UX!)
  • Keep HTTP requests down

Inline required SVG icons, inline critcal fonts

Lazy-load images

  • Stay in control – no Drupal Javascript, Ajax, …

→ Loading animatons, ...

  • Use modern stuf: Vue.js, ES6, no jQuery

→ Leverage modern frontend toolchain (Webpack)

slide-46
SLIDE 46

O p t i m i z e f

  • r

f i r s t r e n d e r

  • Keep only critcal CSS and Javascript in main builds
  • Lazy-load additonal frontend assets when needed
  • Leverage webpack code-splitng

→ Asynchronous Vue.js components lazy-load chunks

slide-47
SLIDE 47

We b p a c k c h u n k s & c a c h i n g

  • Drupal’s JS/CSS aggregaton is great for cached pages
  • Webpack chunks bypass it
  • Situatons with cached pages requiring old chunks may arise

→ Take care to keep old chunks around → Copy chunks to Drupal’s JS and use .htaccess to fallback to deliver else missing chunks

slide-48
SLIDE 48

Performance Testing

slide-49
SLIDE 49

S i t e s p e e d . i

  • Focused on frontend performance
  • Provides docker container with chrome & frefox
  • Analyzes rendering and provides

Metrics (Backend-Time, First Visual Paint, Last Visual Change)

Suggestons for improvements (like lighthouse)

Records videos of the rendering process

Waterfall of requests

slide-50
SLIDE 50

S i t e s p e e d . i

  • i

n t e g r a t i

  • n
  • Test all page variants
  • Tested pages without page cache
  • Integrate in CI workfow to automatcally generate the

report

  • Defne performance budget

→ fail if it is not met

slide-51
SLIDE 51

E x a m p l e r e p

  • r

t

slide-52
SLIDE 52

U s e B e h a t t

  • v

e r i f y C a c h i n g r e q u i r e m e n t s

  • Add behat feature per page-type

Test cache headers (Page Cache, Dynamic Page Cache)

Test Drupal cache metadata

Ensure no jQuery is added in

  • Test header / footer region responses
  • Test cachability of API responses
slide-53
SLIDE 53

Takeaways

slide-54
SLIDE 54

T a k e a w a y

  • Caching-strategy must be planned from the beginning
  • Caching / Freshness requirements must be clear
  • Drupal has great caching optons, but it could be easier to

use

  • Improve Drupal’s cache metadata
  • Use testng to avoid accidental regressions
slide-55
SLIDE 55

T h a n k y

  • u

!

  • Questons?