user1201917
user1201917

Reputation: 1370

What is the purpose of nil? and exists? methods in ruby/rails conditions?

I often (very often) see code like this in the conditions:

<% catalog.each do |article| %>
  <% if article.image.nil? %>
    ...

or (e.g. seen there)

<% catalog.each do |article| %>
  <% if article.image.exists? %>
    ...

However we all know that nil interprets like false in the conditions. ActiveRecord query returns nil if nothing found.

Why not simply write:

<% unless article.image %> (unless there is article do something)

instead of

<% if article.image.nil? %> (if there is nothing at article.image do something)

and

<% if article.image %> instead of <% if article.image.exists? %>

I usually write the code without nil? and exists?. What am I missing? Is there any pitfalls?

Upvotes: 0

Views: 1555

Answers (3)

rmhunter
rmhunter

Reputation: 581

In your example, and in many typical RESTful Rails patterns, you're correct that using the implicit version is identical in behavior.

But there are certainly suations where nil? and exists? are necessary and/or more readable...

For instance, nil? is the only option when you're reading a boolean attribute, and you need different behavior for false vs nil (since both are falsey in Ruby).

Or, assume in your example, that each Article has many images, and you define a method to get an Article's first image according to display order:

def primary_image
  images.order(display_order: "ASC").limit(1)
end

In this case, if your Article doesn't have any images, primary_image will return an empty collection, which is truthy. So, in this case, you'd need to use exists? (or present?). Rails provides several convenience methods for checking data records.

(or make sure the primary_image method returns nil or false when the collection is empty)

Upvotes: 3

Tobias
Tobias

Reputation: 4653

Most of the time it's just to be more explicit I suppose.

In your example above it doesn't matter if you check explicitly or implicitly.

But if you want to check explicitly for nil for example, you use the #nil? because sometimes you want to react differently if false is returned.

As an example: false and nil are often not interchangeable for boolean values in a database.

Like @lusketeer already said is nil? a method of the ruby standard library and exists? a method of the Rails framework.

But I think almost always you are good with the implicit way.

Upvotes: 1

lusketeer
lusketeer

Reputation: 1930

Personally, I rarely use either one of them. Like you suggested, I mostly just use if or unless depends on the situation without bothering with nil? or exists?

As for the difference between the two:

nil? is a Ruby method to see whether the object is nil or not.

exists? is a Rails method to see whether the record exists in the database

I guess, just use whichever is more efficient. I have been trying to convert my codes to use try to avoid no method error.

Upvotes: 1

Related Questions