Starting Rails Server With a Different Port in Development
So recently, because I was working on a project where we had to boot up different Rails applications in a development environment, it became necessary to have each rails server boot up locally with a different default port.
Solution 1: The Typical Solution
The typical solution is to pass a port option at the command line as follows:
rails s -p 4000
Solution 2: Use rake
But obviously, it can be tiresome to keep typing rails s with a different port each time. You could use rake as well.
task :custom_serve do
`rails s -p 4000`
end
Now you can type rake custom_serve
at the command like to get the desired effect. Of course this means you have to have people be aware that they need to run a rake task to do this. It’s a slight inconvenience in my opinion.
Solution 3: Use foreman if you’re using something like Unicorn
Use foreman to start your web server via Procfile, and then specify the port number in the Unicorn config file. This is a perfectly fine setup, but sometimes you just want to get going with the Webrick you have, instead of the production server you want.
Solution 4 (Final Solution): Hack the bootup process in Rails 4/5
In Rails 4/5 projects, you typically get a setup as follows in bin/rails:
#!/usr/bin/env ruby
begin
load File.expand_path("../spring", **FILE**)
rescue LoadError
end
APP_PATH = File.expand_path('../../config/application', **FILE**)
require_relative '../config/boot'
require 'rails/commands'
Modify the setup in bin/rails to the following:
#!/usr/bin/env ruby
begin
load File.expand_path("../spring", __FILE__)
rescue LoadError<br />
end
APP_PATH = File.expand_path('../../config/application', __FILE__)
require_relative '../config/boot'
###Added to start rails on port 4000 in development environment (the port number is arbitrary)
require 'rails/commands/server'
module DefaultOptions
def default_options
super.merge!(Port: 4000) if Rails.env.development?
end
end
Rails::Server.send(:prepend, DefaultOptions)
require 'rails/commands'
Note the use of prepend. This is because prepend is private. You also need Ruby >= 2.0.0