-
Notifications
You must be signed in to change notification settings - Fork 1.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Support React on Rails by merging Webpacker Lite #601
Changes from all commits
afe9c99
41cda6a
b73fa8e
c71bd6f
4cf3fca
23c1f23
4498a48
5740921
32ff0d0
5599fd6
bb71faa
96fa67e
fe292e6
e4337db
d523fb9
007e36e
7f7fcac
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,5 @@ | ||
/.bundle | ||
/pkg | ||
/test/test_app/log | ||
/test/test_app/tmp | ||
node_modules |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -33,6 +33,7 @@ development: | |
host: localhost | ||
port: 8080 | ||
https: false | ||
hmr: false | ||
|
||
test: | ||
<<: *default | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
module Webpacker::DevServer | ||
extend self | ||
|
||
def running? | ||
socket = Socket.tcp(host, port, connect_timeout: 1) | ||
socket.close | ||
true | ||
|
||
rescue Errno::ECONNREFUSED, NoMethodError | ||
false | ||
end | ||
|
||
def hmr? | ||
case ENV["WEBPACKER_HMR"] | ||
when /true/i then true | ||
when /false/i then false | ||
else fetch(:hmr) | ||
end | ||
|
||
rescue NoMethodError | ||
false | ||
end | ||
|
||
def host | ||
fetch(:host) | ||
end | ||
|
||
def port | ||
fetch(:port) | ||
end | ||
|
||
def https? | ||
fetch(:https) | ||
end | ||
|
||
def protocol | ||
https? ? "https" : "http" | ||
end | ||
|
||
def base_url | ||
"#{protocol}://#{host}:#{port}" | ||
end | ||
|
||
def fetch(key) | ||
Webpacker::Configuration.data[:dev_server][key] || Webpacker::Configuration.defaults[:dev_server][key] | ||
end | ||
end |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -17,31 +17,90 @@ def file_path | |
Webpacker::Configuration.manifest_path | ||
end | ||
|
||
def lookup(name) | ||
# Converts the "name" (aka the pack or bundle name) to to the full path for use in a browser. | ||
def pack_path(name) | ||
relative_pack_path = "#{Webpacker::Configuration.public_output_path}/#{lookup(name)}" | ||
|
||
if Webpacker::DevServer.running? | ||
"#{Webpacker::DevServer.base_url}/#{relative_pack_path}" | ||
else | ||
relative_pack_path.starts_with?("/") ? relative_pack_path : "/#{relative_pack_path}" | ||
end | ||
end | ||
|
||
# Converts the "name" (aka the pack or bundle name) to the possibly hashed name per a manifest. | ||
# | ||
# If Configuration.compile? then compilation is invoked the file is missing. | ||
# | ||
# Options | ||
# throw_if_missing: default is true. If false, then nill is returned if the file is missing. | ||
def lookup(name, throw_if_missing: true) | ||
instance.confirm_manifest_exists | ||
|
||
if Webpacker::Configuration.compile? | ||
compile_and_find!(name) | ||
compile_and_find!(name, throw_if_missing: throw_if_missing) | ||
else | ||
find!(name) | ||
# Since load checks a `mtime` on the manifest for a non-production env before loading, | ||
# we should always call this before a call to `find!` since one may be using | ||
# `webpack -w` and a file may have been added to the manifest since Rails first started. | ||
load | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We're not going to want to do a file stat in production. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @dhh There's no file stat in production. The code checks the Rails.env. Does that meet your concern here? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Forgive the drive-by comment, but framework code should not be directly checking the environment: we have a config subsystem for that. People often have a (More locally-relevant, this should likely use the file watcher to avoid the stat [where possible] even in development.) |
||
raise Webpacker::FileLoader::FileLoaderError.new("Webpacker::Manifest.load must be called first") unless instance | ||
|
||
return find!(name, throw_if_missing: throw_if_missing) | ||
end | ||
end | ||
|
||
# Why does this method exist? Testing? It's not in the README | ||
def lookup_path(name) | ||
Rails.root.join(File.join(Webpacker::Configuration.public_path, lookup(name))) | ||
Rails.root.join(File.join(Webpacker::Configuration.output_path, lookup(name))) | ||
end | ||
|
||
private | ||
def find!(name) | ||
def missing_file_from_manifest_error(bundle_name) | ||
msg = <<-MSG | ||
Webpacker can't find #{bundle_name} in your manifest at #{file_path}. Possible causes: | ||
1. You are hot reloading. | ||
2. You want to set Configuration.compile to true for your environment. | ||
3. Webpack has not re-run to reflect updates. | ||
4. You have misconfigured Webpacker's config/webpacker.yml file. | ||
5. Your Webpack configuration is not creating a manifest. | ||
Your manifest contains: | ||
#{instance.data.to_json} | ||
MSG | ||
raise(Webpacker::FileLoader::NotFoundError.new(msg)) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. this is great 👍 🍰 |
||
end | ||
|
||
def missing_manifest_file_error(path_object) | ||
msg = <<-MSG | ||
Webpacker can't find the manifest file: #{path_object} | ||
Possible causes: | ||
1. You have not invoked webpack. | ||
2. You have misconfigured Webpacker's config/webpacker_.yml file. | ||
3. Your Webpack configuration is not creating a manifest. | ||
MSG | ||
raise(Webpacker::FileLoader::NotFoundError.new(msg)) | ||
end | ||
|
||
def find!(name, throw_if_missing: true) | ||
ensure_loaded_instance(self) | ||
instance.data[name.to_s] || | ||
raise(Webpacker::FileLoader::NotFoundError.new("Can't find #{name} in #{file_path}. Is webpack still compiling?")) | ||
value = instance.data[name.to_s] | ||
return value if value.present? | ||
|
||
if throw_if_missing | ||
missing_file_from_manifest_error(name) | ||
end | ||
end | ||
|
||
def compile_and_find!(name) | ||
def compile_and_find!(name, throw_if_missing: true) | ||
Webpacker.logger.tagged("Webpacker") { Webpacker.compile } | ||
find!(name) | ||
find!(name, throw_if_missing: throw_if_missing) | ||
end | ||
end | ||
|
||
def confirm_manifest_exists | ||
raise missing_manifest_file_error(@path) unless File.exist?(@path) | ||
end | ||
|
||
private | ||
def load | ||
return super unless File.exist?(@path) | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Webpacker::Env
already does this - https://github.com/shakacode/webpacker/blob/4cf3fcab5c03203216be7ab0b7f161b591908174/lib/webpacker/env.rb#L19so if we just call
Webpacker.env.production?
it would be same thing as thisThere was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@gauravtiwari are you sure that would work since you're creating a circular dependency amongst the files. I don't think so but if you're sure, I'll try.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh yes, totally missed 👍