phusion / passenger

A fast and robust web server and application server for Ruby, Python and Node.js
https://www.phusionpassenger.com/
MIT License
5.01k stars 548 forks source link

Passenger seems to ignore initializer file while Puma doesn't. #2066

Open netsensei opened 6 years ago

netsensei commented 6 years ago

Issue report

Question 1: What is the problem?

I'm trying to run this application which contains this gem. The gem documentation states that I can change the behaviour of the gem by creating or adapting the initializer file riiif.rb to suit my needs. In my case I'm trying to change the first line with this piece of code:

Riiif::Image.file_resolver = Riiif::FileSystemFileResolver.new(base_path: '/vagrant/images')

(See the original app code)

However, when I boot the app via passenger, fire up a browser and navigate to a page (i.e. http://rails.box:3000/iiif/2/0000_GRO0026_I/full/full/50/default.jpg) while I have an image file called 0000_GRO0026_I.jpg stored in the /vagrant/images folder on my machine, I get a nasty exception:

#<Riiif::ImageNotFoundError: /vagrant/railsapp/tmp/0000_GRO0026_I.{png,jpg,tif,tiff,jp2}>

The riiif gem is looking for my image in the Rails applications tmp/ folder instead of the one I configured in the intializer.

However, when I run the same the same code via Puma with rails server... everything works as expected. The rails app and the gem will play nice and fetch the image from the /vagrant/images location instead of the apps tmp/ folder.

The problem happens when I set up passenger + nginx or when I just run passenger standalone in development mode.

So my question: Why does Passenger seem to ignore my config/initializer/riiif.rb initializer? Is this initializer file even ignored? Why doesn't Puma throw me an error?

I'm running on:

This is the stack trace output:

Started GET "/iiif/2/0000_GRO0026_I/full/full/50/default.jpg" for 192.168.2.1 at 2018-04-17 12:49:43 +0000
Processing by Riiif::ImagesController#show as JPEG
  Parameters: {"rotation"=>"50", "region"=>"full", "quality"=>"default", "model"=>"riiif/image", "id"=>"0000_GRO0026_I", "size"=>"full"}
Completed 404 Not Found in 1ms

Riiif::ImageNotFoundError (/vagrant/railsapp/tmp/0000_GRO0026_I.{png,jpg,tif,tiff,jp2}):

vendor/ruby/2.4.0/gems/riiif-2.0.0/app/resolvers/riiif/abstract_file_system_resolver.rb:28:in `path'
vendor/ruby/2.4.0/gems/riiif-2.0.0/app/resolvers/riiif/abstract_file_system_resolver.rb:21:in `find'
vendor/ruby/2.4.0/gems/riiif-2.0.0/app/models/riiif/image.rb:33:in `file'
vendor/ruby/2.4.0/gems/riiif-2.0.0/app/models/riiif/image.rb:47:in `block in render'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/cache.rb:297:in `block in fetch'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/cache.rb:586:in `block in save_block_result_to_cache'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/cache.rb:555:in `block in instrument'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/notifications.rb:168:in `instrument'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/cache.rb:555:in `instrument'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/cache.rb:585:in `save_block_result_to_cache'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/cache.rb:297:in `fetch'
vendor/ruby/2.4.0/gems/riiif-2.0.0/app/models/riiif/image.rb:46:in `render'
vendor/ruby/2.4.0/gems/riiif-2.0.0/app/controllers/riiif/images_controller.rb:23:in `show'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal/basic_implicit_render.rb:4:in `send_action'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/abstract_controller/base.rb:186:in `process_action'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal/rendering.rb:30:in `process_action'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/abstract_controller/callbacks.rb:20:in `block in process_action'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/callbacks.rb:131:in `run_callbacks'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/abstract_controller/callbacks.rb:19:in `process_action'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal/rescue.rb:20:in `process_action'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal/instrumentation.rb:32:in `block in process_action'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/notifications.rb:166:in `block in instrument'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/notifications/instrumenter.rb:21:in `instrument'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/notifications.rb:166:in `instrument'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal/instrumentation.rb:30:in `process_action'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal/params_wrapper.rb:252:in `process_action'
vendor/ruby/2.4.0/gems/activerecord-5.1.6/lib/active_record/railties/controller_runtime.rb:22:in `process_action'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/abstract_controller/base.rb:124:in `process'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal.rb:189:in `dispatch'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_controller/metal.rb:253:in `dispatch'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/routing/route_set.rb:49:in `dispatch'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/routing/route_set.rb:31:in `serve'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/journey/router.rb:50:in `block in serve'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/journey/router.rb:33:in `each'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/journey/router.rb:33:in `serve'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/routing/route_set.rb:844:in `call'
vendor/ruby/2.4.0/gems/rack-2.0.4/lib/rack/etag.rb:25:in `call'
vendor/ruby/2.4.0/gems/rack-2.0.4/lib/rack/conditional_get.rb:25:in `call'
vendor/ruby/2.4.0/gems/rack-2.0.4/lib/rack/head.rb:12:in `call'
vendor/ruby/2.4.0/gems/activerecord-5.1.6/lib/active_record/migration.rb:556:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/callbacks.rb:26:in `block in call'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/callbacks.rb:97:in `run_callbacks'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/callbacks.rb:24:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/executor.rb:12:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/debug_exceptions.rb:59:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/show_exceptions.rb:31:in `call'
vendor/ruby/2.4.0/gems/railties-5.1.6/lib/rails/rack/logger.rb:36:in `call_app'
vendor/ruby/2.4.0/gems/railties-5.1.6/lib/rails/rack/logger.rb:24:in `block in call'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/tagged_logging.rb:69:in `block in tagged'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/tagged_logging.rb:26:in `tagged'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/tagged_logging.rb:69:in `tagged'
vendor/ruby/2.4.0/gems/railties-5.1.6/lib/rails/rack/logger.rb:24:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/remote_ip.rb:79:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/request_id.rb:25:in `call'
vendor/ruby/2.4.0/gems/rack-2.0.4/lib/rack/runtime.rb:22:in `call'
vendor/ruby/2.4.0/gems/activesupport-5.1.6/lib/active_support/cache/strategy/local_cache_middleware.rb:27:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/executor.rb:12:in `call'
vendor/ruby/2.4.0/gems/actionpack-5.1.6/lib/action_dispatch/middleware/static.rb:125:in `call'
vendor/ruby/2.4.0/gems/rack-2.0.4/lib/rack/sendfile.rb:111:in `call'
vendor/ruby/2.4.0/gems/honeybadger-3.3.0/lib/honeybadger/rack/error_notifier.rb:33:in `block in call'
vendor/ruby/2.4.0/gems/honeybadger-3.3.0/lib/honeybadger/agent.rb:337:in `with_rack_env'
vendor/ruby/2.4.0/gems/honeybadger-3.3.0/lib/honeybadger/rack/error_notifier.rb:30:in `call'
vendor/ruby/2.4.0/gems/honeybadger-3.3.0/lib/honeybadger/rack/user_feedback.rb:31:in `call'
vendor/ruby/2.4.0/gems/honeybadger-3.3.0/lib/honeybadger/rack/user_informer.rb:21:in `call'
vendor/ruby/2.4.0/gems/railties-5.1.6/lib/rails/engine.rb:522:in `call'
passenger (5.2.3) src/ruby_supportlib/phusion_passenger/rack/thread_handler_extension.rb:97:in `process_request'
passenger (5.2.3) src/ruby_supportlib/phusion_passenger/request_handler/thread_handler.rb:152:in `accept_and_process_next_request'
passenger (5.2.3) src/ruby_supportlib/phusion_passenger/request_handler/thread_handler.rb:113:in `main_loop'
passenger (5.2.3) src/ruby_supportlib/phusion_passenger/request_handler.rb:416:in `block (3 levels) in start_threads'
passenger (5.2.3) src/ruby_supportlib/phusion_passenger/utils.rb:113:in `block in create_thread_and_abort_on_exception'
** [Honeybadger] Unable to send error report: API key is missing. id=dfe387b2-8718-41dd-86c3-4a9826994906 level=3 pid=28818

Question 2: Passenger version and integration mode:

Question 3: OS or Linux distro, platform (including version):

Question 4: Passenger installation method:

Question 5: Your app's programming language (including any version managers) and framework (including versions):

Question 6: Are you using a PaaS and/or containerization? If so which one?

No.

Question 7: Anything else about your setup that we should know?

Installing the application is fairly easy:

  1. clone the repo
  2. run bundle install --path vendor
  3. open up config/initializers/riiif.rb in a text editor
  4. Change the first line to Riiif::Image.file_resolver = Riiif::FileSystemFileResolver.new(base_path: '/vagrant/images') (change the path to something else for testing purposes)
  5. Create /vagrant/images (or whatever path)
  6. Put a JPG file in that folder. i.e. a file called foobar.jpg
  7. Start up the app with rails server
  8. Navigate to http://127.0.0.1:3000/iiif/2/foobar/full/full/50/default.jpg
  9. You should now see the image in the browser.

Now, shut down the server and try again with passenger in standalone mode: passenger start --address 0.0.0.0 --port 3000 Reload the page and notice now how you get a nasty error.

FooBarWidget commented 6 years ago

Thanks for reporting this. You hypothesize that the initializer is ignored. We should verify that.

Can you add this to config/initializers/riiif.rb?

raise 'error'

Then start Passenger. Do you see the above exception being thrown?

OnixGH commented 6 years ago

@netsensei any updates?

netsensei commented 6 years ago

Sorry for the late response.

Yup. I added the 'raise error' line to the initializer. It doesn't get thrown. Oddly enough.

CamJN commented 6 years ago

It turns out this is due to a conflict with smart spawning. Please review the debug steps here: https://www.phusionpassenger.com/library/indepth/ruby/spawn_methods/#the-smart-spawning-method

EverardB commented 4 years ago

ruby-2.6.3-p62 passenger-6.0.4 rails-6.0.2.2 Apache httpd-2.4.43

The problem still occurs. My initializer is loaded with puma but not with passenger Any suggested fixes?

EverardB commented 4 years ago

UPDATE: Adding 'PassengerSpawnMethod direct' to my apache config solves it, as noted by @CamJN