Part 1: ES6 syntax
ES6 is the next version of JavaScript!
- 2009: ES5
- 2015: ES6
- 2016: ES7
With Babel transformer, we can use ES6 now!
Babel is included in react-rails gem.
Links
The arrow symbol =>
Useful in .jsx loops with .map()
function and event handlers.
Benefits:
- compact! no
function
, no{}
, noreturn
- No problem scope with
this
keyword
JSX Example 1: create table rows
BEFORE
<tbody>
{ entries.map( function (entry, i) {
return(<RestoreLogList.Entry
entry={ entry }
key={ i }
/>);
}
) }
</tbody>
AFTER
<tbody>
{ entries.map( (entry, i) =>
<RestoreLogList.Entry
entry={ entry }
key={ i }
/>
) }
</tbody>
JSX Example 2: create a button toolbar
BEFORE
var self = this;
<div className="btn-group">
{ this.props.options.map(
function (item, i) {
return (<button
key={ i }
type="button"
className={ 'btn' + (self.props.value == item ? ' active' : '') }
onClick={ function () { self.props.onChange(item); } }
>
{ item }
</button>);
}
)}
</div>
AFTER
<div className="btn-group">
{ this.props.options.map( (item, i) =>
<button
key={ i }
type="button"
className={ 'btn' + (this.props.value == item ? ' active' : '') }
onClick={ () => this.props.onChange(item) }
>
{ item }
</button>
) }
</div>
Destructuring
BEFORE
var x = data.x;
var y = data.y;
var z = data.z;
AFTER
let {x, y, z} = data;
Other nice features
class
-
let
andconst
- default parameter value
- ...
Coming soon: ES7 (ES2016) !
An example of feature: [decorators] (https://medium.com/google-developers/exploring-es7-decorators-76ecb65fb841)
Part 2: use JavaScript modules ?
1. Old JavaScript (everything is global)
//React is in the global namespace.
var MyComponent = React.createClass({
handleSubmit: function(e) {
},
render: function() {
}
});
//MyComponent is an object declared in the global namespace
<MyComponent />
2. CommonJS module system (used by node.js)
require
module.exports
var React = require('react');
var MyComponent = React.createClass({
handleSubmit: function(e) {
},
render: function() {
}
});
module.exports = MyComponent
var MyComponent = require('./path/to/my-component.jsx');
<MyComponent />
3. ES6 modules
import
export
import React from "react";
export default class MyComponent extends React.Component {
handleSubmit(e) {
}
render() {
}
}
import MyComponent from './path/to/my-component.jsx';
<MyComponent />
More details about ES6 class syntax: React on ES6+
Why use modules (instead of Rails sprockets) ?
- Code easier to read and maintain
- Code easier to test
- npm ecosystem power: more choice, librairies up-to-date...
- Decoupled architecture (Front-end application + Rails backend application, used to make API calls)
Blog entry and discussion: Rails with Webpack - Why and How
Love the asset pipeline to death, but the lack of true modules definitely gets noticable with larger amounts of client side code.
How to use modules in our Rails application ?
We need to convert modules to plain JavaScript code.
Webpack can be used to require any file (JavaScript, CoffeeScript, JSX, css, sass) and generates a single bundle file.
A nice add-on : react-hot-reload
React hot loader automaically updates the browser when a .JSX file is updated, keeping the context (state and props).
Examples of Rails + Webpack integration
- rails-webpack-react-flux: Rails + CoffeeScript + Flux (Flummox) + csjx + Webpack
- react-webpack-rails-tutorial: Rails + ES6 + Flux (Alt) + Webpack
- FFRRIWB on Rails: Flux (Flummox), React, React Router, Immutable
Discussion
Single-Page-Application ("SPA") pros and cons
Pros:
- Fast (static assets pushed to a CDN, Rails only serves JSON data)
- Rich user experience
- Decoupled architecture: more flexible UI, easier to change
- Mobile application (native or hybrid) are possible
Cons:
- requires modern JavaScript skills!
- Building process
- in local environment, 2 servers are needed: a back-end server (Rails) + a front-end server that builds asset and serves static content (node.js)
- Too complicated ? (皆んなさん、どう思いますか?)
Coming soon, next 勉強会
- How to test (modern) JavaScript
- Flux architecture
- ...