Transcript
Page 1: Writing a massive javascript app

Hojoon ParkSr. Software Engineer

LinkedIn

www.linkedin.com/in/justindoit

Writing a massive javascript app

Page 2: Writing a massive javascript app

2

Over the last 3 years,

Single Page Application (BackboneJS, AngularJS)

Template System(Handlebars, Dust.LI)

Web Framework (SugarAPIFramework, Java Play Framework)

Unit Test (JasmineJS, SinonJS)

Page 3: Writing a massive javascript app

3

Agenda

Web Frameworks

Single Page Application

Case Study

Performance Tuning

Demo

Page 4: Writing a massive javascript app

4

Avoid spaghetti code in Front-end development

Too much copy/paste

Too much 3rd party recourses

Hard to debug the errors

Page 5: Writing a massive javascript app

5

Web Frameworks, recommend?

Play

Spring

Ruby on Rails

Yii

Node.JS

Angular

Backbone

jQuery

YUI

Require

Knockout

Bootstrap

Page 6: Writing a massive javascript app

6

Case Study: BackboneJS on PHP

Pure SPA

Metadata Manager

Data Manager

Page 7: Writing a massive javascript app

7

Case Study: BackboneJS on Java Play

Hybrid Web Application

sbt-concat, sass compiler

Model Hierarchy

Page 8: Writing a massive javascript app

8

Case Study: AngularJS on Java Play

Pure SPA

Grunt Builder

Less compiler by Grunt

Page 9: Writing a massive javascript app

9

What is SPA (Single Page Application)?

Routing

Angular RouteProvider / Backbone Router

MVC Framework

Models as the single source

Views observe model changes

Minimized DOM dependent-code

Asset Packaging

Page 10: Writing a massive javascript app

10

SPA (Single Page Application)

Cons. Pros.

SEO OptimizationNo longer server side loading

(Read data thru AJAX)

Higher Risk, Higher Reward

(Memory Leak)Client/Server code partitioning

Large File Size No Page Refresh

Page 11: Writing a massive javascript app

11

Consideration for SPA

Resources/Assets Management

JS/CSS compressor

Template compiler

Additional: LESS/SASS compiler

Page 12: Writing a massive javascript app

12

Why Asset Management is important?

Continuously growing JS/CSS resources

Duplicated JS files / version inconsistency

Page 13: Writing a massive javascript app

13

Sync vs. Async

Sync Async

Controller

Web framework

(Compiler plugin,

AssetManager)

Front-end Tools

(Require.JS, Inject.JS)

Pros. No delay on click Lazy Load

Cons. Longer loading time Loading on click

Page 14: Writing a massive javascript app

14

Anatomy: Directory(1)

By Resource Type

Page 15: Writing a massive javascript app

15

Anatomy: Directory(2)

By Feature

Page 16: Writing a massive javascript app

16

Asset Packaging: Play Framework

sbt-concat plugin

JavascriptMinifierCompiler

Page 17: Writing a massive javascript app

17

Asset Packaging: Yii Framework

AssetManager

Page 18: Writing a massive javascript app

18

Build asset packages without web framework

Resources/Assets Management

JS/CSS compressor

Template compiler

Additional: LESS/SASS compiler

Build System

ToolPackage

Manager

Bower

Page 19: Writing a massive javascript app

19

Metadata Manager

Sort the dependent modules

FlexListView

extends: ListView

ListView

DashableListView

extends: ListView

RecordListView

Extends: FlexListView

ListView

FlexListView

extends: ListView

DashableListView

extends: ListView

RecordListView

Extends: FlexListView

Page 20: Writing a massive javascript app

/**

* Sorts components in the order they should be declared as classes. This is required since a parent

* widget class must likewise be declared before a child that depends on it.

* @param {String} type Metadata type e.g. field, view. layout

* @param {Array} components List of modules

* @param {String} module Module name

* @return {Array} Sorted components

*/

_sortControllers : function(type, components, module) {

var updated = {}, nameMap = {}, entries = {},

updateWeights = function(entry){

var controller = entry.controller;

// Here we decrement the weight of any extended components. Note, that if sorting platform

// specific components (e.g. portal), and one "extends from" a base component, that parent

// will have already been declared since _sortControllers first gets called with base components

if (_.isObject(controller) && _.isString(controller.extendsFrom) &&

entries[controller.extendsFrom] && !updated[controller.extendsFrom])

{

// Negative weights as we want to load those first

entries[controller.extendsFrom].weight--;

updated[controller.extendsFrom] = true;

updateWeights(entries[controller.extendsFrom]);

}

};

// Start by creating a mapping from short name to final class name and precompiling all the controllers that are strings

_.each(components, function(entry, name) {

if (entry.controller) {

var controller = entry.controller,

className = (module || "") + app.utils.capitalizeHyphenated(name) + app.utils.capitalize(type);

nameMap[className] = name;

if (_.isString(controller)) {

20

Metadata Manager: cont.

Implementation

Page 21: Writing a massive javascript app

Great Design patterns are reusable, modular

expressions of what’s going on in your code.

They allow you to communicate to other

developers simply by the way you code,

in addition to being easily maintainable

themselves

21

Why Patterns?

Page 22: Writing a massive javascript app

22

Software design patterns

Factory

Singleton

MVC

Strongly OOP

Mixin

Event Driven

Page 23: Writing a massive javascript app

23

Object Oriented Programming

Code Reuse and recycling

Design Benefits

More features,

same amount of time

ListView

FlexListView

SubPanelListView

DashableListView

RecordListViewSelectionListView

Page 24: Writing a massive javascript app

Mixin pool

24

Decorator: Mixin (plugin)

RecordListView

extends: ListView

ErrorDecoration

Editable

MergeDuplicates

CreateView

Audit

FindDuplicates

Tooltip

ListView MergeDuplicateView

Timeago

ActivityStreamView

Page 25: Writing a massive javascript app

25

BackboneJS: Life-cycle of View Component

Initialize Bind events

Render

template

Unbind

eventsDispose

WatchersRegister

Trigger

Unregister

Page 26: Writing a massive javascript app

26

AngularJS: Life-cycle of scope

CreationWatcher

registration

Model

mutation

Mutation

observationScope

destruction

Page 27: Writing a massive javascript app

He who binds himself to a joy

Does the winged life destroy;

But he who kisses the joy as it flies

Lives in eternity's sun rise.

27

William Blake

Page 28: Writing a massive javascript app

28

Performance tuning

Remove duplicate listeners

Watcher optimization

Backbone: _events stack

Angular: $__watchers in $digest cycle

How many watchers will be incurred?

Page 29: Writing a massive javascript app

29

Don’t blame browser

Page 30: Writing a massive javascript app

30

Memory Management

Dispose safeInitialize Bind events

Render

Unbind eventsDispose

WatchersRegister

Trigger

Unregister

Page 31: Writing a massive javascript app

31

Memory Management: cont.

Catch while unit testing

Page 32: Writing a massive javascript app

32

Debugging

Firebug

Chrome developer tool

Network filtering

Recording

Profiler

Local Storage in resources tab

Page 33: Writing a massive javascript app

33

Unit Test

Jasmine, Karma, Sinon

Travis CI

Selenium WebDriver

Page 34: Writing a massive javascript app

34

Demo