react_on_rails 11.1.7 → 11.3.1.beta.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.eslintrc +8 -2
- data/.prettierignore +1 -0
- data/.prettierrc +20 -0
- data/.release-it.json +3 -0
- data/.travis.yml +10 -9
- data/CHANGELOG.md +60 -3
- data/CONTRIBUTING.md +2 -10
- data/Gemfile +1 -2
- data/Gemfile.rails32 +0 -1
- data/README.md +30 -14
- data/SUMMARY.md +6 -2
- data/docs/additional-reading/{hot-reloading-rails-development.md → hot-reloading-rails-development-asset-pipeline.md} +2 -12
- data/docs/additional-reading/images.md +1 -1
- data/docs/additional-reading/rails_view_rendering_from_inline_javascript.md +2 -1
- data/docs/additional-reading/upgrade-webpacker-v3-to-v4.md +10 -0
- data/docs/api/view-helpers-api.md +12 -8
- data/docs/basics/configuration.md +4 -4
- data/docs/basics/generator-details.md +1 -1
- data/docs/basics/minitest-configuration.md +31 -0
- data/docs/basics/react-server-rendering.md +3 -1
- data/docs/basics/recommended-project-structure.md +24 -1
- data/docs/basics/rspec-configuration.md +2 -2
- data/docs/basics/upgrading-react-on-rails.md +11 -1
- data/docs/basics/webpack-configuration.md +11 -0
- data/docs/misc-pending/code-splitting.md +2 -2
- data/docs/misc-pending/manual-installation-overview.md +1 -1
- data/docs/testimonials/hvmn.md +25 -0
- data/docs/testimonials/resortpass.md +13 -0
- data/docs/testimonials/testimonials.md +28 -0
- data/docs/tutorial.md +123 -11
- data/lib/generators/react_on_rails/dev_tests_generator.rb +1 -0
- data/lib/generators/react_on_rails/install_generator.rb +2 -0
- data/lib/react_on_rails.rb +1 -0
- data/lib/react_on_rails/assets_precompile.rb +3 -0
- data/lib/react_on_rails/configuration.rb +2 -1
- data/lib/react_on_rails/git_utils.rb +2 -0
- data/lib/react_on_rails/helper.rb +71 -70
- data/lib/react_on_rails/json_output.rb +1 -1
- data/lib/react_on_rails/locales_to_js.rb +2 -0
- data/lib/react_on_rails/react_component/render_options.rb +4 -0
- data/lib/react_on_rails/server_rendering_js_code.rb +42 -0
- data/lib/react_on_rails/server_rendering_pool/ruby_embedded_java_script.rb +44 -14
- data/lib/react_on_rails/utils.rb +5 -1
- data/lib/react_on_rails/version.rb +1 -1
- data/lib/react_on_rails/version_checker.rb +4 -1
- data/lib/react_on_rails/webpacker_utils.rb +9 -1
- data/package-scripts.yml +46 -0
- data/package.json +24 -15
- data/rakelib/release.rake +3 -2
- data/react_on_rails.gemspec +1 -1
- data/webpackConfigLoader.js +2 -2
- data/yarn.lock +4431 -1689
- metadata +18 -10
- data/docs/testimonials.md +0 -11
@@ -36,6 +36,7 @@ module ReactOnRails
|
|
36
36
|
|
37
37
|
def replace_prerender_if_server_rendering
|
38
38
|
return unless options.example_server_rendering
|
39
|
+
|
39
40
|
hello_world_index = File.join(destination_root, "app", "views", "hello_world", "index.html.erb")
|
40
41
|
hello_world_contents = File.read(hello_world_index)
|
41
42
|
new_hello_world_contents = hello_world_contents.gsub(/prerender: false/,
|
@@ -62,6 +62,7 @@ module ReactOnRails
|
|
62
62
|
|
63
63
|
def missing_yarn?
|
64
64
|
return false unless ReactOnRails::Utils.running_on_windows? ? `where yarn`.blank? : `which yarn`.blank?
|
65
|
+
|
65
66
|
error = "yarn is required. Please install it before continuing. https://yarnpkg.com/en/docs/install"
|
66
67
|
GeneratorMessages.add_error(error)
|
67
68
|
true
|
@@ -69,6 +70,7 @@ module ReactOnRails
|
|
69
70
|
|
70
71
|
def missing_node?
|
71
72
|
return false unless ReactOnRails::Utils.running_on_windows? ? `where node`.blank? : `which node`.blank?
|
73
|
+
|
72
74
|
error = "** nodejs is required. Please install it before continuing. https://nodejs.org/en/"
|
73
75
|
GeneratorMessages.add_error(error)
|
74
76
|
true
|
data/lib/react_on_rails.rb
CHANGED
@@ -11,6 +11,7 @@ require "react_on_rails/version"
|
|
11
11
|
require "react_on_rails/version_checker"
|
12
12
|
require "react_on_rails/configuration"
|
13
13
|
require "react_on_rails/server_rendering_pool"
|
14
|
+
require "react_on_rails/server_rendering_js_code"
|
14
15
|
require "react_on_rails/engine"
|
15
16
|
require "react_on_rails/react_component/render_options"
|
16
17
|
require "react_on_rails/version_syntax_converter"
|
@@ -64,6 +64,7 @@ module ReactOnRails
|
|
64
64
|
# references from webpack's CSS would be invalid. The fix is to symlink the double-digested
|
65
65
|
# file back to the original digested name, and make a similar symlink for the gz version.
|
66
66
|
return unless @symlink_non_digested_assets_regex
|
67
|
+
|
67
68
|
manifest_glob = Dir.glob(@assets_path.join(".sprockets-manifest-*.json")) +
|
68
69
|
Dir.glob(@assets_path.join("manifest-*.json")) +
|
69
70
|
Dir.glob(@assets_path.join("manifest.yml"))
|
@@ -86,6 +87,7 @@ module ReactOnRails
|
|
86
87
|
manifest_data.each do |original_filename, rails_digested_filename|
|
87
88
|
# TODO: we should remove any original_filename that is NOT in the webpack deploy folder.
|
88
89
|
next unless original_filename =~ @symlink_non_digested_assets_regex
|
90
|
+
|
89
91
|
# We're symlinking from the digested filename back to the original filename which has
|
90
92
|
# already been symlinked by Webpack
|
91
93
|
symlink_file(rails_digested_filename, original_filename)
|
@@ -100,6 +102,7 @@ module ReactOnRails
|
|
100
102
|
def delete_broken_symlinks
|
101
103
|
Dir.glob(@assets_path.join("*")).each do |filename|
|
102
104
|
next unless File.lstat(filename).symlink?
|
105
|
+
|
103
106
|
begin
|
104
107
|
target = File.readlink(filename)
|
105
108
|
rescue StandardError
|
@@ -21,7 +21,7 @@ module ReactOnRails
|
|
21
21
|
prerender: false,
|
22
22
|
replay_console: true,
|
23
23
|
logging_on_server: true,
|
24
|
-
raise_on_prerender_error:
|
24
|
+
raise_on_prerender_error: Rails.env.development?,
|
25
25
|
trace: Rails.env.development?,
|
26
26
|
development_mode: Rails.env.development?,
|
27
27
|
server_renderer_pool_size: DEFAULT_POOL_SIZE,
|
@@ -218,6 +218,7 @@ module ReactOnRails
|
|
218
218
|
|
219
219
|
def configure_skip_display_none_deprecation
|
220
220
|
return if skip_display_none.nil?
|
221
|
+
|
221
222
|
Rails.logger.warn "[DEPRECATION] ReactOnRails: remove skip_display_none from configuration."
|
222
223
|
end
|
223
224
|
end
|
@@ -6,8 +6,10 @@ module ReactOnRails
|
|
6
6
|
module GitUtils
|
7
7
|
def self.uncommitted_changes?(message_handler)
|
8
8
|
return false if ENV["COVERAGE"] == "true"
|
9
|
+
|
9
10
|
status = `git status --porcelain`
|
10
11
|
return false if $CHILD_STATUS.success? && status.empty?
|
12
|
+
|
11
13
|
error = if !$CHILD_STATUS.success?
|
12
14
|
"You do not have Git installed. Please install Git, and commit your changes before continuing"
|
13
15
|
else
|
@@ -136,7 +136,7 @@ module ReactOnRails
|
|
136
136
|
# It is exactly like react_component except for the following:
|
137
137
|
# 1. prerender: true is automatically added, as this method doesn't make sense for client only
|
138
138
|
# rendering.
|
139
|
-
# 2. Your JavaScript for server rendering must return an Object
|
139
|
+
# 2. Your JavaScript generator function for server rendering must return an Object rather than a React component.
|
140
140
|
# 3. Your view code must expect an object and not a string.
|
141
141
|
#
|
142
142
|
# Here is an example of the view code:
|
@@ -206,6 +206,7 @@ module ReactOnRails
|
|
206
206
|
# that contains a data props.
|
207
207
|
def redux_store_hydration_data
|
208
208
|
return if @registered_stores_defer_render.blank?
|
209
|
+
|
209
210
|
@registered_stores_defer_render.reduce("".dup) do |accum, redux_store_data|
|
210
211
|
accum << render_redux_store_data(redux_store_data)
|
211
212
|
end.html_safe
|
@@ -265,6 +266,7 @@ module ReactOnRails
|
|
265
266
|
|
266
267
|
def json_safe_and_pretty(hash_or_string)
|
267
268
|
return "{}" if hash_or_string.nil?
|
269
|
+
|
268
270
|
unless hash_or_string.is_a?(String) || hash_or_string.is_a?(Hash)
|
269
271
|
raise ReactOnRails::Error, "#{__method__} only accepts String or Hash as argument "\
|
270
272
|
"(#{hash_or_string.class} given)."
|
@@ -275,6 +277,59 @@ module ReactOnRails
|
|
275
277
|
ReactOnRails::JsonOutput.escape(json_value)
|
276
278
|
end
|
277
279
|
|
280
|
+
# This is the definitive list of the default values used for the rails_context, which is the
|
281
|
+
# second parameter passed to both component and store generator functions.
|
282
|
+
# This method can be called from views and from the controller, as `helpers.rails_context`
|
283
|
+
#
|
284
|
+
# rubocop:disable Metrics/AbcSize
|
285
|
+
def rails_context(server_side: true)
|
286
|
+
@rails_context ||= begin
|
287
|
+
result = {
|
288
|
+
railsEnv: Rails.env,
|
289
|
+
inMailer: in_mailer?,
|
290
|
+
# Locale settings
|
291
|
+
i18nLocale: I18n.locale,
|
292
|
+
i18nDefaultLocale: I18n.default_locale,
|
293
|
+
rorVersion: ReactOnRails::VERSION,
|
294
|
+
rorPro: ReactOnRails::Utils.react_on_rails_pro?
|
295
|
+
}
|
296
|
+
if defined?(request) && request.present?
|
297
|
+
# Check for encoding of the request's original_url and try to force-encoding the
|
298
|
+
# URLs as UTF-8. This situation can occur in browsers that do not encode the
|
299
|
+
# entire URL as UTF-8 already, mostly on the Windows platform (IE11 and lower).
|
300
|
+
original_url_normalized = request.original_url
|
301
|
+
if original_url_normalized.encoding.to_s == "ASCII-8BIT"
|
302
|
+
original_url_normalized = original_url_normalized.force_encoding("ISO-8859-1").encode("UTF-8")
|
303
|
+
end
|
304
|
+
|
305
|
+
# Using Addressable instead of standard URI to better deal with
|
306
|
+
# non-ASCII characters (see https://github.com/shakacode/react_on_rails/pull/405)
|
307
|
+
uri = Addressable::URI.parse(original_url_normalized)
|
308
|
+
# uri = Addressable::URI.parse("http://foo.com:3000/posts?id=30&limit=5#time=1305298413")
|
309
|
+
|
310
|
+
result.merge!(
|
311
|
+
# URL settings
|
312
|
+
href: uri.to_s,
|
313
|
+
location: "#{uri.path}#{uri.query.present? ? "?#{uri.query}" : ''}",
|
314
|
+
scheme: uri.scheme, # http
|
315
|
+
host: uri.host, # foo.com
|
316
|
+
port: uri.port,
|
317
|
+
pathname: uri.path, # /posts
|
318
|
+
search: uri.query, # id=30&limit=5
|
319
|
+
httpAcceptLanguage: request.env["HTTP_ACCEPT_LANGUAGE"]
|
320
|
+
)
|
321
|
+
end
|
322
|
+
if ReactOnRails.configuration.rendering_extension
|
323
|
+
custom_context = ReactOnRails.configuration.rendering_extension.custom_context(self)
|
324
|
+
result.merge!(custom_context) if custom_context
|
325
|
+
end
|
326
|
+
result
|
327
|
+
end
|
328
|
+
|
329
|
+
@rails_context.merge(serverSide: server_side)
|
330
|
+
end
|
331
|
+
# rubocop:enable Metrics/AbcSize
|
332
|
+
|
278
333
|
private
|
279
334
|
|
280
335
|
def build_react_component_result_for_server_rendered_string(
|
@@ -284,9 +339,15 @@ module ReactOnRails
|
|
284
339
|
render_options: required("render_options")
|
285
340
|
)
|
286
341
|
content_tag_options = render_options.html_options
|
342
|
+
if content_tag_options.key?(:tag)
|
343
|
+
content_tag_options_html_tag = content_tag_options[:tag]
|
344
|
+
content_tag_options.delete(:tag)
|
345
|
+
else
|
346
|
+
content_tag_options_html_tag = "div"
|
347
|
+
end
|
287
348
|
content_tag_options[:id] = render_options.dom_id
|
288
349
|
|
289
|
-
rendered_output = content_tag(
|
350
|
+
rendered_output = content_tag(content_tag_options_html_tag.to_sym,
|
290
351
|
server_rendered_html.html_safe,
|
291
352
|
content_tag_options)
|
292
353
|
|
@@ -431,22 +492,13 @@ module ReactOnRails
|
|
431
492
|
#
|
432
493
|
# Read more here: http://timelessrepo.com/json-isnt-a-javascript-subset
|
433
494
|
|
434
|
-
|
435
|
-
|
436
|
-
(
|
437
|
-
|
438
|
-
|
439
|
-
|
440
|
-
|
441
|
-
name: '#{react_component_name}',
|
442
|
-
domNodeId: '#{render_options.dom_id}',
|
443
|
-
props: props,
|
444
|
-
trace: #{render_options.trace},
|
445
|
-
railsContext: railsContext
|
446
|
-
});
|
447
|
-
})()
|
448
|
-
JS
|
449
|
-
# rubocop:enable Layout/IndentHeredoc
|
495
|
+
js_code = ReactOnRails::ServerRenderingJsCode.server_rendering_component_js_code(
|
496
|
+
props_string: props_string(props).gsub("\u2028", '\u2028').gsub("\u2029", '\u2029'),
|
497
|
+
rails_context: rails_context(server_side: true).to_json,
|
498
|
+
redux_stores: initialize_redux_stores,
|
499
|
+
react_component_name: react_component_name,
|
500
|
+
render_options: render_options
|
501
|
+
)
|
450
502
|
|
451
503
|
begin
|
452
504
|
result = ReactOnRails::ServerRenderingPool.server_render_js_with_console_logging(js_code, render_options)
|
@@ -478,6 +530,7 @@ module ReactOnRails
|
|
478
530
|
JS
|
479
531
|
|
480
532
|
return result unless @registered_stores.present? || @registered_stores_defer_render.present?
|
533
|
+
|
481
534
|
declarations = "var reduxProps, store, storeGenerator;\n".dup
|
482
535
|
all_stores = (@registered_stores || []) + (@registered_stores_defer_render || [])
|
483
536
|
|
@@ -494,58 +547,6 @@ module ReactOnRails
|
|
494
547
|
result
|
495
548
|
end
|
496
549
|
|
497
|
-
# This is the definitive list of the default values used for the rails_context, which is the
|
498
|
-
# second parameter passed to both component and store generator functions.
|
499
|
-
# rubocop:disable Metrics/AbcSize
|
500
|
-
def rails_context(server_side: required("server_side"))
|
501
|
-
@rails_context ||= begin
|
502
|
-
result = {
|
503
|
-
railsEnv: Rails.env,
|
504
|
-
inMailer: in_mailer?,
|
505
|
-
# Locale settings
|
506
|
-
i18nLocale: I18n.locale,
|
507
|
-
i18nDefaultLocale: I18n.default_locale,
|
508
|
-
rorVersion: ReactOnRails::VERSION,
|
509
|
-
rorPro: ReactOnRails::Utils.react_on_rails_pro?
|
510
|
-
}
|
511
|
-
if defined?(request) && request.present?
|
512
|
-
# Check for encoding of the request's original_url and try to force-encoding the
|
513
|
-
# URLs as UTF-8. This situation can occur in browsers that do not encode the
|
514
|
-
# entire URL as UTF-8 already, mostly on the Windows platform (IE11 and lower).
|
515
|
-
original_url_normalized = request.original_url
|
516
|
-
if original_url_normalized.encoding.to_s == "ASCII-8BIT"
|
517
|
-
original_url_normalized = original_url_normalized.force_encoding("ISO-8859-1").encode("UTF-8")
|
518
|
-
end
|
519
|
-
|
520
|
-
# Using Addressable instead of standard URI to better deal with
|
521
|
-
# non-ASCII characters (see https://github.com/shakacode/react_on_rails/pull/405)
|
522
|
-
uri = Addressable::URI.parse(original_url_normalized)
|
523
|
-
# uri = Addressable::URI.parse("http://foo.com:3000/posts?id=30&limit=5#time=1305298413")
|
524
|
-
|
525
|
-
result.merge!(
|
526
|
-
# URL settings
|
527
|
-
href: uri.to_s,
|
528
|
-
location: "#{uri.path}#{uri.query.present? ? "?#{uri.query}" : ''}",
|
529
|
-
scheme: uri.scheme, # http
|
530
|
-
host: uri.host, # foo.com
|
531
|
-
port: uri.port,
|
532
|
-
pathname: uri.path, # /posts
|
533
|
-
search: uri.query, # id=30&limit=5
|
534
|
-
httpAcceptLanguage: request.env["HTTP_ACCEPT_LANGUAGE"]
|
535
|
-
)
|
536
|
-
end
|
537
|
-
if ReactOnRails.configuration.rendering_extension
|
538
|
-
custom_context = ReactOnRails.configuration.rendering_extension.custom_context(self)
|
539
|
-
result.merge!(custom_context) if custom_context
|
540
|
-
end
|
541
|
-
result
|
542
|
-
end
|
543
|
-
|
544
|
-
@rails_context.merge(serverSide: server_side)
|
545
|
-
end
|
546
|
-
|
547
|
-
# rubocop:enable Metrics/AbcSize
|
548
|
-
|
549
550
|
def replay_console_option(val)
|
550
551
|
val.nil? ? ReactOnRails.configuration.replay_console : val
|
551
552
|
end
|
@@ -11,7 +11,7 @@ module ReactOnRails
|
|
11
11
|
"\u2028" => '\u2028',
|
12
12
|
"\u2029" => '\u2029'
|
13
13
|
}.freeze
|
14
|
-
ESCAPE_REGEXP = /[\u2028\u2029&><]/u
|
14
|
+
ESCAPE_REGEXP = /[\u2028\u2029&><]/u.freeze
|
15
15
|
|
16
16
|
def self.escape(json)
|
17
17
|
return escape_without_erb_util(json) if Utils.rails_version_less_than_4_1_1
|
@@ -7,6 +7,7 @@ module ReactOnRails
|
|
7
7
|
def initialize
|
8
8
|
return if i18n_dir.nil?
|
9
9
|
return unless obsolete?
|
10
|
+
|
10
11
|
@translations, @defaults = generate_translations
|
11
12
|
convert
|
12
13
|
end
|
@@ -15,6 +16,7 @@ module ReactOnRails
|
|
15
16
|
|
16
17
|
def obsolete?
|
17
18
|
return true if exist_js_files.empty?
|
19
|
+
|
18
20
|
js_files_are_outdated
|
19
21
|
end
|
20
22
|
|
@@ -0,0 +1,42 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module ReactOnRails
|
4
|
+
module ServerRenderingJsCode
|
5
|
+
class << self
|
6
|
+
def js_code_renderer
|
7
|
+
@js_code_renderer ||= if ReactOnRails::Utils.react_on_rails_pro?
|
8
|
+
ReactOnRailsPro::ServerRenderingJsCode
|
9
|
+
else
|
10
|
+
self
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
def server_rendering_component_js_code(
|
15
|
+
props_string: nil,
|
16
|
+
rails_context: nil,
|
17
|
+
redux_stores: nil,
|
18
|
+
react_component_name: nil,
|
19
|
+
render_options: nil
|
20
|
+
)
|
21
|
+
js_code_renderer.render(props_string, rails_context, redux_stores, react_component_name, render_options)
|
22
|
+
end
|
23
|
+
|
24
|
+
def render(props_string, rails_context, redux_stores, react_component_name, render_options)
|
25
|
+
<<-JS
|
26
|
+
(function() {
|
27
|
+
var railsContext = #{rails_context};
|
28
|
+
#{redux_stores}
|
29
|
+
var props = #{props_string};
|
30
|
+
return ReactOnRails.serverRenderReactComponent({
|
31
|
+
name: '#{react_component_name}',
|
32
|
+
domNodeId: '#{render_options.dom_id}',
|
33
|
+
props: props,
|
34
|
+
trace: #{render_options.trace},
|
35
|
+
railsContext: railsContext
|
36
|
+
});
|
37
|
+
})()
|
38
|
+
JS
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
@@ -4,7 +4,9 @@ require "open-uri"
|
|
4
4
|
|
5
5
|
module ReactOnRails
|
6
6
|
module ServerRenderingPool
|
7
|
+
# rubocop:disable Metrics/ClassLength
|
7
8
|
class RubyEmbeddedJavaScript
|
9
|
+
# rubocop:enable Metrics/ClassLength
|
8
10
|
class << self
|
9
11
|
def reset_pool
|
10
12
|
options = {
|
@@ -17,12 +19,17 @@ module ReactOnRails
|
|
17
19
|
def reset_pool_if_server_bundle_was_modified
|
18
20
|
return unless ReactOnRails.configuration.development_mode
|
19
21
|
|
20
|
-
|
21
|
-
|
22
|
-
return if @server_bundle_timestamp == file_mtime
|
22
|
+
if ReactOnRails::Utils.server_bundle_path_is_http?
|
23
|
+
return if @server_bundle_url == ReactOnRails::Utils.server_bundle_js_file_path
|
23
24
|
|
24
|
-
|
25
|
+
@server_bundle_url = ReactOnRails::Utils.server_bundle_js_file_path
|
26
|
+
else
|
27
|
+
file_mtime = File.mtime(ReactOnRails::Utils.server_bundle_js_file_path)
|
28
|
+
@server_bundle_timestamp ||= file_mtime
|
29
|
+
return if @server_bundle_timestamp == file_mtime
|
25
30
|
|
31
|
+
@server_bundle_timestamp = file_mtime
|
32
|
+
end
|
26
33
|
ReactOnRails::ServerRenderingPool.reset_pool
|
27
34
|
end
|
28
35
|
|
@@ -72,6 +79,7 @@ module ReactOnRails
|
|
72
79
|
|
73
80
|
def trace_js_code_used(msg, js_code, file_name = "tmp/server-generated.js", force: false)
|
74
81
|
return unless ReactOnRails.configuration.trace || force
|
82
|
+
|
75
83
|
# Set to anything to print generated code.
|
76
84
|
File.write(file_name, js_code)
|
77
85
|
msg = <<-MSG.strip_heredoc
|
@@ -95,19 +103,25 @@ module ReactOnRails
|
|
95
103
|
end
|
96
104
|
end
|
97
105
|
|
106
|
+
def read_bundle_js_code
|
107
|
+
server_js_file = ReactOnRails::Utils.server_bundle_js_file_path
|
108
|
+
if ReactOnRails::Utils.server_bundle_path_is_http?
|
109
|
+
file_url_to_string(server_js_file)
|
110
|
+
else
|
111
|
+
File.read(server_js_file)
|
112
|
+
end
|
113
|
+
rescue StandardError => e
|
114
|
+
msg = "You specified server rendering JS file: #{server_js_file}, but it cannot be "\
|
115
|
+
"read. You may set the server_bundle_js_file in your configuration to be \"\" to "\
|
116
|
+
"avoid this warning.\nError is: #{e}"
|
117
|
+
raise ReactOnRails::Error, msg
|
118
|
+
end
|
119
|
+
|
98
120
|
def create_js_context
|
99
121
|
return if ReactOnRails.configuration.server_bundle_js_file.blank?
|
100
122
|
|
101
|
-
|
123
|
+
bundle_js_code = read_bundle_js_code
|
102
124
|
|
103
|
-
begin
|
104
|
-
bundle_js_code = File.read(server_js_file)
|
105
|
-
rescue StandardError => e
|
106
|
-
msg = "You specified server rendering JS file: #{server_js_file}, but it cannot be "\
|
107
|
-
"read. You may set the server_bundle_js_file in your configuration to be \"\" to "\
|
108
|
-
"avoid this warning.\nError is: #{e}"
|
109
|
-
raise ReactOnRails::Error, msg
|
110
|
-
end
|
111
125
|
# rubocop:disable Layout/IndentHeredoc
|
112
126
|
base_js_code = <<-JS
|
113
127
|
#{console_polyfill}
|
@@ -118,7 +132,10 @@ module ReactOnRails
|
|
118
132
|
file_name = "tmp/base_js_code.js"
|
119
133
|
begin
|
120
134
|
if ReactOnRails.configuration.trace
|
121
|
-
Rails.logger.info
|
135
|
+
Rails.logger.info do
|
136
|
+
"[react_on_rails] Created JavaScript context with file "\
|
137
|
+
"#{ReactOnRails::Utils.server_bundle_js_file_path}"
|
138
|
+
end
|
122
139
|
end
|
123
140
|
ExecJS.compile(base_js_code)
|
124
141
|
rescue StandardError => e
|
@@ -189,6 +206,19 @@ var console = { history: [] };
|
|
189
206
|
JS
|
190
207
|
# rubocop:enable Layout/IndentHeredoc
|
191
208
|
end
|
209
|
+
|
210
|
+
private
|
211
|
+
|
212
|
+
def file_url_to_string(url)
|
213
|
+
response = Net::HTTP.get_response(URI.parse(url))
|
214
|
+
content_type_header = response["content-type"]
|
215
|
+
match = content_type_header.match(/\A.*; charset=(?<encoding>.*)\z/)
|
216
|
+
encoding_type = match[:encoding]
|
217
|
+
response.body.force_encoding(encoding_type)
|
218
|
+
rescue StandardError => e
|
219
|
+
msg = "file_url_to_string #{url} failed\nError is: #{e}"
|
220
|
+
raise ReactOnRails::Error, msg
|
221
|
+
end
|
192
222
|
end
|
193
223
|
end
|
194
224
|
end
|