Ruby on Rails (RoR) is a very popular framework that enables developers to quickly create web applications that adhere to modern design patterns. Using Rails, with just a few commands, you can build a production-ready vanilla CRUD (Create, Read, Update, Delete) application without having to write any code at all. Apache Phusion Passenger, Unicorn, and Puma are some of the popular servers which are used to run Rails applications.
The performance of Ruby MRI has improved considerably over the years. However, it is still slow compared to languages like Java or C. If you are interested in faster write times, which is necessary for critical, concurrent, distributed, and enterprise-grade applications, you should use JRuby instead, a Java implementation of Ruby.
Concurrency — Ruby MRI uses GIL (Global Interpreter Lock), and consequently has limited concurrency. JRuby, on the other hand, is able to use JVM’s threads, allowing you to achieve much higher levels of concurrency. This is usually the most important reason why JRuby is chosen over other Rubies.
Thread safety — Most of Ruby’s core classes are not thread-safe. Using such classes in multi-threaded applications is error-prone. JRuby is capable of using Java’s classes instead, which are designed for parallel processing.
More libraries — When you use JRuby, you have at your disposal not only a repertoire of Ruby gems but also all Java and Scala libraries. This lets you focus more on your application’s core functionality.
Ease of deployment — A JRuby on Rails application can be packaged into a single WAR file, which can be trivially deployed to any Java EE server. A lot of them even have browser-based interfaces to manage applications.
In this tutorial you will learn to:
At the end of the tutorial, you’ll have a working JRuby on Rails application deployed.
Deploy a 32-bit Ubuntu 14.04 Droplet. Tomcat and JRuby will run on a 64-bit server, but will likely be slower.
Create a sudo user.
If your Droplet has less than 2 GB of RAM, you should add at least 1 GB of swap space. Refer to the following tutorial for more information: How To Add Swap on Ubuntu 14.04.
Install the latest version of RVM on your machine. Refer to Step One of the following tutorial: How To Install Ruby on Rails on Ubuntu 12.04 LTS (Precise Pangolin) with RVM. You might need to add the key before you can install RVM:
gpg --keyserver hkp://keys.gnupg.net --recv-keys D39DC0E3
Follow that tutorial through the rvm requirements command.
Initialize RVM. This initialization is necessary for every new terminal you open.
. ~/.rvm/scripts/rvm
Note: If you already have a Rails application that uses Ruby 1.9.3, you can now skip to Step 2.
Create a directory to house all your Rails applications, and enter that directory.
mkdir ~/my_applications
cd ~/my_applications
We use Ruby 1.9.3 for this tutorial, because that is the latest version of Ruby that JRuby supports.
rvm install 1.9.3
rvm use 1.9.3
Install Rails.
gem install rails -N
Create a new Rails application, called simple.
rails new simple
Enter the application’s directory.
cd ~/my_applications/simple
Use nano to edit the Gemfile and uncomment the line for the gem therubyracer. This gem has to be added because our Rails application needs a JavaScript runtime.
nano ~/my_applications/simple/Gemfile
Ignoring the comments, your updated file should look like this:
source 'https://rubygems.org'
gem 'rails', '4.1.7'
gem 'sqlite3'
gem 'sass-rails', '~> 4.0.3'
gem 'uglifier', '>= 1.3.0'
gem 'coffee-rails', '~> 4.0.0'
gem 'therubyracer'
gem 'jquery-rails'
gem 'turbolinks'
gem 'jbuilder', '~> 2.0'
gem 'sdoc', '~> 0.4.0', group: :doc
gem 'spring', group: :development
You’ll want to remove the , platforms: :ruby
portion of the commented therubyracer
line, because eventually we’ll be using JRuby rather than Ruby.
Install all the gems listed in the Gemfile.
bundle install
Add a few pages to the application using Rails’ scaffolding feature.
rails g scaffold Employee name:string age:integer address:text
The rails g scaffold
command generates a few migrations. Apply them:
rake db:migrate
Change the root of the application to show the list of all employees. Use nano to edit ~/my_applications/simple/config/routes.rb
and change its contents to what’s shown below, minus the comments:
Rails.application.routes.draw do
resources :employees
root 'employees#index'
end
Your Rails application that uses Ruby MRI is now ready. Run it on the development server by typing in:
rails s
This will take a minute or two to start up.
You can visit the application in your browser by visiting http://<server-IP>:3000. Create a couple of records to make sure everything is working as expected.
Return to your console, and stop the server by pressing Ctrl+C.
In order to install and use JRuby, a JDK is required. Oracle JDK 8 can be installed using apt-get after adding the webupd8team/java
PPA.
Add the repository by typing in the following:
sudo add-apt-repository ppa:webupd8team/java
Press Enter to accept the new repository.
Update apt-get’s package index files.
sudo apt-get update
Install Oracle JDK 8.
sudo apt-get install oracle-java8-installer
Note: You will be prompted to accept a license agreement before the actual installation begins.
Select <Ok> and press Enter, then select <Yes> and press Enter.
After the installation is complete, run the command:
java -version
You should be able to see the following output, which means Java was installed correctly:
java version "1.8.0_25"
Java(TM) SE Runtime Environment (build 1.8.0_25-b17)
Java HotSpot(TM) Client VM (build 25.25-b02, mixed mode)
Use RVM to install and use JRuby.
rvm install jruby
rvm use jruby
The latest version of JRuby (1.7.16.1 as of November 2014) is now ready to be used. Check the version:
jruby -v
This shows you your server is using Oracle JDK 8. You should see output similar to this:
jruby 1.7.16.1 (1.9.3p392) 2014-10-28 4e93f31 on Java HotSpot(TM) Client VM 1.8.0_25-b17 +jit [linux-i386]
Install JRuby on Rails.
gem install rails -N
JRuby on Rails is now installed.
While a lot of Ruby MRI gems are supported by JRuby seamlessly, some gems that have native code aren’t. Most gems that are interfaces to databases fall into this category. Our application currently uses the sqlite3 gem, which is not supported by JRuby. activerecord-jdbcsqlite3-adapter should be used instead.
Similarly, JRuby uses therubyrhino instead of the therubyracer gem as a JavaScript engine.
Use nano to edit ~/my_applications/simple/Gemfile
to make this change.
nano ~/my_applications/simple/Gemfile
Your file should look like this after updating the two lines, minus the comments:
source 'https://rubygems.org'
gem 'rails', '4.1.7'
gem 'activerecord-jdbcsqlite3-adapter'
gem 'sass-rails', '~> 4.0.3'
gem 'uglifier', '>= 1.3.0'
gem 'coffee-rails', '~> 4.0.0'
gem 'therubyrhino'
gem 'jquery-rails'
gem 'turbolinks'
gem 'jbuilder', '~> 2.0'
gem 'sdoc', '~> 0.4.0', group: :doc
gem 'spring', group: :development
If you didn’t before, now you need to remove the platform
setting from the therubyrhino line.
Some of our gems require native extensions. Type in the following to allow JRuby to support C extensions.
echo "cext.enabled=true" >> ~/.jrubyrc
You can now install the newly-added gems.
bundle install
If you are not using SQLite3 as a database, you might need one of these gems:
Using a browser, download the JCE Unlimited Strength Jurisdiction policy files. You will have to accept Oracle’s License Agreement first.
(You can’t wget the files because you have to accept the agreement.)
On your local computer, upload the file to your server using scp:
scp Downloads/jce_policy-8.zip user@server-ip:~
On your server, install the unzip utility:
sudo apt-get install unzip
Unzip the file in a directory in /tmp.
cd /tmp
unzip ~/jce_policy-8.zip
Copy the policy files to the JRE’s lib/security directory.
cd /tmp/UnlimitedJCEPolicyJDK8
sudo cp *.jar /usr/lib/jvm/java-8-oracle/jre/lib/security/
Go back to your application’s directory.
cd ~/my_applications/simple
Execute the following command to speed up the JVM startup. This is necessary because virtual server environments tend to generate very little randomness on their own.
export JAVA_OPTS="-Djava.security.egd=file:/dev/./urandom"
At this point, our Rails application is fully configured to use JRuby. Start the development server:
rails s
This server might take several seconds to start. Wait till you see the following output before proceeding:
=> Booting WEBrick
=> Rails 4.1.7 application starting in development on http://0.0.0.0:3000
=> Run `rails server -h` for more startup options
=> Notice: server is listening on all interfaces (0.0.0.0). Consider using 127.0.0.1 (--binding option)
=> Ctrl-C to shutdown server
[2014-11-06 04:38:15] INFO WEBrick 1.3.1
[2014-11-06 04:38:15] INFO ruby 1.9.3 (2014-09-25) [java]
[2014-11-06 04:38:15] INFO WEBrick::HTTPServer#start: pid=2620 port=3000
Use a browser to visit http://<server-ip>:3000 and test your application. Except for the fact that it is currently running on the JVM instead of using Ruby MRI, you should find nothing different about the application.
Return to the terminal and press Ctrl+C to stop the server.
To run the JRuby on Rails application on a servlet container like Tomcat, it should first be packaged into a WAR (Web application ARchive) file. This can be done using the warbler gem.
Install warbler.
gem install warbler
The SQLite database that our application uses is currently present in the application’s directory. When the WAR file is generated, the database in its current state will be placed inside the WAR file. We do not want this, because any changes that are made to the database after deployment will be overwritten if the application is redeployed.
Therefore, the SQLite database files should be moved to a location outside the application’s directory.
Create a new directory for the databases:
mkdir -p ~/databases/simple
In this tutorial, we are only concerned about the development database. Therefore, move the development database file to the newly-created directory:
mv ~/my_applications/simple/db/development.sqlite3 ~/databases/simple
Edit the database.yml file using nano.
nano ~/my_applications/simple/config/database.yml
Update the path of the development database. You can also remove the details for other environments, because you won’t be needing them for this tutorial. After the changes, your file should look like this:
default: &default
adapter: sqlite3
pool: 5
timeout: 5000
development:
<<: *default
database: ~/databases/simple/development.sqlite3
Warbler also needs to know the Rails environment of the WAR. In this tutorial, we stick to the development environment. This is specified using a config/warble.rb
file.
Use nano to create a new file named warble.rb
nano ~/my_applications/simple/config/warble.rb
Add the following to the file:
Warbler::Config.new do |config|
config.webxml.rails.env = 'development'
end
Our application is now ready to be packaged into a WAR file. Run the following command to generate the file:
warble executable war
This will take a few moments.
Successful output should look like:
Downloading winstone-0.9.10-jenkins-43.jar
rm -f simple.war
Creating simple.war
At this point, there will be a file named simple.war in your application’s directory. Adding the argument executable to the command generates a WAR file that has a tiny embedded server (called Winstone) in it. This file can be used indepedently (without any external server) as follows:
java -jar simple.war
This is a good way to check for any problems with your WAR file. You can now use a browser to visit http://<server-ip>:8080. After a few minutes, you should be able see your application working correctly. All the entries you made in the database application earlier should be visible here.
You should wait until you see output similar to the following, to let you know that the server has started:
Nov 13, 2014 12:24:37 PM winstone.Logger logInternal
INFO: Started GET "/assets/application.js?body=1" for 108.29.37.206 at 2014-11-13 12:24:37 -0500
Return to the terminal, and press Ctrl+C to stop the embedded server.
Now that you have confirmed that the application is working as a WAR, generate a new WAR for Tomcat using the following command:
warble war
It will replace the old executable WAR with a new WAR file that doesn’t have any embedded server in it.
Download the latest version of Tomcat.
cd ~
wget http://mirror.cc.columbia.edu/pub/software/apache/tomcat/tomcat-7/v7.0.56/bin/apache-tomcat-7.0.56.tar.gz
Create a new directory for Tomcat and enter that directory.
mkdir ~/Tomcat
cd ~/Tomcat
Extract the archive:
tar -xvzf ~/apache-tomcat-7.0.56.tar.gz
Set the maximum heap size available to Tomcat to 512m to avoid java.lang.OutOfMemoryError
. This export has to be done every time you start the Tomcat server.
export CATALINA_OPTS="-Xmx512m"
As before, set the randomness generation:
export JAVA_OPTS="-Djava.security.egd=file:/dev/./urandom"
Start Tomcat:
~/Tomcat/apache-tomcat-7.0.56/bin/catalina.sh start
This server too takes several seconds to start. To monitor its logs, type in:
tail -f ~/Tomcat/apache-tomcat-7.0.56/logs/catalina.out
When the server is ready, you will see log messages like these:
Nov 10, 2014 4:12:32 AM org.apache.catalina.startup.HostConfig deployDirectory
INFO: Deployment of web application directory ~/Tomcat/apache-tomcat-7.0.56/webapps/manager has finished in 210 ms
Nov 10, 2014 4:12:32 AM org.apache.coyote.AbstractProtocol start
INFO: Starting ProtocolHandler ["http-bio-8080"]
Nov 10, 2014 4:12:32 AM org.apache.coyote.AbstractProtocol start
INFO: Starting ProtocolHandler ["ajp-bio-8009"]
Nov 10, 2014 4:12:32 AM org.apache.catalina.startup.Catalina start
INFO: Server startup in 3390 ms
Press Ctrl+C to end the tail command.
Tomcat is now installed and running. You can use a browser to visit http://<server-ip>:8080. You should be able to see Tomcat’s welcome page.
To deploy a WAR to Tomcat, all you have to do is copy it to Tomcat’s webapps folder.
cp ~/my_applications/simple/simple.war ~/Tomcat/apache-tomcat-7.0.56/webapps
It might take a minute or so for your application to be automatically deployed. While you are waiting, you can monitor the contents of Tomcat’s log file using:
tail -f ~/Tomcat/apache-tomcat-7.0.56/logs/catalina.out
When your application is ready to be used, you will see log messages like these:
INFO: Deploying web application archive ~/Tomcat/apache-tomcat-7.0.56/webapps/simple.war
Oct 30, 2014 4:42:35 AM org.apache.catalina.startup.HostConfig deployWAR
INFO: Deployment of web application archive ~/Tomcat/apache-tomcat-7.0.56/webapps/simple.war has finished in 47,131 ms
Press Ctrl+C to end the tail
command.
You can now use a browser to visit http://<server-ip>:8080/simple/ and see your JRuby on Rails application running on Tomcat.
If you disconnect from your SSH session at any time, you should run the following three commands:
cd ~/my_applications/simple
. ~/.rvm/scripts/rvm
rvm use jruby
And if you need to restart Tomcat, run the previous three commands, and make sure you set the two environment variables before starting the server:
export CATALINA_OPTS="-Xmx512m"
export JAVA_OPTS="-Djava.security.egd=file:/dev/./urandom"
~/Tomcat/apache-tomcat-7.0.56/bin/catalina.sh start
Thus, a Ruby on Rails application can be converted into a JRuby on Rails application with just a few configuration changes. JRuby on Rails applications can run on almost all servlet containers. In this tutorial, you have already seen how to run one on Apache Tomcat and Winstone.
Thanks for learning with the DigitalOcean Community. Check out our offerings for compute, storage, networking, and managed databases.
This textbox defaults to using Markdown to format your answer.
You can type !ref in this text area to quickly search our full set of tutorials, documentation & marketplace offerings and insert the link!
Excellent Article! I was successfully able to implements on many system.But for few systems (Windowss 7) I am facing a issue. I follow all the steps till gem ‘activerecord-jdbcsqlite3-adapter’. After bundle install when I do rails s, I get below exception.
activerecord-jdbc-adapter is for use with JRuby only C:/RailsInstaller/Ruby2.1.0/lib/ruby/gems/2.1.0/gems/activerecord-jdbc-adapter-1 .3.20/lib/arjdbc/sqlite3/adapter.rb:1:in
<top (required)>': undefined method 'load_java_part' for ArJdbc:Module (NoMethodError) from C:/RailsInstaller/Ruby2.1.0/lib/ruby/gems/2.1.0/gems/activerecord-j dbc-adapter-1.3.20/lib/arjdbc/sqlite3.rb:2:in
require’Can you please help me out with this.This really critical