How does one use rescue in Ruby without the begin and end block
Asked Answered
N

5

135

I know of the standard technique of having a begin <some code> rescue <rescue code> end

How does one just use the rescue block on its own?

How does it work, and how does it know which code is being monitored?

Nifty answered 9/10, 2009 at 8:58 Comment(1)
rubyinside.com/21-ruby-tricks-902.htmlNecroscopy
P
258

A method "def" can serve as a "begin" statement:

def foo
  ...
rescue
  ...
end
Papillose answered 9/10, 2009 at 9:0 Comment(5)
Also, class definitions, module definitions and (I think) do/end block literals form implicit exception blocks.Canna
can you do def rescue ensure end as well?Dorinedorion
You can absolutely do def rescue ensure end as well :-)Extravaganza
can you use more than one rescue in your def?Lexeme
@Lexeme yes you can use multiple rescues, either explicitly (each rescue clause/block on its own line) like rescue TypeError; rescue NameError -- or you can comma-separate the exception classes, e.g. rescue TypeError, NameErrorThayne
A
53

You can also rescue inline:

1 + "str" rescue "EXCEPTION!"

will print out "EXCEPTION!" since 'String can't be coerced into Fixnum'

Ankerite answered 9/10, 2009 at 9:6 Comment(3)
How do you rescue and show the exception backtrace inline ?Shannanshannen
how to return the actual exception?Chopstick
Inline rescue is not a good practice as it rescues StandardError and all its subclasses, like NameError – meaning that even a typo in your code won't raise an error.. See thoughtbot.com/blog/don-t-inline-rescue-in-ruby.Moat
B
30

I'm using the def / rescue combination a lot with ActiveRecord validations:

def create
   @person = Person.new(params[:person])
   @person.save!
   redirect_to @person
rescue ActiveRecord::RecordInvalid
   render :action => :new
end

I think this is very lean code!

Broadfaced answered 9/10, 2009 at 9:10 Comment(0)
H
22

Example:

begin
  # something which might raise an exception
rescue SomeExceptionClass => some_variable
  # code that deals with some exception
ensure
  # ensure that this code always runs
end

Here, def as a begin statement:

def
  # something which might raise an exception
rescue SomeExceptionClass => some_variable
  # code that deals with some exception
ensure
  # ensure that this code always runs
end
Horseshoes answered 17/9, 2014 at 4:8 Comment(0)
A
5

Bonus! You can also do this with other sorts of blocks. E.g.:

[1, 2, 3].each do |i|
  if i == 2
    raise
  else
    puts i
  end
rescue
  puts 'got an exception'
end

Outputs this in irb:

1
got an exception
3
 => [1, 2, 3]
Arpeggio answered 18/8, 2020 at 2:13 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.