Bundling Client Side Assets

68
Client Side Assets Thursday, 13 December 12

description

 

Transcript of Bundling Client Side Assets

Page 1: Bundling Client Side Assets

Client Side Assets

Thursday, 13 December 12

Page 2: Bundling Client Side Assets

Thursday, 13 December 12

Page 3: Bundling Client Side Assets

npm for the front-end

Thursday, 13 December 12

Page 4: Bundling Client Side Assets

> bower install jquery

Thursday, 13 December 12

Page 5: Bundling Client Side Assets

> bower install jquery bower cloning git://github.com/components/jquery.gitbower caching git://github.com/components/jquery.gitbower fetching jquerybower checking out jquery#1.8.1bower copying /Users/timoxley/.bower/jquery

Thursday, 13 December 12

Page 6: Bundling Client Side Assets

{  "name": "myProject",  "version": "1.0.0",  "main": "./path/to/main.css",  "dependencies": {    "jquery": "~1.7.1"  }}

component.json

Thursday, 13 December 12

Page 7: Bundling Client Side Assets

> bower install bower cloning git://github.com/components/jquery.gitbower cached git://github.com/components/jquery.gitbower fetching jquerybower checking out jquery#1.7.1bower copying /Users/timoxley/.bower/jquery

component.json

Thursday, 13 December 12

Page 8: Bundling Client Side Assets

> bower update bower cloning git://github.com/components/jquery.gitbower cached git://github.com/components/jquery.gitbower fetching jquerybower checking out jquery#1.7.2bower copying /Users/timoxley/.bower/jquery

Thursday, 13 December 12

Page 9: Bundling Client Side Assets

componentsby TJ Holowaychuk

Thursday, 13 December 12

Page 10: Bundling Client Side Assets

modular… components.

Thursday, 13 December 12

Page 11: Bundling Client Side Assets

> component install component/jquery

Thursday, 13 December 12

Page 12: Bundling Client Side Assets

single responsibility principle

Thursday, 13 December 12

Page 13: Bundling Client Side Assets

“Have you ever seen a great jQuery plugin and thought to yourself “damn! I’m using MooTools!” or perhaps the other way around?”

Thursday, 13 December 12

Page 14: Bundling Client Side Assets

“That highlights the problem right there, we should have no “jQuery plugins”, no “Dojo modules”, just simply “components” that we can all consume.”

Thursday, 13 December 12

Page 15: Bundling Client Side Assets

“Components could then utilize these smaller, more modular dependencies to perform tasks.”

Thursday, 13 December 12

Page 16: Bundling Client Side Assets

“Instead of requiring jQuery as a dependency to convert a string of HTML into elements, one could simply add domify as a dependency and invoke domify(html).”

Thursday, 13 December 12

Page 17: Bundling Client Side Assets

“…ubiquitous libraries like jQuery will eventually be a thing of the past and fragmentation will hopefully decrease.” – TJ Holowaychuk

Thursday, 13 December 12

Page 18: Bundling Client Side Assets

microjs meets npm

Thursday, 13 December 12

Page 19: Bundling Client Side Assets

Thursday, 13 December 12

Page 20: Bundling Client Side Assets

Thursday, 13 December 12

Page 21: Bundling Client Side Assets

Thursday, 13 December 12

Page 22: Bundling Client Side Assets

Thursday, 13 December 12

Page 23: Bundling Client Side Assets

Thursday, 13 December 12

Page 24: Bundling Client Side Assets

Thursday, 13 December 12

Page 25: Bundling Client Side Assets

•visionmedia/superagent•visionmedia/page.js•jprichardson/string.js•guille/ms.js•component/domify•component/emitter•component/tip•component/dialog•component/notification•visionmedia/bytes.js•component/bus•component/overlay•component/autoscale-canvas•component/popover•component/event•component/confirmation•component/confirmation-popover•component/popup•component/menu•component/clipboard•jamesarosen/ember-progressbars•component/suggest-email•component/clipboard-dom•component/cookie•component/path•component/path-to-regexp•component/color-picker•component/within-document•component/classes•component/upload•component/file•component/touchit•component/color•component/thumb•component/calendar•component/url•component/query-string•component/progress-notification•component/progress•forbeslindesay/ajax•component/dropload

•component/history•component/moment•forbeslindesay/booting-sub-nav•juliangruber/stream•component/t•component/grow•component/dom•component/matches-selector•component/color-parser•component/inherit•component/select•component/map•component/escape-html•component/pager•component/bind•component/more•component/trim•component/object•component/removed•component/pie•component/inserted•component/mime•component/sketch•component/indexof•component/convolve•component/preloader•component/piecon•component/json•component/pad•component/confirmation-

