Slide 1

Slide 1 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Automate Your Site's Front-End Performance Kitt Hodsden / @kitt slides here

Slide 2

Slide 2 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 2 You.

Slide 3

Slide 3 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 3 Me.

Slide 4

Slide 4 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 4

Slide 5

Slide 5 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 5 Performance is everyone’s problem.

Slide 6

Slide 6 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 6 “What does FAST even mean?”

Slide 7

Slide 7 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 7 Determine key metrics

Slide 8

Slide 8 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 8 Determine key metrics Establish a baseline

Slide 9

Slide 9 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 9 Determine key metrics Establish a baseline Make a change

Slide 10

Slide 10 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 10 Determine key metrics Establish a baseline Make a change Measure effects

Slide 11

Slide 11 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 11 Determine key metrics Establish a baseline Make a change Measure effects

Slide 12

Slide 12 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 12 Determine key metrics

Slide 13

Slide 13 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 13 40% will abandon a website that takes more than 3 seconds to load.

Slide 14

Slide 14 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 14 https://blog.kissmetrics.com/loading-time/ Not quite

Slide 15

Slide 15 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 15 https://blog.kissmetrics.com/loading-time/ Not quite

Slide 16

Slide 16 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 16 Performance Budget

Slide 17

Slide 17 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 17 http://timkadlec.com/2013/01/setting-a-performance-budget/ http://timkadlec.com/2014/11/performance-budget-metrics/ http://danielmall.com/articles/how-to-make-a-performance-budget/

Slide 18

Slide 18 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 18 http://timkadlec.com/2013/01/setting-a-performance-budget/ http://timkadlec.com/2014/11/performance-budget-metrics/ http://danielmall.com/articles/how-to-make-a-performance-budget/

Slide 19

Slide 19 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 19 http://timkadlec.com/2013/01/setting-a-performance-budget/ http://timkadlec.com/2014/11/performance-budget-metrics/ http://danielmall.com/articles/how-to-make-a-performance-budget/

Slide 20

Slide 20 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 20 https://speakerdeck.com/lara/designing-for-performance?slide=69

Slide 21

Slide 21 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 21 Determine key metrics

Slide 22

Slide 22 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 22 Establish a baseline

Slide 23

Slide 23 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 23 How fast is our site?

Slide 24

Slide 24 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 24 https://www.flickr.com/photos/28277470@N05/8613726003

Slide 25

Slide 25 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 25 No.

Slide 26

Slide 26 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 26 The simplest way?

Slide 27

Slide 27 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 27 Your browser

Slide 28

Slide 28 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 28 Firefox

Slide 29

Slide 29 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 29 Safari

Slide 30

Slide 30 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 30 IE

Slide 31

Slide 31 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 31 Chrome

Slide 32

Slide 32 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 32 Chrome

Slide 33

Slide 33 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 33 https://developer.chrome.com/devtools/docs/network#resource-network-timing

Slide 34

Slide 34 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 34

Slide 35

Slide 35 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 35

Slide 36

Slide 36 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 But… but… 36

Slide 37

Slide 37 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 My network! 37

Slide 38

Slide 38 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 My browsers! 38

Slide 39

Slide 39 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Automation! 39

Slide 40

Slide 40 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 40

Slide 41

Slide 41 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 41 http://nodejs.org/

Slide 42

Slide 42 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm 42 Node Package Manager for installing node packages

Slide 43

Slide 43 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 43

Slide 44

Slide 44 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install -g grunt-cli 44

Slide 45

Slide 45 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 45 package.json Gruntfile.js The two files grunt uses

Slide 46

Slide 46 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Just download them. https://github.com/search?q=Gruntfile.js https://github.com/kitt/grunt-perf-template 46

Slide 47

Slide 47 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 47 { "engines": { "node": ">= 0.12.0" }, "devDependencies": { "grunt": "~0.4.2", "grunt-contrib-jshint": "~0.7.2", "grunt-contrib-watch": "~0.5.3", } } This is what a package.json file looks like

Slide 48

Slide 48 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 48 { "engines": { "node": ">= 0.12.0" }, "devDependencies": { "grunt": "~0.4.2", "grunt-contrib-jshint": "~0.7.2", "grunt-contrib-watch": "~0.5.3", } } This is what a package.json file looks like

