I've been scratching my head with this one for close to 2 weeks. I have an Ubuntu 14.04 server with rbenv installed running a number of different Rails websites, some of them on older versions of Rails, some of them on the latest version.
I have 2 websites in particular that both require a different version of puma_worker_killer, 1 requires 0.1.0 and the other 0.1.1. Both these websites use Ruby 2.5.3.
When I start the server with RAILS_ENV=dev3 bundle exec pumactl -F ./config/puma.rb start
I get the following error in the logs and the website hangs:
You have already activated puma_worker_killer 0.1.1, but your Gemfile requires puma_worker_killer 0.1.0. Prepending `bundle exec` to your command may solve this. (Gem::LoadError)
At first I thought it may've been an issue with rbenv as I had the gems installed in ~/.gem instead of in ~/.rbenv so I've nuked all rubies in ~/.gem and installed them freshly into the correct rbenv folder with bundle install
and I still get this same issue.
Now at this point I want to clarify that I've done extensive research on this subject online and I know that I can do many things to solve this.
I know I can just change the version and bundle update puma_worker_killer
.
I also know I can remove the latest version by doing gem uninstall puma_worker_killer
and choosing 0.1.1 but this would mean the dependencies on the other website wouldn't be met.
I've done some digging into the source code of bundler and can see that it's caused by the following line of code:
return if activated_spec.version == spec.version
When running in the context of bundler using bundle exec
both the activated_spec
and spec
match, meaning that the following code in that method (check_for_activated_spec!
) doesn't run. For some reason, when running the command above to start the server, activated_spec
(the activated gem) is the latest version (0.1.1) and not the one listed in the Gemfile (0.1.0), meaning it doesn't return and throws the error above.
I should also mention that there also seems to be the same issue with get_process_mem, which is one of the dependencies of puma_worker_killer. It complains of already activating 0.2.5 but my Gemfile wants 0.2.4:
You have already activated get_process_mem 0.2.5, but your Gemfile requires get_process_mem 0.2.4. Prepending `bundle exec` to your command may solve this. (Gem::LoadError)
It is my understanding of bundler that it should load the version listed in the Gemfile when using bundle exec
to counteract this very problem of having multiple versions of the same gem.
I know I could also create a separate gemset (which can be done with rbenv apparently) that has different versions of puma_worker_killer in them and then run rbenv local 2.5.3-pwk0.1.0
or rbenv local 2.5.3-pwk0.1.1
depending on the version I want, inside the project, but that seems overkill for what I want to achieve.
At this rate I'm tempted to just update all websites with the latest version of both puma_worker_killer and get_process_mem and then lock them in and remove all older versions on the server, but I don't think I should have to do that.
Does anyone know what's happening here or whether I'm doing something glaringly wrong?
Below is the piece of code I use to use puma_worker_killer in my puma config.
before_fork do
require 'puma_worker_killer'
PumaWorkerKiller.config do |config|
config.ram = 1024 # mb
config.frequency = 5 # seconds
config.percent_usage = 0.98
config.rolling_restart_frequency = 12 * 3600 # 12 hours in seconds
end
PumaWorkerKiller.start
end