Love Ruby on Rails

by Eugene MelnikovNovember 6, 2015
This blog post compares Ruby on Rails and Node.js across a number of scenarios: implementing changes, debugging, dealing with packages, etc.

 

Ruby on Rails vs. Node.js

Recently, I had a chance to try Node.js and plunge into the JavaScript world. For those who just started learning Node.js, but already have a Ruby-on-Rails background, it might be useful to associate some Ruby on Rails packages with Node.js packages.


Node.js
Ruby on Rails
nvmrvm
karmarake
protractorrspec + capybara
npmbundle
expresssinatra
jasminerspec
npmjs.comrubygems.org


Please don’t blame me, it is just a rough comparison.

Here, I will look into the two technologies and compare them across a number of points.

 
Implementing changes to functionality

The first problem I faced is the necessity to restart the server after each change. Hopefully, I discovered nodemon that helped to solve the issue. In Ruby on Rails, it’s not necessary at least for the development environment.

 
Debugging

However, I had to debug soon and realized that I need to start the server with --debug flag + install node-inspector, which opens Google Chrome development tools with all it’s power. It’s a big advantage, because you can see the full source file, as well as objects by just hovering a mouse on a variable and even edit the file. This advantage, though, easily turns into a weakness if you fork subprocesses, as you have to pass a unique debug port for each fork, and node-inspector should be opened for each subprocess on a unique web port. I’d prefer to use Pry or Byebug instead.

I could accept this, because it’s a different technology, but when I tried, Protractor drove me mad. When I write browser.pause(), it stops sending commands to Selenium. Although I can open development tools, it’s late already, as I can’t check the Network tab to proceed with these tools, because the tab closes when I take the next step. Adding multiple pauses in the test doesn’t make any sense, because command C is doing the next step without closing a debugger to proceed. Even if you type repl, it’s still impossible to check a variable in your test, because you are in a different fake context. browser.debugger() works only if you add the --debug key in the command line and stops at a fake context, as well. I understand that browser.pause() is still experimental (too long). Why can’t they allow to use a simple debugger without any wrappers? It seems that WebdriverIO allows for better debugging. I’m going to try it.

 
Creating separate repositories

In addition, I noticed that some package authors create a separate repository for Bower releases. It’s strange for me, because the bower.json file can be created in the main repository. In Ruby on Rails, we are not creating a separate repository for RubyGems. By the way, nodemon has recently released a new version that allows for deduplicating the same dependencies. Previously, they put all dependencies in a folder with a package. Now, all packages in node_modules are flatten.

 
Dealing with packages

Updating packages in Ruby on Rails is also much more simple: bundle an update instead of npm update && npm update -g && npm update --dev && bower update. You may have noticed that for the client side, a bundle is replaced with Bower. While for the server-side packages, they use npm. It’s due to different types of including packages (AMD, CommonJS, and ES). In Ruby on Rails, we have only one package. Even if you have Bower packages in the Ruby application, you can update them together with RubyGems thanks to Rails-Assets. It’s also funny to see that Bower bought an expensive domain, but can’t afford more stable hosting. I saw several times when search packages are down. However, I’ve never seen RubyGems down.

 
Parsing HTTP files

To get a file via HTTP, you need to install a special request parser, e.g., multiparty. Then you can work with a file in the same way as in Ruby on Rails.

 
The sync and async functions

In a node, some async functions are duplicated with sync analogs. It’s very useful, because in tests, you will most likely use sync analogs. While in an application, you may consider using async function to speed up the response. Unfortunately, not all package authors duplicate their functions, and you may need to use the async package to convert async functions to sync ones.

Love Ruby on Rails!

 

Further reading