notification•component/dropdown•component/relative-date•component/type•component/favicon•component/counter•component/assert•component/states•component/countries•component/regexps•component/style

•component/noticon•component/zepto•component/escape-regexp•component/jquery•component/batch•solutionio/countdown•componitable/editable•juliangruber/span•component/underscore•solutionio/backbone•solutionio/async•component/buttonset•colinf/datecalc•retrofox/to-object•componitable/format-number•retrofox/toolkit•component/aurora-calendar

Thursday, 13 December 12

Page 26: Bundling Client Side Assets

GRUNTThursday, 13 December 12

Page 27: Bundling Client Side Assets

Grunt is a task-based command line build tool for JavaScript projects.

Thursday, 13 December 12

Page 28: Bundling Client Side Assets

• GNU Make

• Apache Ant

• Jake

• Cake

• Rake

• Buildr

• Sprockets

• + many more

Similar Tools

Thursday, 13 December 12

Page 29: Bundling Client Side Assets

What does a grunt file look like?

Thursday, 13 December 12

Page 30: Bundling Client Side Assets

module.exports = function(grunt) {

// Project configuration. grunt.initConfig({ lint: { all: ['grunt.js', 'lib/**/*.js', 'test/**/*.js'] }, jshint: { options: { browser: true } } });

// Load tasks from "grunt-sample" grunt plugin installed via Npm. grunt.loadNpmTasks('grunt-sample');

// Default task. grunt.registerTask('default', 'lint sample');

};

Thursday, 13 December 12

Page 31: Bundling Client Side Assets

module.exports = function(grunt) {  grunt.initConfig({    handlebars: {      all: {        src: "src/templates/",        dest: "public/js/templates.js"      }    },    less: {      all: {        src: 'src/less/application.less',        dest: 'public/css/application.css'      }    },    concat: {      app: {        src: ['src/app/*.coffee'],        dest: 'public/js/main.coffee'      }    },    watch: {      all: {        files: ["src/*", "src/**"],        tasks: "default"      }    },    coffee: {      all: {        src: ["public/js/main.coffee"],        dest: "public/js",        options: {          bare: false        }      }    }  });

  grunt.loadNpmTasks("grunt-handlebars");  grunt.loadNpmTasks("grunt-coffee");  grunt.loadNpmTasks("grunt-less");  return grunt.registerTask("default", "handlebars concat coffee less");};

Thursday, 13 December 12

Page 32: Bundling Client Side Assets

module.exports = function(grunt) {

  // Project configuration.  grunt.initConfig({    meta: {      version: '0.1.0',      banner: '/*! App Name - v<%= meta.version %> - ' +        '<%= grunt.template.today("yyyy-mm-dd") %>\n' +        '* THIS FILE IS GENERATED BY GRUNT. DO NOT MODIFY MANUALLY\n' +        '* http://app/\n' +        '* Copyright (c) <%= grunt.template.today("yyyy") %> ' +        'Company Inc.; */'    },    lint: {      files: ['grunt.js', 'frontend/src/app.js', 'frontend/src/models/*.js', 'frontend/src/collections/*.js', 'frontend/src/views/*.js', 'frontend/src/router.js', 'frontend/spec/**/*.js', 'frontend/src/statechart.js']    },    concat: {      libs: {        src: ['<banner:meta.banner>',              'frontend/src/vendor/jquery-1.7.2.min.js',              'frontend/src/vendor/underscore-min.js',              'frontend/src/vendor/backbone.js',              'frontend/src/vendor/stativus.js',              'frontend/src/vendor/handlebars.runtime.js',              'frontend/src/vendor/moment-1.6.2.js'        ],        dest: 'public/js/libs.js'      },      tribe: {        src: ['<banner:meta.banner>', 'frontend/src/app.js', 'frontend/src/models/*.js', 'frontend/src/collections/*.js', 'frontend/src/views/*.js', 'frontend/src/router.js', 'frontend/src/statechart.js'],        dest: 'public/js/tribe.js'      },      css: {        src: ['<banner:meta.banner>', 'frontend/css/reset.css', 'frontend/css/base.css', 'frontend/css/tribe.css'],        dest: 'public/css/screen.css'      }    },    min: {      libs: {        src: ['<banner:meta.banner>', 'public/js/libs.js'],        dest: 'public/js/libs.min.js'      },      tribe: {        src: ['<banner:meta.banner>', 'public/js/tribe.js'],        dest: 'public/js/tribe.min.js'      },      templates: {        src: ['<banner:meta.banner>', 'public/js/templates.js'],        dest: 'public/js/templates.min.js'      }    },    recess: {      css: {        src: ['public/css/screen.css'],        dest: 'public/css/screen.min.css',        options: {          compress: true,          noIDs: false        }      }    },    handlebars: {      all: {        src: 'frontend/src/templates',        dest: 'public/js/templates.js'      }    },    watch: {      files: ['<config:lint.files>', 'frontend/css/*.css', 'frontend/src/templates/*.handlebars'],      tasks: 'handlebars concat:tribe concat:css min:tribe min:templates recess'    },    jshint: {      options: {        curly: true,        eqeqeq: true,        immed: true,        latedef: true,        newcap: true,        noarg: true,        sub: true,        undef: true,        boss: true,        eqnull: true,        browser: true      },      globals: {}    },    uglify: {}  });

  grunt.loadNpmTasks('grunt-handlebars');  grunt.loadNpmTasks('grunt-recess');

  // Default task.  grunt.registerTask('default', 'lint handlebars concat min recess');

};

