আপনার কোড সেই ব্যতিক্রমের জীবনচক্র নিয়ন্ত্রণ না করলেও সাম্প্রতিকতম ব্যতিক্রম পেতে সক্ষম হওয়া প্রায়শই কার্যকর। কল্পনা করুন যে আপনি আপনার অ্যাপ্লিকেশনে মৌলিক ক্র্যাশ সনাক্তকরণ যোগ করতে চান। আপনি যেকোন ক্র্যাশ সম্পর্কে অতিরিক্ত তথ্য লগ করতে চান যা একটি ধরা না পড়া ব্যতিক্রমের ফলে ঘটে।
প্রথম ধাপ হল একটি হ্যান্ডলার যোগ করা যা আপনার অ্যাপ্লিকেশন থেকে বের হলেই চালানো হয়। রুবি কার্নেলের at_exit পদ্ধতির মাধ্যমে এটি করা খুবই সহজ।
at_exit
puts "the app exited"
end
কিন্তু কিভাবে আমরা জানতে পারি যে প্রস্থান কলব্যাক একটি ব্যতিক্রমের ফলে আহ্বান করা হয়েছিল? ঠিক আছে, রুবি ক্রিপ্টিলি নামে $!
প্রদান করে বিশ্ব পরিবর্তনশীল। এটিতে সাম্প্রতিককালে উত্থাপিত ব্যতিক্রম রয়েছে যা বর্তমান কল স্ট্যাকের কোথাও ঘটেছে।
$!
ব্যবহার করা তুচ্ছ একটি ব্যতিক্রমের কারণে প্রোগ্রামটি প্রস্থান করা হচ্ছে কিনা তা সনাক্ত করতে। এটা এই মত কিছু দেখায়:
at_exit do
save_error_to_log($!) if $!
end
$!
-এর সীমাবদ্ধতা
দুর্ভাগ্যবশত, $!
বর্তমান কল স্ট্যাকের কোথাও ব্যতিক্রম ঘটলেই পদ্ধতিটি কাজ করে। যদি আপনি একটি ব্যতিক্রম উদ্ধার করেন, তাহলে $!
অ্যাক্সেস করার চেষ্টা করুন রেসকিউ ক্লজের বাইরে, আপনি শূন্য পাবেন।
begin
raise "x"
rescue
puts $! # => RuntimeError
end
puts $! # => nil
এর মানে হল $!
IRB এর মত শেল এর ভিতরে বেশ অকেজো। প্রায়শই IRB-তে, আমি একটি পদ্ধতি চালাব এবং একটি ব্যতিক্রম পাব। কখনও কখনও আমি সেই ব্যতিক্রম বস্তুটি ধরে রাখতে চাই। কিন্তু $!
এর জন্য কাজ করে না৷
irb(main):001:0> 1/0
ZeroDivisionError: divided by 0
from (irb):1:in `/'
irb(main):002:0> $!
=> nil
$ এর কাছাকাছি কাজ করা! PRY
এর সাথে
PRY $!
-এর সীমাবদ্ধতার কাছাকাছি চলে নিজস্ব স্থানীয় ভেরিয়েবল যোগ করে, _ex_
. এই ভেরিয়েবলে সবচেয়ে সাম্প্রতিক ধরা না পড়া ব্যতিক্রম রয়েছে।
[1] pry(main)> raise "hi"
RuntimeError: hi
from (pry):1:in `__pry__'
[2] pry(main)> _ex_
=> #<RuntimeError: hi>
পিআরওয়াই এটি করতে সক্ষম হওয়ার কারণ হল পিআরওয়াই বা আইআরবি-এর ভিতরে আসলেই কোন ধরা পড়া ব্যতিক্রম নেই। শেল নিজেই ব্যতিক্রমগুলি ক্যাচ করে এবং সুন্দরভাবে ফর্ম্যাট করা ত্রুটি বার্তা হিসাবে প্রদর্শন করে৷
আমি নীচের PRY উত্সের প্রাসঙ্গিক বিটগুলি অনুলিপি করেছি৷ আপনি দেখতে পাচ্ছেন যে কোডটি যেটি আপনার কমান্ডের মূল্যায়ন করে সেটি একটি সূচনা/উদ্ধার/শেষ ব্লকের ভিতরে মোড়ানো রয়েছে। যখন একটি উদ্ধারযোগ্য ব্যতিক্রম ঘটে, তখন PRY ব্যতিক্রমটিকে self.last_exception-এ সংরক্ষণ করে এবং এটি পরে _ex_
-এ বরাদ্দ করা হয়। .
# Excerpted from the PRY source at https://github.com/pry/pry/blob/623306966bfa86890ac182bc8375ec9699abe90d/lib/pry/pry_instance.rb#L273
begin
if !process_command_safely(line)
@eval_string << "#{line.chomp}\n" if !line.empty? || !@eval_string.empty?
end
rescue RescuableException => e
self.last_exception = e
result = e
Pry.critical_section do
show_result(result)
end
return
end
ইংরেজি প্রয়োজন
সম্ভবত আপনি $!
এর মত পরিবর্তনশীল নামগুলি খুঁজে পাচ্ছেন চোখের উপর একটু কঠিন? সৌভাগ্যবশত, রুবিতে "ইংরেজি" নামক একটি মডিউল রয়েছে যা অনেক বৈশ্বিক ভেরিয়েবলের ইংরেজি-ভাষা সংস্করণ সরবরাহ করে যা অন্যথায় রোবট কাসওয়ার্ডের মতো দেখায়।
$!
এর প্রতিশব্দ হল $ERROR_INFO
. আপনি যেখানেই সাধারণত $!
ব্যবহার করেন সেখানে আপনি এটি ব্যবহার করতে পারেন .
require "English"
begin
raise "x"
rescue
puts $ERROR_INFO # => RuntimeError
end
এবং যদিও বেশিরভাগ অন্যান্য ইংরেজি সমতুল্যের এই ব্লগ পোস্টের বিষয়ের সাথে কিছুই করার নেই, আমি সেগুলিকে কিক করার জন্য অন্তর্ভুক্ত করছি। ইংরেজি ভেরিয়েবল বাম দিকে আছে. আসলগুলি ডানদিকে রয়েছে৷
$ERROR_INFO | $! |
$ERROR_POSITION | $@ |
$FS | $; |
$FIELD_SEPARATOR | $; |
$OFS | $, |
$OUTPUT_FIELD_SEPARATOR | $, |
$RS | $/ |
$INPUT_RECORD_SEPARATOR | $/ |
$ORS | $\ |
$OUTPUT_RECORD_SEPARATOR | $\ |
$INPUT_LINE_NUMBER | $। |
$NR | $। |
$LAST_READ_LINE | $__ |
$DEFAULT_OUTPUT | $> |
$DEFAULT_INPUT | $< |
$PID | $$ |
$PROCESS_ID | $$ |
$CHILD_STATUS | $? |
$LAST_MATCH_INFO | $~ |
$IGNORECASE | $= |
$ARGV | $* |
$MATCH | $& |
$PREMATCH | $` |
$POSTMATCH | $‘ |
$LAST_PAREN_MATCH | $+ |