{"id":333,"date":"2012-01-29T02:18:41","date_gmt":"2012-01-28T23:18:41","guid":{"rendered":"http:\/\/www.held.org.il\/blog\/?p=333"},"modified":"2012-05-21T02:45:40","modified_gmt":"2012-05-20T23:45:40","slug":"raise-or-return-using-exceptions-part-1","status":"publish","type":"post","link":"http:\/\/www.held.org.il\/blog\/2012\/01\/raise-or-return-using-exceptions-part-1\/","title":{"rendered":"Raise or Return? (using exceptions, part 1)"},"content":{"rendered":"<p>Ever since I've been using exceptions, uncertainty has always been there: when are we better off with return codes? when is it smart to catch the exceptions? when should they better be left untouched and propagate higher? Create a separate exception class, or just pass an argument to the constructor?<\/p>\n<div style=\"width: 190px\" class=\"wp-caption alignright\"><a href=\"http:\/\/www.flickr.com\/photos\/jmchuff\/2403104412\/\"><img loading=\"lazy\" class=\" \" src=\"http:\/\/farm3.staticflickr.com\/2405\/2403104412_27594979f1_m_d.jpg\" alt=\"\" width=\"180\" height=\"240\" \/><\/a><p class=\"wp-caption-text\">cc-by-sa Jason McHuff<\/p><\/div>\n<p>During the recent few years, I've been gathering some best practices I learned from my peers and by experience, which I'll dump here to a short series of posts. I hope it'll help to provoke some discussion on this rather important design matter. As it's a highly debatable matter, discussions are more effective than trying to declare the ultimate truth of proper usage of exceptions.<\/p>\n<p>Most of my experience in this area is related to Python, but I believe the same discussion usually applies to all dynamic languages, and possibly to languages that use <em>throw<\/em> rather than <em>raise<\/em>.<\/p>\n<p>Enough disclaimers, let's get started. An easy one for starters:<br \/>\n<!--more--><\/p>\n<h2><strong>Part 1: Should a function raise an exception or return a failure value?<\/strong><\/h2>\n<p>Exceptions, as their name suggests, should be raised in <strong>exceptional cases<\/strong>. To differentiate between exceptional and normal, I usually ask myself <strong>what's the purpose of the function. <\/strong>If a function is well-named (it should be!), it gets easy to deduce that. [I also find <a href=\"http:\/\/en.wikipedia.org\/wiki\/Test-driven_development\">TDD<\/a> very helpful in deciding what's the purpose of a function, and thus how to properly name it]<\/p>\n<p>To sum up my take on this, in a single sentence: <strong><span style=\"color: #008000;\"><br \/>\n<\/span>Exceptions should be raised only when the function encounters a case that is out of the scope of its purpose.<\/strong><\/p>\n<h2>Distinctive examples<\/h2>\n<h4><span style=\"color: #00ff00;\"><strong>Do raise an exception - something out-of-scope has occurred:<\/strong><\/span><\/h4>\n<ul>\n<li><strong><em>read_file_contents(file_handle)<\/em><\/strong>, may raise an exception if file handle is closed or if read has unexpectedly failed.<br \/>\ne.g. FileReadError()<br \/>\n<strong>Update: <\/strong>My assumption here is that the file open operation occurred earlier and succeeded; this makes read errors exceptional and not expected.<strong><\/strong><\/li>\n<li><em><strong>parse_configuration(data)<\/strong><\/em> may raise an exception if given data is bad.<br \/>\ne.g. BadConfigurationDataError()<br \/>\n<strong>Update:<\/strong> I refer here to an internal not-user-modifiable configuration file, which renders a parsing failure exceptional and not expected.<\/li>\n<\/ul>\n<h4><span style=\"color: #ff0000;\"><strong>Don't raise (return a value) - something normal, in-scope, has occurred:<\/strong><\/span><\/h4>\n<ul>\n<li><strong><em>file.is_open()<\/em><\/strong> should NOT throw an exception if file is not open: its name suggests its a boolean function, therefore it should return False. A closed file is a normal case for this function.<\/li>\n<li>\n<div style=\"width: 250px\" class=\"wp-caption alignright\"><a href=\"http:\/\/www.flickr.com\/photos\/msr\/448820990\/\"><img loading=\"lazy\" class=\" \" src=\"http:\/\/farm1.staticflickr.com\/249\/448820990_099a4aa69f_m_d.jpg\" alt=\"\" width=\"240\" height=\"163\" \/><\/a><p class=\"wp-caption-text\">cc-by-nc msr<\/p><\/div>\n<p><em><strong>apples.count()<\/strong><\/em> - if apple count is 0, I would expect the function to return 0, rather than\u00c2\u00a0 raising <em>ZeroApplesError() exception<\/em>. Zero apples is a normal case for a the scope of the <em>count<\/em>() function.<br \/>\nBut it's not always that obvious! In the larger context (e.g. an apple juice factory control program), zero apples may seem like an exceptional case - but we should look at the <strong>scope of the function<\/strong> and not beyond. In this hypothetical juice factory case, it WILL make sense to raise an exception at a higher-level function such as <em>squeeze_apples()<\/em>, if <em>apples.count()<\/em> == 0.<\/li>\n<\/ul>\n<p>Of course in reality we encounter cases which are harder to differentiate, but I find it useful to compare the real cases to these fictional edge cases. Furthermore, even these edge cases DO happen sometimes...<\/p>\n<p>Do you agree? disagree? Do you find cases where even the most unexpected error should return -1 rather than raise an exception? Add your comments.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Ever since I&#8217;ve been using exceptions, uncertainty has always been there: when are we better off with return codes? when is it smart to catch the exceptions? when should they better be left untouched and propagate higher? Create a separate exception class, or just pass an argument to the constructor? During the recent few years, [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":[],"categories":[4],"tags":[171,173,175,174,170,198,93,172],"_links":{"self":[{"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/posts\/333"}],"collection":[{"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/comments?post=333"}],"version-history":[{"count":0,"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/posts\/333\/revisions"}],"wp:attachment":[{"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/media?parent=333"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/categories?post=333"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/www.held.org.il\/blog\/wp-json\/wp\/v2\/tags?post=333"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}