Skip to content

Commit 36f51b4

Browse files
committed
fix(turbolinks) use good turbolinks events
1 parent d16c932 commit 36f51b4

File tree

4 files changed

+166
-111
lines changed

4 files changed

+166
-111
lines changed

lib/assets/javascripts/react_ujs.js

Lines changed: 81 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,34 @@ return /******/ (function(modules) { // webpackBootstrap
7878
/************************************************************************/
7979
/******/ ([
8080
/* 0 */
81+
/***/ (function(module, exports) {
82+
83+
// Assume className is simple and can be found at top-level (window).
84+
// Fallback to eval to handle cases like 'My.React.ComponentName'.
85+
// Also, try to gracefully import Babel 6 style default exports
86+
var topLevel = typeof window === "undefined" ? this : window;
87+
88+
module.exports = function(className) {
89+
var constructor;
90+
// Try to access the class globally first
91+
constructor = topLevel[className];
92+
93+
// If that didn't work, try eval
94+
if (!constructor) {
95+
constructor = eval(className);
96+
}
97+
98+
// Lastly, if there is a default attribute try that
99+
if (constructor && constructor['default']) {
100+
constructor = constructor['default'];
101+
}
102+
103+
return constructor;
104+
}
105+
106+
107+
/***/ }),
108+
/* 1 */
81109
/***/ (function(module, exports, __webpack_require__) {
82110

83111
var nativeEvents = __webpack_require__(7)
@@ -118,58 +146,26 @@ module.exports = function(ujs) {
118146
}
119147

120148

121-
/***/ }),
122-
/* 1 */
123-
/***/ (function(module, exports) {
124-
125-
// Assume className is simple and can be found at top-level (window).
126-
// Fallback to eval to handle cases like 'My.React.ComponentName'.
127-
// Also, try to gracefully import Babel 6 style default exports
128-
var topLevel = typeof window === "undefined" ? this : window;
129-
130-
module.exports = function(className) {
131-
var constructor;
132-
// Try to access the class globally first
133-
constructor = topLevel[className];
134-
135-
// If that didn't work, try eval
136-
if (!constructor) {
137-
constructor = eval(className);
138-
}
139-
140-
// Lastly, if there is a default attribute try that
141-
if (constructor && constructor['default']) {
142-
constructor = constructor['default'];
143-
}
144-
145-
return constructor;
146-
}
147-
148-
149149
/***/ }),
150150
/* 2 */
151-
/***/ (function(module, exports) {
151+
/***/ (function(module, exports, __webpack_require__) {
152+
153+
// Make a function which:
154+
// - First tries to require the name
155+
// - Then falls back to global lookup
156+
var fromGlobal = __webpack_require__(0)
157+
var fromRequireContext = __webpack_require__(12)
152158

153-
// Load React components by requiring them from "components/", for example:
154-
//
155-
// - "pages/index" -> `require("components/pages/index")`
156-
// - "pages/show.Header" -> `require("components/pages/show").Header`
157-
// - "pages/show.Body.Content" -> `require("components/pages/show").Body.Content`
158-
//
159159
module.exports = function(reqctx) {
160+
var fromCtx = fromRequireContext(reqctx)
160161
return function(className) {
161-
var parts = className.split(".")
162-
var filename = parts.shift()
163-
var keys = parts
164-
// Load the module:
165-
var component = reqctx("./" + filename)
166-
// Then access each key:
167-
keys.forEach(function(k) {
168-
component = component[k]
169-
})
170-
// support `export default`
171-
if (component.__esModule) {
172-
component = component["default"]
162+
var component;
163+
try {
164+
// `require` will raise an error if this className isn't found:
165+
component = fromCtx(className)
166+
} catch (err) {
167+
// fallback to global:
168+
component = fromGlobal(className)
173169
}
174170
return component
175171
}
@@ -202,9 +198,9 @@ var React = __webpack_require__(3)
202198
var ReactDOM = __webpack_require__(4)
203199
var ReactDOMServer = __webpack_require__(5)
204200

205-
var detectEvents = __webpack_require__(0)
206-
var constructorFromGlobal = __webpack_require__(1)
207-
var constructorFromRequireContext = __webpack_require__(2)
201+
var detectEvents = __webpack_require__(1)
202+
var constructorFromGlobal = __webpack_require__(0)
203+
var constructorFromRequireContextWithGlobalFallback = __webpack_require__(2)
208204

209205
var ReactRailsUJS = {
210206
// This attribute holds the name of component which should be mounted
@@ -255,8 +251,8 @@ var ReactRailsUJS = {
255251
// the default is ReactRailsUJS.ComponentGlobal
256252
getConstructor: constructorFromGlobal,
257253

258-
loadContext: function(req) {
259-
this.getConstructor = constructorFromRequireContext(req)
254+
useContext: function(req) {
255+
this.getConstructor = constructorFromRequireContextWithGlobalFallback(req)
260256
},
261257

262258
// Render `componentName` with `props` to a string,
@@ -360,8 +356,9 @@ module.exports = {
360356
module.exports = {
361357
// Turbolinks 5+ got rid of named events (?!)
362358
setup: function(ujs) {
363-
ujs.handleEvent('turbolinks:load', function() { ujs.mountComponents() });
364-
ujs.handleEvent('turbolinks:before-render', function() { ujs.unmountComponents() });
359+
ujs.handleEvent('DOMContentLoaded', function() { ujs.mountComponents() })
360+
ujs.handleEvent('turbolinks:render', function() { ujs.mountComponents() })
361+
ujs.handleEvent('turbolinks:before-render', function() { ujs.unmountComponents() })
365362
},
366363
}
367364

@@ -397,6 +394,36 @@ module.exports = {
397394
}
398395

399396

397+
/***/ }),
398+
/* 12 */
399+
/***/ (function(module, exports) {
400+
401+
// Load React components by requiring them from "components/", for example:
402+
//
403+
// - "pages/index" -> `require("components/pages/index")`
404+
// - "pages/show.Header" -> `require("components/pages/show").Header`
405+
// - "pages/show.Body.Content" -> `require("components/pages/show").Body.Content`
406+
//
407+
module.exports = function(reqctx) {
408+
return function(className) {
409+
var parts = className.split(".")
410+
var filename = parts.shift()
411+
var keys = parts
412+
// Load the module:
413+
var component = reqctx("./" + filename)
414+
// Then access each key:
415+
keys.forEach(function(k) {
416+
component = component[k]
417+
})
418+
// support `export default`
419+
if (component.__esModule) {
420+
component = component["default"]
421+
}
422+
return component
423+
}
424+
}
425+
426+
400427
/***/ })
401428
/******/ ]);
402429
});

react_ujs/dist/react_ujs.js

Lines changed: 81 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,34 @@ return /******/ (function(modules) { // webpackBootstrap
7878
/************************************************************************/
7979
/******/ ([
8080
/* 0 */
81+
/***/ (function(module, exports) {
82+
83+
// Assume className is simple and can be found at top-level (window).
84+
// Fallback to eval to handle cases like 'My.React.ComponentName'.
85+
// Also, try to gracefully import Babel 6 style default exports
86+
var topLevel = typeof window === "undefined" ? this : window;
87+
88+
module.exports = function(className) {
89+
var constructor;
90+
// Try to access the class globally first
91+
constructor = topLevel[className];
92+
93+
// If that didn't work, try eval
94+
if (!constructor) {
95+
constructor = eval(className);
96+
}
97+
98+
// Lastly, if there is a default attribute try that
99+
if (constructor && constructor['default']) {
100+
constructor = constructor['default'];
101+
}
102+
103+
return constructor;
104+
}
105+
106+
107+
/***/ }),
108+
/* 1 */
81109
/***/ (function(module, exports, __webpack_require__) {
82110

83111
var nativeEvents = __webpack_require__(7)
@@ -118,58 +146,26 @@ module.exports = function(ujs) {
118146
}
119147

120148

121-
/***/ }),
122-
/* 1 */
123-
/***/ (function(module, exports) {
124-
125-
// Assume className is simple and can be found at top-level (window).
126-
// Fallback to eval to handle cases like 'My.React.ComponentName'.
127-
// Also, try to gracefully import Babel 6 style default exports
128-
var topLevel = typeof window === "undefined" ? this : window;
129-
130-
module.exports = function(className) {
131-
var constructor;
132-
// Try to access the class globally first
133-
constructor = topLevel[className];
134-
135-
// If that didn't work, try eval
136-
if (!constructor) {
137-
constructor = eval(className);
138-
}
139-
140-
// Lastly, if there is a default attribute try that
141-
if (constructor && constructor['default']) {
142-
constructor = constructor['default'];
143-
}
144-
145-
return constructor;
146-
}
147-
148-
149149
/***/ }),
150150
/* 2 */
151-
/***/ (function(module, exports) {
151+
/***/ (function(module, exports, __webpack_require__) {
152+
153+
// Make a function which:
154+
// - First tries to require the name
155+
// - Then falls back to global lookup
156+
var fromGlobal = __webpack_require__(0)
157+
var fromRequireContext = __webpack_require__(12)
152158

153-
// Load React components by requiring them from "components/", for example:
154-
//
155-
// - "pages/index" -> `require("components/pages/index")`
156-
// - "pages/show.Header" -> `require("components/pages/show").Header`
157-
// - "pages/show.Body.Content" -> `require("components/pages/show").Body.Content`
158-
//
159159
module.exports = function(reqctx) {
160+
var fromCtx = fromRequireContext(reqctx)
160161
return function(className) {
161-
var parts = className.split(".")
162-
var filename = parts.shift()
163-
var keys = parts
164-
// Load the module:
165-
var component = reqctx("./" + filename)
166-
// Then access each key:
167-
keys.forEach(function(k) {
168-
component = component[k]
169-
})
170-
// support `export default`
171-
if (component.__esModule) {
172-
component = component["default"]
162+
var component;
163+
try {
164+
// `require` will raise an error if this className isn't found:
165+
component = fromCtx(className)
166+
} catch (err) {
167+
// fallback to global:
168+
component = fromGlobal(className)
173169
}
174170
return component
175171
}
@@ -202,9 +198,9 @@ var React = __webpack_require__(3)
202198
var ReactDOM = __webpack_require__(4)
203199
var ReactDOMServer = __webpack_require__(5)
204200

205-
var detectEvents = __webpack_require__(0)
206-
var constructorFromGlobal = __webpack_require__(1)
207-
var constructorFromRequireContext = __webpack_require__(2)
201+
var detectEvents = __webpack_require__(1)
202+
var constructorFromGlobal = __webpack_require__(0)
203+
var constructorFromRequireContextWithGlobalFallback = __webpack_require__(2)
208204

209205
var ReactRailsUJS = {
210206
// This attribute holds the name of component which should be mounted
@@ -255,8 +251,8 @@ var ReactRailsUJS = {
255251
// the default is ReactRailsUJS.ComponentGlobal
256252
getConstructor: constructorFromGlobal,
257253

258-
loadContext: function(req) {
259-
this.getConstructor = constructorFromRequireContext(req)
254+
useContext: function(req) {
255+
this.getConstructor = constructorFromRequireContextWithGlobalFallback(req)
260256
},
261257

262258
// Render `componentName` with `props` to a string,
@@ -360,8 +356,9 @@ module.exports = {
360356
module.exports = {
361357
// Turbolinks 5+ got rid of named events (?!)
362358
setup: function(ujs) {
363-
ujs.handleEvent('turbolinks:load', function() { ujs.mountComponents() });
364-
ujs.handleEvent('turbolinks:before-render', function() { ujs.unmountComponents() });
359+
ujs.handleEvent('DOMContentLoaded', function() { ujs.mountComponents() })
360+
ujs.handleEvent('turbolinks:render', function() { ujs.mountComponents() })
361+
ujs.handleEvent('turbolinks:before-render', function() { ujs.unmountComponents() })
365362
},
366363
}
367364

@@ -397,6 +394,36 @@ module.exports = {
397394
}
398395

399396

397+
/***/ }),
398+
/* 12 */
399+
/***/ (function(module, exports) {
400+
401+
// Load React components by requiring them from "components/", for example:
402+
//
403+
// - "pages/index" -> `require("components/pages/index")`
404+
// - "pages/show.Header" -> `require("components/pages/show").Header`
405+
// - "pages/show.Body.Content" -> `require("components/pages/show").Body.Content`
406+
//
407+
module.exports = function(reqctx) {
408+
return function(className) {
409+
var parts = className.split(".")
410+
var filename = parts.shift()
411+
var keys = parts
412+
// Load the module:
413+
var component = reqctx("./" + filename)
414+
// Then access each key:
415+
keys.forEach(function(k) {
416+
component = component[k]
417+
})
418+
// support `export default`
419+
if (component.__esModule) {
420+
component = component["default"]
421+
}
422+
return component
423+
}
424+
}
425+
426+
400427
/***/ })
401428
/******/ ]);
402429
});

react_ujs/src/events/turbolinks.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
module.exports = {
22
// Turbolinks 5+ got rid of named events (?!)
33
setup: function(ujs) {
4-
ujs.handleEvent('turbolinks:load', function() { ujs.mountComponents() });
5-
ujs.handleEvent('turbolinks:before-render', function() { ujs.unmountComponents() });
4+
ujs.handleEvent('DOMContentLoaded', function() { ujs.mountComponents() })
5+
ujs.handleEvent('turbolinks:render', function() { ujs.mountComponents() })
6+
ujs.handleEvent('turbolinks:before-render', function() { ujs.unmountComponents() })
67
},
78
}

test/test_helper.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@
3232
# `page.driver.debug` will cause Poltergeist to open a browser window
3333
inspector: true,
3434
# hide warnings from React.js whitespace changes:
35-
js_errors: false,
35+
# js_errors: false,
3636
}
3737
Capybara::Poltergeist::Driver.new(app, poltergeist_options)
3838
end

0 commit comments

Comments
 (0)