back to contents

Systems Stuff: Ruby is pretty cool

fyi

If you're looking for a Ruby on Rails guide, turn around now. I'm not gonna get into RoR.

What I am going to get into is object-oriented programming, how neat Ruby is, and using Ruby as a systems language.

ruby is pretty neat

yeah, I said that already, but really it's true. I came upon Ruby one snowy evening, trying to find a way to quickly burn through huge LDAP structures very quickly without consuming large amounts of memory. Ruby is pretty good for that, it turns out.

Ruby is a deeply object-oriented language, but it's dynamic and interpreted just like Perl and PHP and Python. You can use it very functionally like PHP or Python, but you'd be missing out on a lot of its power. Not only that, but it's a language designed to be simple and even colloquial. Here, let me show you.

You're hopefully at least a little familiar with what this means in Javascript:

var cats = 30;

This is pretty straightforward. The variable cats equals the number 30. Here's the same thing in Ruby:

cats = 30

Seems pretty simple, because it is. No need for semicolons. You don't even need to declare it as a variable, because everything is an Object by default. (And a variable is a kind of Object, so to speak.) But here's something neat you could then do with that variable:

cats.class

That would spit out "Fixnum"... because the cats variable is of class Fixnum, which is Ruby's basic number class. Why is this crazy?

Everything in Ruby is an Object. I capitalized "Object" because that, in itself, is an Object. CRAZY. Not only that, but Ruby is reflective, which means every Object knows it's an Object!

And most importantly, every class in Ruby is a child of the Object class... even nil (Ruby's NULL). So you can use any method that the Object class has. So whether it's a number or a string or whatever, it'll have access to the .class method.

That's why you can ask the cats variable what its class is by using the .class method on it! If you wanted, you could pick any number, like so:

138.class

And it would return "Fixnum", because the number doesn't even have to be contained in a variable, it's still an Object. Likewise:

"hello".class

would spit back "String", because that's a String! It doesn't even need to be a variable, it's already an Object just because you typed it out.

Interactive Ruby

So this is all neat and cool to tell you about, but you should definitely play with it, too. The easiest way to do it is to use irb, or the Interactive Ruby Interpreter.

irb and Ruby itself come installed on Macs, so you can open a Terminal window, type irb, and start using it. On Linux, you'll have to install Ruby and irb. On Debian you'd just do this:

> apt-get install ruby irb

If you're on Windows, you can try using the RubyInstaller.

Anyway, once you have that loaded, you can play with the above examples.

Learning Ruby

I found Ruby ridiculously easy to learn, mostly because there's a very great (albeit nerd-hipstery) community surrounding it. Here are a few really good ones:

why's guide alone makes me not want to bother making a how-to guide for Ruby, because it has already been done so beautifully. the full documentation for Ruby, like PHP's docs, are also very well made and thorough, as any API reference should be.

which is why I don't really want to make a "Learning Ruby" guide here. it's been done way better than I can do it. but... I can provide a few tips.

Ruby tips and thoughts

Here are a few of my useful thoughts on Ruby:

Ruby is written to be way more colloquial than most languages, as I've said. For this reason above all others, it's a charm to work with. Stuff like not needing to care about semicolons, and the fact that methods use punctuation that's indicative of their purpose, like the .eql? method.

Normally in other languages like PHP you run a conditional like this:

if ($rofl == 10) {
  echo "lol!";
}

But in Ruby, you could write it like this:

puts "lol!" if rofl.eql?(10)

You can pretty much read that line out loud, that's how easy it is. And almost all of Ruby is like that. And it's pretty awesome that you can add the if after the statement. Similarly, but importantly, there's an unless keyword!

puts "lol!" unless rofl.eql?(10)

So. Cool.

That having been said, the reason you use .eql? and not == is because everything is an object! Testing for equality requires you to make sure you're also testing by class, and each class tests equality differently. Using the .eql? method makes sure that you're using the right way each class wants to check for equality.

Therefore, Ruby doesn't want to assume much for you; so if you want to add a number to the end of a string, you need to use the .to_s method to convert the number to a string in the same operation, like so:

somenumber = 10
whatever = "whatever" + somenumber.to_s

Otherwise it'll actually try to do math with the somenumber variable! You have to convert the number to a string using .to_s before it can be added to the end of the string.

Ruby's Array and Hash methods are divine in their simplicity. Learn them well. The mere fact that there are .each and .include? methods is wonderful. In fact, Ruby's block functionality is pretty neat. Here's an example:

[ "lol", "rofl", "lmao" ].each do |wut| puts wut end

That takes the array with the three strings in it, and for each, uses puts to print them out one at a time. The do and end keywords denote the beginning and end of a block. You could use curly braces if you wanted:

[ "lol", "rofl", "lmao" ].each { |wut| puts wut }

If that makes it easier for you to read, then great. It's wonderful to have the option to go either way! The object contained within the | characters represents whatever iteration the loop is currently on.

When you're building things that interface with other systems, there's probably a module for it. Kinda like node.js, except Ruby has been around a lot longer. If you need something special done, Ruby probably has a library for it somewhere. It's like how PHP has extensions, but they're not very friendly usually.

With Ruby, you just need to install RubyGems and let that take care of 99% of the work for you! It's a lot like npm is for node and apt is for Debian; it will install the packages and libraries for you.

A neat idea: make your own damn classes. Everything is an Object in Ruby, so use that to your advantage by making your own types of Objects to streamline things for you. Here's a fun example:

class Cat
  def initialize(name)
    @name = name
  end
  
  def meow
    puts "MEOW!"
  end
end

kitty = Cat.new("Muffy")
kitty.meow

You can save that as cat.rb, run it in the command line using ruby (ruby cat.rb) and it'll print out "MEOW!" See what we did there?

Ruby for Systems

Ruby can be used as a web development language, sure, it already is. But I use it primarily as a system backend language, for automation and interoperability, because of its memory management and its objectivity (lol).

Honestly, I tried Ruby on Rails, and I didn't like it. Too much sass, not enough substance. Plus, when people leave Ruby on Rails and "upgrade" to Java because it's more scalable, you know something is wrong. But that's all I'll say about Ruby on Rails.

Ruby, like Python, (... and like Perl, I'm sure) is a very robust language for automation. It has a lot of great, easy File handling classes. But it's just a tool in the utility belt.

I think I could've swung either way... Python or Ruby. I decided not to learn Python and instead learn Ruby. I'm not sure if it matters which one I picked; I would've written a similar little guide for Python.

the end

honestly I don't know what else to write, other than "try out Ruby". I wrote about half of a text adventure game in Ruby, and then node.js came out, and I ported the game to that. no regrets. I don't have any crazy tricks for Ruby, because I think Ruby in itself is a crazy trick.

however, Ruby continues to power some of my more "heavy" scripts. I use it less frequently than say PHP, but when I do use it, it's with a purpose. learn Ruby, appreciate it within the context of your experience, and use it sometime.