Single Page Apps with
Drupal 8
Chris Tankersley
php[world] 2015
php[world] 2015 1
Who Am I
• PHP Programmer for over 10 years
• Drupal developer for 5 years
• Maintainer of Social Media Bar
• Reigning, Defending, PHP Magic the
Gathering Champion
• https://github.com/dragonmantank
php[world] 2015 2
What is a Single Page Application?
• An application that loads itself in in a single page
php[world] 2015 3
What is a Single Page Application?
• Loads all the necessary HTML, CSS, and JS needed in a single page
load
• Loads all the necessary HTML, CSS, and JS needed to bootstrap an
application in a single page load
php[world] 2015 4
Traditional Application Workflow
php[world] 2015 5
Browser Server
User requests a page
Server returns a response
1) Server gets the request
2) Server calls PHP
3) PHP builds the HTML
Browser Server
User requests a page
Server returns a response
1) Server gets the request
2) Server calls PHP
3) PHP builds the HTML
Single Page Application workflow
php[world] 2015 6
Browser Server
User requests a page
Server returns a response
1) Server gets the request
2) Server returns base HTML
Browser requests data
Server returns a response
1) Server gets the request
2) Server calls PHP
3) PHP returns JSON
Browser requests data
Server returns a response
1) Server gets the request
2) Server calls PHP
3) PHP returns JSON
…
SPAs are great!
• Reduce server load
• More responsive
• Separates the server and the front end
• Make the front end people do all the work
php[world] 2015 7
SPA ALL THE THINGS!
php[world] 2015 8
php[world] 2015 9
It’s not all great
• Users have to have JS enabled
• SEO SUUUUUUUUUUUUUUCKS
• This will probably break navigation
• This will probably break your analytics
• Your host might not support it
php[world] 2015 10
Why do you want a Single Page
Application?
php[world] 2015 11
Create an SPA if…
• You want a more desktop-like experience
• A lot of data is coming and going
• You want/have a good API backend
• The interface lends itself to being an SPA
php[world] 2015 12
GMail makes sense
php[world] 2015 13
http://3.bp.blogspot.com/-y96KrBvSbuQ/Tgu5oLmVZyI/AAAAAAAAAKE/EFkwE1ZIic8/s1600/threadlist-large.png
My blog doesn’t
php[world] 2015 14
Don’t create an SPA if…
• You just want to reduce page refreshes
• You think it sounds cool
php[world] 2015 15
tl;dr: Only create an SPA if it makes sense
php[world] 2015 16
Parts of a Single Page Application
php[world] 2015 17
The knee bone is connected to…
• Controllers
• Chunks and Templates
• Routing
• Data
• Data Transport
php[world] 2015 18
Controllers
php[world] 2015 19
https://en.wikipedia.org/wiki/Game_controller#/media/File:SNES-Controller.jpg
The logic of our application
php[world] 2015 20
function node_page_default() {
$select = db_select('node', 'n')
->fields('n', array('nid', 'sticky', 'created'))
->condition('n.promote', 1)
->condition('n.status', 1)
->orderBy('n.sticky', 'DESC')
->orderBy('n.created', 'DESC')
->extend('PagerDefault')
->limit(variable_get('default_nodes_main', 10))
->addTag('node_access');
$nids = $select->execute()->fetchCol();
if (!empty($nids)) {
$nodes = node_load_multiple($nids);
$build = node_view_multiple($nodes);
Chunks and Templates
php[world] 2015 21
<?php print render($page['header']); ?>
<div id="wrapper">
<div id="container" class="clearfix">
<div id="header">
<div id="logo-floater">
<?php if ($logo || $site_title): ?>
<?php if ($title): ?>
<div id="branding"><strong><a href="<?php print $front_page ?>">
<?php if ($logo): ?>
<img src="<?php print $logo ?>" alt="<?php print
$site_name_and_slogan ?>" title="<?php print $site_name_and_slogan ?>" id="logo"
/>
<?php endif; ?>
<?php print $site_html ?>
Routing
php[world] 2015 22
function hook_menu() {
$items['example'] = array(
'title' => 'Example Page',
'page callback' => 'example_page',
'access arguments' => array('access content'),
'type' => MENU_SUGGESTED_ITEM,
);
$items['example/feed'] = array(
'title' => 'Example RSS feed',
'page callback' => 'example_feed',
'access arguments' => array('access content'),
'type' => MENU_CALLBACK,
);
return $items;
}
Data
php[world] 2015 23
function node_schema() {
$schema['node'] = array(
'description' => 'The base table for nodes.',
'fields' => array(
'nid' => array(
'description' => 'The primary identifier for a node.',
'type' => 'serial',
'unsigned' => TRUE,
'not null' => TRUE,
),
// Defaults to NULL in order to avoid a brief period of potential
// deadlocks on the index.
'vid' => array(
'description' => 'The current {node_revision}.vid version identifier.',
'type' => 'int’,
Data Transport
• AJAX
• AJAJ
• AJAH
php[world] 2015 24
Sample SPA Application
DEMO TIME!
php[world] 2015 25
Picking a JavaScript Framework
php[world] 2015 26
Backbone
php[world] 2015 27
EmberJS
php[world] 2015 28
AngularJS
php[world] 2015 29
Getting Drupal 8 to work with Single Page
Applications
php[world] 2015 30
Turn on the Modules
php[world] 2015 31
Set the Permissions
php[world] 2015 32
Rest UI
php[world] 2015 33
Creating New Endpoints with Views
php[world] 2015 34
Setting Accept Types
php[world] 2015 35
Stop!
Demo Time!
php[world] 2015 36
Notes for working with the REST API
• No more headers. It’s all through ?_format=*
• You have to know all your base routes
• Use hal_json as a format to make finding links easier
php[world] 2015 37
Why HAL?
• Open spec for describing generic REST resources
• Supports XML and JSON
• Exposes useful links to other bits of resources you might need
• http://phlyrestfully.readthedocs.org/en/latest/halprimer.html
php[world] 2015 38
Getting it into your Drupal site
php[world] 2015 39
Use a .html file
• Really easy to do
• Doesn’t impact your existing site
php[world] 2015 40
Add it to a template
• Start small
php[world] 2015 41
Just make a small module
• Gives you more control
php[world] 2015 42
Questions?
php[world] 2015 43
Thank You!
http://ctankersley.com
chris@ctankersley.com
@dragonmantank
https://joind.in/14801
php[world] 2015 44

Single Page Apps with Drupal 8

  • 1.
    Single Page Appswith Drupal 8 Chris Tankersley php[world] 2015 php[world] 2015 1
  • 2.
    Who Am I •PHP Programmer for over 10 years • Drupal developer for 5 years • Maintainer of Social Media Bar • Reigning, Defending, PHP Magic the Gathering Champion • https://github.com/dragonmantank php[world] 2015 2
  • 3.
    What is aSingle Page Application? • An application that loads itself in in a single page php[world] 2015 3
  • 4.
    What is aSingle Page Application? • Loads all the necessary HTML, CSS, and JS needed in a single page load • Loads all the necessary HTML, CSS, and JS needed to bootstrap an application in a single page load php[world] 2015 4
  • 5.
    Traditional Application Workflow php[world]2015 5 Browser Server User requests a page Server returns a response 1) Server gets the request 2) Server calls PHP 3) PHP builds the HTML Browser Server User requests a page Server returns a response 1) Server gets the request 2) Server calls PHP 3) PHP builds the HTML
  • 6.
    Single Page Applicationworkflow php[world] 2015 6 Browser Server User requests a page Server returns a response 1) Server gets the request 2) Server returns base HTML Browser requests data Server returns a response 1) Server gets the request 2) Server calls PHP 3) PHP returns JSON Browser requests data Server returns a response 1) Server gets the request 2) Server calls PHP 3) PHP returns JSON …
  • 7.
    SPAs are great! •Reduce server load • More responsive • Separates the server and the front end • Make the front end people do all the work php[world] 2015 7
  • 8.
    SPA ALL THETHINGS! php[world] 2015 8
  • 9.
  • 10.
    It’s not allgreat • Users have to have JS enabled • SEO SUUUUUUUUUUUUUUCKS • This will probably break navigation • This will probably break your analytics • Your host might not support it php[world] 2015 10
  • 11.
    Why do youwant a Single Page Application? php[world] 2015 11
  • 12.
    Create an SPAif… • You want a more desktop-like experience • A lot of data is coming and going • You want/have a good API backend • The interface lends itself to being an SPA php[world] 2015 12
  • 13.
    GMail makes sense php[world]2015 13 http://3.bp.blogspot.com/-y96KrBvSbuQ/Tgu5oLmVZyI/AAAAAAAAAKE/EFkwE1ZIic8/s1600/threadlist-large.png
  • 14.
  • 15.
    Don’t create anSPA if… • You just want to reduce page refreshes • You think it sounds cool php[world] 2015 15
  • 16.
    tl;dr: Only createan SPA if it makes sense php[world] 2015 16
  • 17.
    Parts of aSingle Page Application php[world] 2015 17
  • 18.
    The knee boneis connected to… • Controllers • Chunks and Templates • Routing • Data • Data Transport php[world] 2015 18
  • 19.
  • 20.
    The logic ofour application php[world] 2015 20 function node_page_default() { $select = db_select('node', 'n') ->fields('n', array('nid', 'sticky', 'created')) ->condition('n.promote', 1) ->condition('n.status', 1) ->orderBy('n.sticky', 'DESC') ->orderBy('n.created', 'DESC') ->extend('PagerDefault') ->limit(variable_get('default_nodes_main', 10)) ->addTag('node_access'); $nids = $select->execute()->fetchCol(); if (!empty($nids)) { $nodes = node_load_multiple($nids); $build = node_view_multiple($nodes);
  • 21.
    Chunks and Templates php[world]2015 21 <?php print render($page['header']); ?> <div id="wrapper"> <div id="container" class="clearfix"> <div id="header"> <div id="logo-floater"> <?php if ($logo || $site_title): ?> <?php if ($title): ?> <div id="branding"><strong><a href="<?php print $front_page ?>"> <?php if ($logo): ?> <img src="<?php print $logo ?>" alt="<?php print $site_name_and_slogan ?>" title="<?php print $site_name_and_slogan ?>" id="logo" /> <?php endif; ?> <?php print $site_html ?>
  • 22.
    Routing php[world] 2015 22 functionhook_menu() { $items['example'] = array( 'title' => 'Example Page', 'page callback' => 'example_page', 'access arguments' => array('access content'), 'type' => MENU_SUGGESTED_ITEM, ); $items['example/feed'] = array( 'title' => 'Example RSS feed', 'page callback' => 'example_feed', 'access arguments' => array('access content'), 'type' => MENU_CALLBACK, ); return $items; }
  • 23.
    Data php[world] 2015 23 functionnode_schema() { $schema['node'] = array( 'description' => 'The base table for nodes.', 'fields' => array( 'nid' => array( 'description' => 'The primary identifier for a node.', 'type' => 'serial', 'unsigned' => TRUE, 'not null' => TRUE, ), // Defaults to NULL in order to avoid a brief period of potential // deadlocks on the index. 'vid' => array( 'description' => 'The current {node_revision}.vid version identifier.', 'type' => 'int’,
  • 24.
    Data Transport • AJAX •AJAJ • AJAH php[world] 2015 24
  • 25.
    Sample SPA Application DEMOTIME! php[world] 2015 25
  • 26.
    Picking a JavaScriptFramework php[world] 2015 26
  • 27.
  • 28.
  • 29.
  • 30.
    Getting Drupal 8to work with Single Page Applications php[world] 2015 30
  • 31.
    Turn on theModules php[world] 2015 31
  • 32.
  • 33.
  • 34.
    Creating New Endpointswith Views php[world] 2015 34
  • 35.
  • 36.
  • 37.
    Notes for workingwith the REST API • No more headers. It’s all through ?_format=* • You have to know all your base routes • Use hal_json as a format to make finding links easier php[world] 2015 37
  • 38.
    Why HAL? • Openspec for describing generic REST resources • Supports XML and JSON • Exposes useful links to other bits of resources you might need • http://phlyrestfully.readthedocs.org/en/latest/halprimer.html php[world] 2015 38
  • 39.
    Getting it intoyour Drupal site php[world] 2015 39
  • 40.
    Use a .htmlfile • Really easy to do • Doesn’t impact your existing site php[world] 2015 40
  • 41.
    Add it toa template • Start small php[world] 2015 41
  • 42.
    Just make asmall module • Gives you more control php[world] 2015 42
  • 43.
  • 44.