Thursday, 13 December 12

Page 33: Bundling Client Side Assets

Running grunt

Thursday, 13 December 12

Page 34: Bundling Client Side Assets

> grunt

Thursday, 13 December 12

Page 37: Bundling Client Side Assets

Concatenate

grunt.initConfig({ concat: { dist: { src: ['src/intro.js', 'src/project.js', 'src/outro.js'], dest: 'dist/built.js' } }});

Thursday, 13 December 12

Page 38: Bundling Client Side Assets

Lint

grunt.initConfig({ lint: { files: ['grunt.js', 'lib/*.js', 'test/*.js'] }});

Thursday, 13 December 12

Page 39: Bundling Client Side Assets

Lintgrunt.initConfig({ lint: { files: ['grunt.js', 'src/**/*.js', 'test/**/*.js'] }, jshint: { options: { curly: true, sub: true, undef: true }, globals: { jQuery: true } },});

Thursday, 13 December 12

Page 40: Bundling Client Side Assets

Minify

grunt.initConfig({ min: { dist: { src: ['vendor/*'], dest: 'public/libs.min.js' } }});

Thursday, 13 December 12

Page 41: Bundling Client Side Assets

Watch

grunt.initConfig({ watch: { files: ['src/*.jade'], tasks: 'jade' }, jade: { html: { src: ['src/*.jade'], dest: 'public' } }});

Thursday, 13 December 12

Page 42: Bundling Client Side Assets

CoffeeScript makes for tidy Gruntfiles

Thursday, 13 December 12

Page 43: Bundling Client Side Assets

module.exports = (grunt) ->  grunt.initConfig    handlebars:      all:        src: "src/templates/"        dest: "public/js/templates.js"    less:      all:        src: 'src/less/application.less'        dest: 'public/css/application.css'    concat:      app:        src: [          'src/app/*.coffee'        ]        dest: 'public/js/main.coffee'    watch:      all:        files: [          "src/*",          "src/**"        ]        tasks: "default"

  grunt.loadNpmTasks "grunt-handlebars"  grunt.loadNpmTasks "grunt-less"

  grunt.registerTask "default", "handlebars concat less"

Thursday, 13 December 12

Page 44: Bundling Client Side Assets

> grunt --config ./grunt.coffee

Thursday, 13 December 12

Page 45: Bundling Client Side Assets

150+ 3rd Party Tasks

Thursday, 13 December 12

Page 46: Bundling Client Side Assets

• contrib-clean - Clear files and folders.

• cp - A Grunt plugin for copying directories (recursively)

• md5 - generate md5 filename

• shell - Run shell commands

• s3 - automate moving files to/from Amazon S3.

Thursday, 13 December 12

Page 49: Bundling Client Side Assets

• image-embed - Embed images as base64 data URIs inside your stylesheets.

• smushit - Remove unnecessary bytes of PNG and JPG using Yahoo Smushit

• willitmerge - Check if open Github pull requests are merge-able.

• rigger - Rigging tasks for elegant includes

Thursday, 13 December 12

Page 50: Bundling Client Side Assets

min: { app: { src: ['app/*'], dest: 'public/app.min.js' }, libs: { src: ['vendor/*'], dest: 'public/libs.min.js' } }

> grunt min:app> grunt min:libs

Thursday, 13 December 12

Page 51: Bundling Client Side Assets

Creating Custom Plugins is Easy

Thursday, 13 December 12

Page 52: Bundling Client Side Assets

> grunt init:gruntplugin

Thursday, 13 December 12

Page 53: Bundling Client Side Assets

