Upload
mixonic
View
3.563
Download
2
Embed Size (px)
Citation preview
Aligning Ember withWeb Standards
EmberConf 2015
@mixonic
Matthew Beale
201 Created
The JavaScript standardizationprocess is about to change
#1
STANDARDS PROCESS
WHATWG + W3C
TC39 + Ecma International
WHATWG + W3C
TC39 + Ecma International
DOMHTML Web Components XHR, Fetch
Promises for loops var, let, const classes
WHATWG W3C
TC39 Ecma International
WHATWG W3C
TC39 Ecma International
WORKING
GROUPSSTANDARDS GROUPS
The plan at the time was to finish the specification this year and publish a snapshot of "HTML5" in 2012. However, shortly after that we realized that the demand for new features in HTML remained high, and so we would have to continue maintaining HTML and adding features to it before we could call “HTML5" complete, and as a result we moved to a new development model, where the technology is not versioned and instead we just have a living document that defines the technology as it evolves.
Ian Hickson, 2011
“Living Standard”
ES3
ES4
ES5
ES6
ES6
ES2015
“ES2015” signifies a newstandardization process
github.com/ tc39/ecma262
0. Strawman 1. Proposal 2. Draft 3. Candidate 4. Finished
0. Strawman 1. Proposal -> Polyfills 2. Draft -> Experimental 3. Candidate -> Compliant 4. Finished -> Shipping
a “Living Web”
Aligning with standardsis not a one time event
Aligning with standardsis not free
Why standards?
Productivity
1. are portable 2. reflect best practices 3. endure
Standards…
Participants win
Design
Polyfill, demo
Real world use
Learning
Design
Polyfill, demo
Real world use
Learning
2. Transpilers are here to stay
This is not the first time features have been added to JavaScript
ES3 -> ES5
HTML5
“Polyfill”- Remy Sharp
ES5 -> ES2015
var map = new Map(); map.set('key', 'value'); var value = map.get('key');
var map = new Map(); map.set('key', 'value'); var value = map.get('key');
1 var delayed = new Promise( 2 function(resolve, reject){ 3 setTimeout(resolve, 100); 4 } 5 ); 6 delayed.then(function(){ 7 console.log('HTMLBars'); 8 });
1 var delayed = new Promise( 2 function(resolve, reject){ 3 setTimeout(resolve, 100); 4 } 5 ); 6 delayed.then(function(){ 7 console.log('HTMLBars'); 8 });
1 var loggingObject = new Proxy({}, { 2 get(target, propertyKey, receiver) { 3 console.log('GET '+propertyKey); 4 return target[propertyKey]; 5 } 6 }); 7 8 loggingObject.whatever; // Logs: GET whatever
1 var loggingObject = new Proxy({}, { 2 get(target, propertyKey, receiver) { 3 console.log('GET '+propertyKey); 4 return target[propertyKey]; 5 } 6 }); 7 8 loggingObject.whatever; // Logs: GET whatever
1 var runner = { 2 count: 0, 3 call: function() { 4 setTimeout(() => { 5 console.log(this.count++); 6 }, 100); 7 } 8 }; 9 10 runner.call();
1 var runner = { 2 count: 0, 3 call: function() { 4 setTimeout(() => { 5 console.log(this.count++); 6 }, 100); 7 } 8 }; 9 10 runner.call();
“Babel will turn your ES6+ code into ES5 friendly code, so you can start using it right
now without waiting for browser support.”
1 "use strict"; 2 3 var runner = { 4 count: 0, 5 call: function call() { 6 var _this = this; 7 8 setTimeout(function () { 9 console.log(_this.count++); 10 }, 100); 11 } 12 }; 13 14 runner.call();
1 var runner = { 2 count: 0, 3 call: function() { 4 setTimeout(() => { 5 console.log(this.count++); 6 }, 100); 7 } 8 }; 9 10 runner.call();
1. syntax (fat arrow, let) 2. APIs (Map, Set) 3. not everything
Enables new…
“Not born to die”
- James Kyle
kangax.github.io/compat-table/es6
ES2015 feature: Uint8Array
ES2015 feature: Uint8Array
IE10+
ES2015 feature: Spread Operator
var list = [1,2,3]; Math.max(...list);
ES2015 feature: Spread Operator
var list = [1,2,3]; Math.max(...list);
Firefox only
ES2015 feature: Block-level function scope1 "use strict"; 2 function a(){ return 1; } 3 { 4 function a(){ return 2; } 5 }; 6 7 a() === 1;
ES2015 feature: Block-level function scope
Chrome only
1 "use strict"; 2 function a(){ return 1; } 3 { 4 function a(){ return 2; } 5 }; 6 7 a() === 1;
The target platforms of Babelare inconsistent
Babel
Chrome
Firefox
The platforms your application supports will drive what features are transpiled.
Targeting platforms can be done by tweaking the enabled
features list.
IMO a mapping to platforms would be better.
What you transpile today,you will blacklist in two years
Yes, you will be transpilingin two years
Yes, you will be transpilingin five years
Yes, you will be transpilingin ?!!?!?! years
Transpilers are here to stay
3. Aligning Ember’s object model
1. stable 2. a good pattern 3. implemented correctly 4. implemented performantly
Is this feature:
ES Classes
1. class 2. extend 3. super
Three new tools:
1 class Car { 2 constructor(gearCount){ 3 this.gearCount = gearCount; 4 } 5 6 toString() { 7 return `A car with: ${gearCount} gears`; 8 } 9 } 10 11 var car = new Car(3); 12 car.toString(); // A car with 3 gears
1 class Vehicle { 2 constructor(gearCount){ 3 this.gearCount = gearCount; 4 } 5 } 6 class Car extends Vehicle { 7 toString() { 8 return `A car with: ${this.gearCount} gears`; 9 } 10 } 11 12 var car = new Car(3); 13 car.toString(); // A car with 3 gears
1 class Vehicle { 2 constructor(gearCount){ 3 this.gearCount = gearCount; 4 } 5 toString() { 6 return `${this.gearCount} gears`; 7 } 8 } 9 class Car extends Vehicle { 10 toString() { 11 return `A car with: ${super.toString()}`; 12 } 13 }
1 class Vehicle { 2 constructor(gearCount){ 3 this.gearCount = gearCount; 4 } 5 toString() { 6 return `${this.gearCount} gears`; 7 } 8 } 9 class Car extends Vehicle { 10 constructor(...args) { 11 console.log(`Created with ${args[0]}`); 12 super(args); 13 } 14 toString() { 15 return `A car with: ${super.toString()}`; 16 } 17 }
1. new syntax 2. super semantics change 3. mixins
gotachas:
4. setUnknownProperty 5. merged/concat properties 6. transpiler ouput?!
more gotachas:
7. only halfway there
7. only halfway thereES Decorators
1 class Car { 2 +attr('gearsCount') 3 +attr('wheelsCount') 4 5 constructor(gearsCount) { 6 this.gearsCount = gearsCount; 7 } 8 9 -dependsOn('gearsCount') 10 get isModern() { 11 return this.gearsCount > 3; 12 } 13 } 14 15 var car = new Car(3); 16 car.isModern; // false
Aligning
1. provide legacy wrapper 2. use syntax as a carrot 3. private use can start sooner
strategy:
1 import EmberObject from "ember/object"; 2 import computed from "ember/computed"; 3 4 class Car extends EmberObject.extend({ 5 6 init(gearsCount) { 7 this._super(...arguments); 8 this.set('gearsCount', gearsCount); 9 }, 10 11 isModern: computed('gearsCount', function(){ 12 return this.get('gearsCount') > 3; 13 }) 14 }); 15 16 export default Car;
1 import EmberObject from "ember/object"; 2 3 class Car extends EmberObject { 4 5 constructor(gearsCount) { 6 super(...arguments); 7 this.gearsCount = gearsCount; 8 } 9 10 get isModern() { 11 return this.gearsCount > 3; 12 } 13 } 14 15 export default Car;
1 import Component from "ember/component"; 2 3 class Car extends Component { 4 5 get isModern() { 6 return this.attrs.gearsCount > 3; 7 } 8 } 9 10 export default Car;
This is a story of Ember 2.0 -> 3.0
Reminder: Standards are a two-way street
ONE MORE THING
201-created.com/ember-community-survey-2015
@ClimbingNarc
201-created.com/ember-community-survey-2015
201-created.com/ember-community-survey-2015
Thank you, you wonderful people.
@mixonic