Slide 49

Slide 49 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 49 $ npm install With a package.json file, you can install the needed packages easily.

Slide 50

Slide 50 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 50 $ npm install No -g here! With a package.json file, you can install the needed packages easily.

Slide 51

Slide 51 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 51 $ ls Gemfile README.txt fonts node_modules tpl Gemfile.lock config.rb img package.json widgets Gruntfile.js css js scss

Slide 52

Slide 52 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Check dependencies into the repo? http://addyosmani.com/blog/checking-in-front-end-dependencies/ http://redotheweb.com/2013/09/12/should-you-commit-dependencies.html 52 Total sidebar on checking dependencies into the repo or not

Slide 53

Slide 53 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 53 module.exports = function(grunt) { // Project configuration. grunt.initConfig({ pkg: grunt.file.readJSON('package.json'), uglify: { options: { banner: '/*! <%= pkg.name %> <%="yyyy-mm-dd") %> */\n' }, build: { src: 'src/<%= pkg.name %>.js', dest: 'build/<%= pkg.name %>.min.js' } } }); // Load the plugin that provides the "uglify" task. grunt.loadNpmTasks('grunt-contrib-uglify'); // Default task(s). grunt.registerTask('default', ['uglify']); };

Slide 54

Slide 54 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 54 module.exports = function(grunt) { // Project configuration. grunt.initConfig({ pkg: grunt.file.readJSON('package.json'), uglify: { options: { banner: '/*! <%= pkg.name %> <%="yyyy-mm-dd") %> */\n' }, build: { src: 'src/<%= pkg.name %>.js', dest: 'build/<%= pkg.name %>.min.js' } } }); // Load the plugin that provides the "uglify" task. grunt.loadNpmTasks('grunt-contrib-uglify'); // Default task(s). grunt.registerTask('default', ['uglify']); }; A basic Gruntfile.js file

Slide 55

Slide 55 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 55 module.exports = function(grunt) { // Project configuration. grunt.initConfig({ pkg: grunt.file.readJSON('package.json'), uglify: { options: { banner: '/*! <%= pkg.name %> <%="yyyy-mm-dd") %> */\n' }, build: { src: 'src/<%= pkg.name %>.js', dest: 'build/<%= pkg.name %>.min.js' } } }); // Load the plugin that provides the "uglify" task. grunt.loadNpmTasks('grunt-contrib-uglify'); // Default task(s). grunt.registerTask('default', ['uglify']); }; A basic Gruntfile.js file

Slide 56

Slide 56 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 56 module.exports = function(grunt) { // Project configuration. grunt.initConfig({ pkg: grunt.file.readJSON('package.json'), uglify: { options: { banner: '/*! <%= pkg.name %> <%="yyyy-mm-dd") %> */\n' }, build: { src: 'src/<%= pkg.name %>.js', dest: 'build/<%= pkg.name %>.min.js' } } }); // Load the plugin that provides the "uglify" task. grunt.loadNpmTasks('grunt-contrib-uglify'); // Default task(s). grunt.registerTask('default', ['uglify']); }; A basic Gruntfile.js file

Slide 57

Slide 57 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 57 $ npm install matchdep --save-dev

Slide 58

Slide 58 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 58 ... // load all the grunt modules instead of one each line require("matchdep").filterDev("grunt-*").forEach(grunt.loadNpmTasks); grunt.registerTask('checkjs', ['jshint']); grunt.registerTask('watchjs', ['jshint', 'watch']); grunt.registerTask('gruntjs', ['jshint:gruntfile', 'watch']);

Slide 59

Slide 59 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 59

Slide 60

Slide 60 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-devperf --save-dev 60

Slide 61

Slide 61 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 61 https://github.com/macbre/phantomas

Slide 62

Slide 62 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 62 devperf: { options: { urls: [ 'http://localhost:8000' ] } } … grunt.registerTask('pe', ['devperf']);

Slide 63

Slide 63 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 63

Slide 64

Slide 64 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 64 … devperf: { options: { urls: [ 'http://fromthemiddle.io/' ], numberOfRuns: 5, openResults: true, resultsFolder: './devperf', phantomasOptions: { 'film-strip': true } } } … grunt.registerTask('pe', ['devperf']);

Slide 65

Slide 65 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 65

Slide 66

Slide 66 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 66

Slide 67

Slide 67 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 67

Slide 68

Slide 68 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 68

Slide 69

Slide 69 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 69

Slide 70

Slide 70 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 70

Slide 71

Slide 71 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 71 http://fluentconf.com/javascript-html-2015/public/schedule/grid/public

Slide 72

Slide 72 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Remove HTML Comments? 72 https://github.com/gruntjs/grunt-contrib-htmlmin

Slide 73

Slide 73 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-contrib-htmlmin —save-dev 73 https://github.com/gruntjs/grunt-contrib-htmlmin

Slide 74

Slide 74 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 74 … htmlmin: { dist: { options: { removeComments: true, collapseWhitespace: true }, files: { 'dist/index.html': 'src/index.html', 'dist/contact.html': 'src/contact.html' } }, dev: { files: { 'dist/index.html': 'src/index.html', 'dist/contact.html': 'src/contact.html' } } } … grunt.registerTask(‘comments-be-gone‘, ['htmlmin']);

Slide 75

Slide 75 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Concatenate and Minify CSS files? 75

Slide 76

Slide 76 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-contrib-cssmin --save-dev 76 Minimize CSS files

Slide 77

Slide 77 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Remove duplicate CSS? 77

Slide 78

Slide 78 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-csscss --save-dev 78 Report duplicate CSS in files

Slide 79

Slide 79 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Remove unused CSS? 79

Slide 80

Slide 80 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-uncss --save-dev 80 Remove unused CSS

Slide 81

Slide 81 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-cssstats --save-dev 81 https://github.com/cssstats/grunt-cssstats Look at the site’s CSS statistics

Slide 82

Slide 82 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 82 https://github.com/cssstats/cssstats

Slide 83

Slide 83 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 83

Slide 84

Slide 84 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 84

Slide 85

Slide 85 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 85

Slide 86

Slide 86 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 86

Slide 87

Slide 87 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 87

Slide 88

Slide 88 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 88 grunt-cssstats configuration https://github.com/cssstats/grunt-cssstats cssstats: { dev: { options: {}, files: { 'stats/css-stats.json': ['css/example.css'] }, } } … grunt.registerTask('stats', ['cssstats']);

Slide 89

Slide 89 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 89 grunt-cssstats configuration https://github.com/cssstats/grunt-cssstats cssstats: { dev: { options: { safe: false }, // Barf on invalid CSS files: { 'stats/cssstats-dev.json': ['app/styles/main.css'] } }, prod: { files: { 'stats/cssstats.json': ['dist/styles.css'] } } }

Slide 90

Slide 90 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 90 grunt-cssstats configuration https://github.com/cssstats/grunt-cssstats cssstats: { dev: { options: { safe: false }, // Barf on invalid CSS files: { 'stats/cssstats-dev.json': ['app/styles/main.css'] } }, prod: { files: { 'stats/cssstats.json': ['dist/styles.css'] } } }

Slide 91

Slide 91 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 https://github.com/cssstats/cssstats 91

Slide 92

Slide 92 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Aggregate and Minify JavaScript? 92

Slide 93

Slide 93 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-contrib-uglify --save-dev 93 Minimize javascript files

Slide 94

Slide 94 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Too many small images? 94 Making things easier with sprites!

Slide 95

Slide 95 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-montage --save-dev 95 Making things easier with sprites!

Slide 96

Slide 96 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 96 grunt.initConfig({ montage: { iconaroo: { files: { "images/sprites": [ "images/icons/*.png" ] }, options: { size: 32, outputImage: "sprite-icons.png", outputStylesheet: "sprite-icons.css" } } } }); Sample grunt-montage configuration

Slide 97

Slide 97 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-contrib-imagemin --save-dev 97 Make pages load faster by reducing image sizes

Slide 98

Slide 98 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 98 imagemin: { prod: { files: [{ expand: true, cwd: 'imgs-src/', src: ['**/*.{png,jpg,gif}'], dest: 'imgs/' }] } }

Slide 99

Slide 99 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-svgmin --save-dev 99 Reduce SVG sizes, too

Slide 100

Slide 100 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 100 grunt.initConfig({ svgmin: { // Task options: { // Configuration that will be passed directly to SVGO plugins: [ { removeViewBox: false }, { removeUselessStrokeAndFill: false } ] }, dist: { // Target files: [{ // Dictionary of files expand: true, // Enable dynamic expansion. cwd: 'img/src', // Src matches are relative to this path. src: ['**/*.svg'], // Actual pattern(s) to match. dest: 'img/', // Destination path prefix. ext: '.min.svg' // Dest filepaths will have this extension. // ie: optimise img/src/branding/logo.svg and store it in img/branding/logo.min.svg }] } }); grunt.loadNpmTasks('grunt-svgmin'); grunt.registerTask('default', ['svgmin']); Sample grunt-svgmin configuration

Slide 101

Slide 101 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 101

Slide 102

Slide 102 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-responsive-images --save-dev 102 Responsive images by resizing https://github.com/andismith/grunt-responsive-images

Slide 103

Slide 103 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 103 grunt.initConfig({ responsive_images: { myTask: { options: { sizes: [{ width: 320, height: 240 },{ name: 'large', width: 640 },{ name: "large", width: 1024, suffix: "_x2", quality: 60 }] }, files: [{ expand: true, src: ['assets/**.{jpg,gif,png}'], cwd: 'test/', dest: 'resize/{%= width %}/' }] } }, }); Sample grunt-responsive-images configuration

Slide 104

Slide 104 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-grunticon --save-dev 104 SVG with PNG fallbacks https://github.com/filamentgroup/grunticon

Slide 105

Slide 105 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Wait… again… 105

Slide 106

Slide 106 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Dependent on my network? 106

Slide 107

Slide 107 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Yep. 107

Slide 108

Slide 108 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 How about not? 108

Slide 109

Slide 109 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 109

Slide 110

Slide 110 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 110

Slide 111

Slide 111 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 111 http://www.webpagetest.org/getkey.php Request an API key.

Slide 112

Slide 112 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 112

Slide 113

Slide 113 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 113 http://www.webpagetest.org/getkey.php Limits of public use The API key is provisioned for up to 200 page loads per day … sufficient for most low-volume use cases and for building a proof-of- concept for larger testing

Slide 114

Slide 114 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 114 Need more?

Slide 115

Slide 115 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 115 https://sites.google.com/a/webpagetest.org/docs/private-instances Set up your own WebPageTest server.

Slide 116

Slide 116 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-perfbudget --save-dev 116 https://github.com/tkadlec/grunt-perfbudget

Slide 117

Slide 117 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 117 perfbudget: { default: { options: { url: ‘http://example.io/', key: 'PUT_YOUR_API_KEY_HERE' } } } … grunt.registerTask('budg', ['perfbudget']);

Slide 118

Slide 118 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 118 perfbudget: { default: { options: { url: 'http://fromthemiddle.io/', key: 'thisismykey', wptInstance: 'ec2.us-west-2.amazonaws.com', location: 'us-west-2_wptdriver', pollResults: 10, connectivity: '3G', runs: 1, timeout: 240 } } }

Slide 119

Slide 119 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 119 perfbudget: { default: { options: { url: 'http://fromthemiddle.io/', key: 'thisismykey', wptInstance: 'ec2.us-west-2.amazonaws.com', location: 'us-west-2_wptdriver', pollResults: 10, connectivity: '3G', runs: 1, timeout: 240 } } }

Slide 120

Slide 120 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 120 perfbudget: { default: { options: { url: 'http://fromthemiddle.io/', key: 'thisismykey', wptInstance: 'ec2.us-west-2.amazonaws.com', location: 'us-west-2_wptdriver', pollResults: 10, connectivity: '3G', runs: 1, timeout: 240 } } }

Slide 121

Slide 121 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 121

Slide 122

Slide 122 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 122 perfbudget: { default: { options: { url: 'http://fromthemiddle.io/', … connectivity: '3G', timeout: 240, budget: { render: '3000', SpeedIndex: '7500', visualComplete: '6000' } } } }

Slide 123

Slide 123 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 123

Slide 124

Slide 124 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 124

Slide 125

Slide 125 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Now what? 125

Slide 126

Slide 126 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Integrate into CI builds 126

Slide 127

Slide 127 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 127

Slide 128

Slide 128 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Tracking over time 128

Slide 129

Slide 129 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Tracking over time 129 http://www.wptmonitor.org/home

Slide 130

Slide 130 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-wpt --save-dev 130 https://github.com/sideroad/grunt-wpt https://github.com/sideroad/grunt-wpt-page

Slide 131

Slide 131 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 131 wpt: { options: { url: 'http://fromthemiddle.io/', server: 'ec2.us-west-2.amazonaws.com', dest: 'wpt/' }, ftm: { options: { server: 'http://ec2.us-west-2.amazonaws.com', url: ['http://fromthemiddle.io/'] }, dest: 'wpt/', } } … grunt.registerTask('wptrun', ['wpt']);

Slide 132

Slide 132 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 132

Slide 133

Slide 133 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 133 https://github.com/trulia/webpagetest-charts-ui https://github.com/trulia/webpagetest-charts-api

Slide 134

Slide 134 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 npm install grunt-shell --save-dev 134 Installing the grunt shell package to get to everything else

Slide 135

Slide 135 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 135 function log(err, stdout, stderr, cb) { console.log(stdout); cb(); } grunt.initConfig({ shell: { dirListing: { command: 'ls', options: { callback: log } } } });

Slide 136

Slide 136 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 136 Make a change Measure effects

Slide 137

Slide 137 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Worth looking at: https://github.com/andyshora/grunt-yslow https://github.com/jrcryer/grunt-pagespeed https://github.com/addyosmani/psi/ http://www.sitespeed.io/ 137

Slide 138

Slide 138 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Questions? 138

Slide 139

Slide 139 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 139 Wait a second…

Slide 140

Slide 140 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 140

Slide 141

Slide 141 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 141 https://sites.google.com/a/webpagetest.org/docs/private-instances Set up your own WebPageTest server.

Slide 142

Slide 142 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 142

Slide 143

Slide 143 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 143

Slide 144

Slide 144 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 144

Slide 145

Slide 145 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 145

Slide 146

Slide 146 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 146

Slide 147

Slide 147 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 147

Slide 148

Slide 148 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 148

Slide 149

Slide 149 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 149

Slide 150

Slide 150 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 150

Slide 151

Slide 151 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 151

Slide 152

Slide 152 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 152

Slide 153

Slide 153 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 153

Slide 154

Slide 154 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 154

Slide 155

Slide 155 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 155

Slide 156

Slide 156 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 156

Slide 157

Slide 157 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 157

Slide 158

Slide 158 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 158

Slide 159

Slide 159 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 159

Slide 160

Slide 160 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 160

Slide 161

Slide 161 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 161

Slide 162

Slide 162 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 162

Slide 163

Slide 163 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 163

Slide 164

Slide 164 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 164

Slide 165

Slide 165 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 165 $ ssh -i downloaded.pem ubuntu@ec2

Slide 166

Slide 166 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 166 $ vi ~/.ssh/authorized_keys

Slide 167

Slide 167 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 167 sudo vi /var/www/webpage/test/www/settings/settings.ini # update host with ec2 hostname # add ec2_key value (optional) # add ec2_secret value (optional) # uncomment EC2.us-west-2.securityGroup line # uncomment EC2.us-west-2.subnetId line #

Slide 168

Slide 168 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 168 sudo vi /var/www/webpage/test/www/settings/keys.ini [server] secret=addarandomstringhere key=addakeyhere [addakeyhere] description=Web UI ;[email protected] limit=0 [thisisyourapikey] description=API Key ;[email protected] limit=0

Slide 169

Slide 169 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 169 $ cd /var/www/webpage/test/www/settings/ $ sudo cp locations.ini.EC2-sample locations.ini

Slide 170

Slide 170 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 170 $ sudo service nginx restart

Slide 171

Slide 171 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 171 Set up testing instances

Slide 172

Slide 172 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 172 EC2 server key in settings.ini

Slide 173

Slide 173 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 173 OR

Slide 174

Slide 174 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 174

Slide 175

Slide 175 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 175 wpt_server=ec2.us-west-2.amazonaws.com wpt_key=YOURKEY wpt_location=us-west-2

Slide 176

Slide 176 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 176 Wait.

Slide 177

Slide 177 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 177

Slide 178

Slide 178 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 178

Slide 179

Slide 179 text

Kitt Hodsden • @kitt • http://ki.tt/fluent2015 Thanks! Kitt Hodsden http://ki.tt/ @kitt 179