Running "init:gruntplugin" (init) taskThis task will create one or more files in the current directory, based on theenvironment and the answers to a few questions. Note that answering "?" to anyquestion will show question-specific help and answering "none" to most questionswill leave its value blank.

"gruntplugin" template notes:The grunt plugin system is still under development. For more information, seethe docs at https://github.com/cowboy/grunt/blob/master/docs/plugins.md

Please answer the following:[?] Project name (grunt-plugin) [?] Description (The best sample grunt tasks ever.) [?] Version (0.1.0) [?] Project git repository (git://github.com/timoxley/grunt-plugin.git) [?] Project homepage (https://github.com/timoxley/grunt-plugin) [?] Project issues tracker (https://github.com/timoxley/grunt-plugin/issues) [?] Licenses (MIT) [?] Author name (Tim Oxley) [?] Author email ([email protected]) [?] Author url (none) [?] What versions of grunt does it require? (~0.3.9) [?] What versions of node does it run on? (*) [?] Do you need to make any changes to the above before continuing? (y/N) N

Writing .npmignore...OKWriting bin/grunt-plugin...OKWriting grunt.js...OKWriting README.md...OKWriting tasks/plugin.js...OKWriting test/plugin_test.js...OKWriting LICENSE-MIT...OK

Initialized from template "gruntplugin".

Done, without errors

Thursday, 13 December 12

Page 54: Bundling Client Side Assets

// Load tasks and helpers from the "tasks" directory, relative to grunt.js.grunt.loadTasks('tasks');

// Load tasks and helpers from the "grunt-sample" Npm-installed grunt plugin.grunt.loadNpmTasks('grunt-sample');

Thursday, 13 December 12

Page 55: Bundling Client Side Assets

html5 boilerplate +grunt +opinions =

Thursday, 13 December 12

Page 56: Bundling Client Side Assets

node-build-script

Thursday, 13 December 12

Page 57: Bundling Client Side Assets

bootstrap for grunt

Thursday, 13 December 12

Page 58: Bundling Client Side Assets

•Concats / Compresses JS

•Concats / Compresses CSS

•Inline CSS imports via RequireJS

•Basic to aggressive html minification (via [html-minfier][])

•Optimizes JPGs and PNGs (with jpegtran & optipng)

Thursday, 13 December 12

Page 59: Bundling Client Side Assets

•Renames JS/CSS to prepend a hash of their contents for easier versioning

•Revises the file names of your assets so that you can use heavy caching

•Updates your HTML to reference these new hyper-optimized CSS + JS files

Thursday, 13 December 12

Page 60: Bundling Client Side Assets

•May rerun the build script on file changes (grunt's watch task ❤)

•May automatically reload the page in your browsers whenever watched files change, through some socket.io magic.

Thursday, 13 December 12

Page 61: Bundling Client Side Assets

node-build-script +bower +more opinions=

Thursday, 13 December 12

Page 62: Bundling Client Side Assets

Thursday, 13 December 12

Page 64: Bundling Client Side Assets

•HTML5 Boilerplate

•Twitter Bootstrap

•Twitter Bootstrap plugins

•RequireJS

•Support for ES6 Modules

•Wraps bower

Thursday, 13 December 12

Page 65: Bundling Client Side Assets

• Lightning-fast scaffolding — Easily scaffold new projects with customizable templates (e.g HTML5 Boilerplate, Twitter Bootstrap), AMD (via RequireJS) and more.

• Automatically compile CoffeeScript & Compass — Our LiveReload watch process automatically compiles source files and refreshes your browser whenever a change is made so you don't have to.

Thursday, 13 December 12

Page 66: Bundling Client Side Assets

• Automatically lint your scripts — All your scripts are automatically run against jshint to ensure they're following language best-practices.

• Built-in preview server — No more having to fire up your own HTTP Server. My built-in one can be fired with just one command.

• Awesome Image Optimization — I optimize all your images using OptiPNG and JPEGTran so your users can spend less time

Thursday, 13 December 12

Page 67: Bundling Client Side Assets

• Integrated package management — Need a dependency? It's just a keystroke away. I allow you to easily search for new packages via the command-line (e.g., yeoman search jquery), install them and keep them updated without needing to open your browser.

• Support for ES6 module syntax — Experiment with writing modules using the latest ECMAScript 6 module syntax. This is an experimental feature that transpiles back to ES5 so you can use the code in all

Thursday, 13 December 12

Page 68: Bundling Client Side Assets

• PhantomJS Unit Testing — Easily run your unit tests in headless WebKit via PhantomJS. When you create a new application, I also include some test scaffolding for your app.

Thursday, 13 December 12