Skip to content
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

"bundle exec puma" fails: NoMethodError: undefined method `include?' for nil:NilClass" #1344

Closed
bughit opened this issue Jun 26, 2017 · 11 comments

Comments

@bughit
Copy link

bughit commented Jun 26, 2017

vendor/cache/puma-c264e6aba83f/lib/puma/launcher.rb:171:in `run'
vendor/cache/puma-c264e6aba83f/lib/puma/cli.rb:77:in `run'
vendor/cache/puma-c264e6aba83f/bin/puma:10:in `<top (required)>'
vendor/bundle/ruby/2.2.0/bin/puma:23:in `load'
vendor/bundle/ruby/2.2.0/bin/puma:23:in `<top (required)>'"; nil
@stereobooster
Copy link
Contributor

Steps to reproduce or example application would be helpful

@bughit
Copy link
Author

bughit commented Jul 1, 2017

I just ran "bundle exec puma"

lib/puma/launcher.rb:171

env["RUBYOPT"] = [env["RUBYOPT"], bundle].join(" ") unless env["RUBYOPT"].include?(bundle)

this code expects RUBYOPT to be always set, when puma is run via bundler, is that a justified assumption? It wasn't set for me.

@stereobooster
Copy link
Contributor

stereobooster commented Jul 1, 2017

What is the result for (in the same dir as bundle exec puma):

bundle exec ruby -e 'puts ENV["RUBYOPT"]'

@stuartc
Copy link

stuartc commented Jul 4, 2017

I can confirm this issue, if I run rails s or puma without bundle exec I get the error.
However, curious; since rails runner 'puts ENV["RUBYOPT"]' (without bundle exec) returns -rbundler/setup.

@stereobooster
Copy link
Contributor

ruby -v
gem -v
bundle -v
rails -v
puma --version
uname -a

@bughit
Copy link
Author

bughit commented Jul 5, 2017

bundle exec ruby -e 'puts ENV["RUBYOPT"]'
-rbundler/setup

ruby -v
ruby 2.2.2p95 (2015-04-13 revision 50295) [x86_64-linux]

bundle -v
Bundler version 1.15.1

bundle exec rails -v
Rails 4.2.8

(bundle exec) puma -v
NoMethodError: undefined method `include?' for nil:NilClass
# puma is from master (5bbe6f3ba610)

uname -a
Linux alexolinux 4.4.0-83-generic #106~14.04.1-Ubuntu SMP Mon Jun 26 18:10:19 UTC 2017 x86_64 x86_64 x86_64 GNU/Linux

@bughit
Copy link
Author

bughit commented Jul 5, 2017

here's the order of relevant events in a bundle exec puma invocation

  1. bundler captures the ORIGINAL_ENV
    module Bundler
      environment_preserver = EnvironmentPreserver.new(ENV, EnvironmentPreserver::BUNDLER_KEYS)
      ORIGINAL_ENV = environment_preserver.restore
    at this point there is no RUBYOPT in the environment
  2. RUBYOPT is set by bundler in Bundler::CLI::Exec#run
  3. without BUNDLE_DISABLE_EXEC_LOAD (which is the default), 'vendor/bundle/ruby/2.2.0/bin/puma" is loaded in-process
  4. puma expects ORIGINAL_ENV["RUBYOPT"] to be present (in lib/puma/launcher.rb:171 env refers to ORIGINAL_ENV)

It's not clear to me how this works for anyone, since puma invocation in a sub-shell is not the default behavior of bundle exec.

@bughit
Copy link
Author

bughit commented Jul 5, 2017

minor issue:

It's probably better not to mutate Bundler::ORIGINAL_ENV but call Bundler::original_env that clones it, or dup it yourself if the constant predates the method.

    def run
      previous_env =
        if defined?(Bundler)
          env = Bundler::ORIGINAL_ENV
          # add -rbundler/setup so we load from Gemfile when restarting
          bundle = "-rbundler/setup"
          env["RUBYOPT"] = [env["RUBYOPT"], bundle].join(" ") unless env["RUBYOPT"].include?(bundle)
          env
        else
          ENV.to_h
        end

@bughit
Copy link
Author

bughit commented Jul 6, 2017

not sure if you'd want to support this scenario, but if puma is started with BUNDLE_DISABLE_EXEC_LOAD=1 bundle exec puma Bundler::ORIGINAL_ENV will already be tainted with BUNDLE_GEMFILE

@wojtodzio
Copy link

wojtodzio commented Jul 6, 2017

I can also confirm this issue - after upgrading Puma from 3.8.2 to 3.9.1 I'm not able to start the server without bundle exec.
As a temporary quick fix, I've added this line:

Bundler::ORIGINAL_ENV['RUBYOPT'] ||= ENV['RUBYOPT']

To my config/puma.rb 😄

@nateberkopec
Copy link
Member

Closed by #1385

dekellum added a commit to dekellum/lionfish that referenced this issue Aug 16, 2017
This reverts commit 853c01d.

No longer needed with fix on puma master

github: puma/puma#1344 puma/puma#1385
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants