• What is a failure?
• How does Ruby handle errors?
• What to do when code fails?
Slide 5
Slide 5 text
What is a failure?
Slide 6
Slide 6 text
No content
Slide 7
Slide 7 text
No content
Slide 8
Slide 8 text
No content
Slide 9
Slide 9 text
Human Fails Computer Fails Human Fails
Slide 10
Slide 10 text
I realized that when a computer program had a fault, the
machine could turn out errors millions of times faster than
any human or group of humans. [...] I could actually
program a machine to make more errors in a day than all
human beings had made in the last 10,000 years.
– Gerald M. Weinberg. “Errors.”
Slide 11
Slide 11 text
begin
do_work
rescue
handle_error
end
Slide 12
Slide 12 text
begin
do_work
rescue
puts $!.message
end
begin
do_work
rescue => my_error
puts my_error.message
end
Slide 13
Slide 13 text
begin
do_work
rescue
# Handle StandardError
end
begin
do_work
rescue ArgumentError
# Handle ArgumentError
end
Slide 14
Slide 14 text
begin
do_work
rescue ErrorA, ErrorB
# Handle ErrorA or ErrorB
end
begin
do_work
rescue ErrorA
# Handle ErrorA
rescue ErrorB
# Handle ErrorB
end
Slide 15
Slide 15 text
begin
do_work
rescue ErrorA, ErrorB
# Handle ErrorA or ErrorB
end
begin
do_work
rescue ErrorA, ErrorB => error
# Handle ErrorA or ErrorB as error
end
Slide 16
Slide 16 text
begin
do_work
rescue ErrorA
# Handle ErrorA
rescue ErrorB
# Handle ErrorB
end
Slide 17
Slide 17 text
parse(str) rescue 'parse failed'
Slide 18
Slide 18 text
def example
do_work
rescue => error
puts error.message
end
def example
begin
do_work
rescue => error
puts error.message
end
end
Slide 19
Slide 19 text
begin
do_work
ensure
cleanup
end
Slide 20
Slide 20 text
begin
file = File.new('greeting.txt', 'w')
file << 'Hello, world!'
ensure
file.close
end
Slide 21
Slide 21 text
def write_to(path)
file = File.new(path, 'w')
yield file
ensure
file.close
end
write_to('greeting.txt') do |file|
file << 'Hello, world!'
end
Slide 22
Slide 22 text
File.open('greeting.txt', 'w') do |f|
f << 'Hello, world!'
end
Slide 23
Slide 23 text
begin
do_work
rescue => error
warn error.message
ensure
cleanup
end
uncaught.rb:2:in `boom': unhandled exception
from uncaught.rb:5:in `'
Slide 37
Slide 37 text
Kernel.raise
Slide 38
Slide 38 text
module RaiseExit
def raise(msg_or_exc, msg=msg_or_exc, trace=caller)
warn msg.to_s
warn caller
exit!
end
end
module Kernel
include RaiseExit if ENV['DEBUG']
end
Slide 39
Slide 39 text
raise inside ensure?
raise inside rescue?
Slide 40
Slide 40 text
begin
do_work
rescue Timeout
handle_error
retry
end
Slide 41
Slide 41 text
tries = 0
begin
do_work
rescue TimeoutError
tries += 1
retry if tries < 3
end
Slide 42
Slide 42 text
tries = 1
begin
do_work
rescue TimeoutError
retry if tries < 3
tries += 1 # Never called...
end
Slide 43
Slide 43 text
begin
do_work
rescue
handle_failure
else
handle_success
end
Slide 44
Slide 44 text
begin
do_work
puts 'success'
rescue
puts 'failure'
end
begin
do_work
rescue
puts 'failure'
else
puts 'success'
end
Slide 45
Slide 45 text
begin
step_1
step_2
rescue
revert_step_1 # Maybe?
end
Slide 46
Slide 46 text
begin
step_1
revert = false
rescue
revert = true
end
if revert
revert_step_1
else
step_2
end
Slide 47
Slide 47 text
begin
step_1
revert = false
rescue
revert = true
end
if revert
revert_step_1
else
step_2
end
begin
step_1
rescue
revert_step_1
else
step_2
end
Slide 48
Slide 48 text
begin
do_work
rescue Timeout
retry
rescue Fatal
log_failure
else
log_success
ensure
cleanup
end