Live data from Hacker News

Error Handling in Node.js

joyent.com

51–60 of 96 posts

Re: Error Handling in Node.js

#51
post #8

My non-node specific suggestions: 1 - Don't catch errors unless you can actually handle them (and chances are, you can't handle them). Let them bubble up to a global handler, where you can have centralized logging. There's a fairly old discussion with Anders Hejlsberg that talks about this in the context of Java's miserable checked exception that I recommend [1]. This is also why, in my mind, Go gets it wrong. 2 - In…

When it comes to 1.), a better way to state things is may be that you shouldn't ignore errors unless you were able to completely handle them. Catching exceptions to throw exceptions with better messages is something I would stronly suggest, since almost no exceptions are useful without contextual information. I.e. which file was not found? The config, not the input or output. Things like this. This is especially usef…

You can sometimes get stack traces in C++, but it's platform and compiler specific. Gcc's system is pretty good.

(I have some code for WinCE that walks stack traces in conjunction with SEH so that crashes in production - segfault etc - get logged in a useful manner. It does rely on parsing and decoding instructions ...)

Re: Error Handling in Node.js

#52
Can anyone explain why this pattern doesn't work? Or point me to some resource?

  function myApiFunc(callback)
  {
    /*
     * This pattern does NOT work!
     */
    try {
      doSomeAsynchronousOperation(function (err) {
        if (err)
          throw (err);
        /* continue as normal */
      });
    } catch (ex) {
      callback(ex);
    }
  }

Re: Error Handling in Node.js

#54
post #52

Can anyone explain why this pattern doesn't work? Or point me to some resource? function myApiFunc(callback) { /* * This pattern does NOT work! */ try { doSomeAsynchronousOperation(function (err) { if (err) throw (err); /* continue as normal */ }); } catch (ex) { callback(ex); } }

There's a footnote about this: https://www.joyent.com/node-js/production/design/errors#fn:1

Re: Error Handling in Node.js

#55
post #25

For me, error handling has a major flaw: stack unwinding - extremely annoying thing to happen when the program state took many many hours to achieve. I don't think there is any language other than CL that allows restarts etc. to be defined; slime-repl too is invaluable when debugging. http://www.gigamonkeys.com/book/beyond-exception-handling-co...

Right! A long time back we came up with a really nice way of validating CSV files using restarts. I wrote a bit about it: http://lisper.in/restarts

Neat. I use it for things like linesearch and regularization (in optimization),

https://github.com/matlisp/matlisp-optimization/blob/master/...

As a fellow Indian lisper, are you by any chance using CL for work ?

Last I heard, the only big CL shop, cleartrip, moved all their codebase to Ocaml.

Re: Error Handling in Node.js

#56
post #8

My non-node specific suggestions: 1 - Don't catch errors unless you can actually handle them (and chances are, you can't handle them). Let them bubble up to a global handler, where you can have centralized logging. There's a fairly old discussion with Anders Hejlsberg that talks about this in the context of Java's miserable checked exception that I recommend [1]. This is also why, in my mind, Go gets it wrong. 2 - In…

If you can't handle an error, why would you allow it. It makes no sense. As a developer you have control of the errors/exceptions that get raised and raising an error that you can't deal with seems.. bad.

Concurrency means you can't prevent errors. Every time you open a file, it could have been deleted out from underneath you, in a race with some other process.

Most files a program opens are not as a result of user action: configuration, libraries, resources, etc. And usually it doesn't make sense to catch these errors at the point of occurrence, because they'll be all over the codebase. And there's very little you can do in response to them.

Re: Error Handling in Node.js

#57
This article promotes the fail-fast approach, something I very much dislike (against popular opinion it seems).

I'm very much in favor of the opposite approach, defensive coding. Often when I read opinion pieces about how bad defensive coding is, they almost always seem to forget that defensive coding without proper logging, error-handling and monitoring is NOT defensive coding. It is extremely dangerous to just detect error conditions without any feedback: you have no idea what is going on in your system!

IMHO properly applied defensive coding, works as follows:

* Detect inconsistent situations (e.g. in a method, expected an object as input argument, but got a null)

* Log this as an error and provides feedback to the caller of the method that the operation failed (e.g. through an error callback).

* The caller can then do anything to recover, (e.g. reset a state, or move to some sort of error state, close a file or connection, etc.).

* The caller should then also provide feedback to its caller, etc. etc.

This programming methodology gives the following advantages:

* You are made to think about the different problems that can occur and how you should recover them (or not)

* Highly semantic feedback about what is going wrong when an issue occurs; this makes it very easy to pinpoint issues and fix them

* Server application keeps on running to handle other requests, or can be gracefully shut down.

* Client side application UIs don’t break, user is kept in the loop about what is happening

Of course you will need to keep a safety net to catch uncaught exceptions, properly logging and monitoring them (and restart your application if relevant)

The fail-fast approach, as I have seen it applied, doesn’t do any checking or mitigation, with the effect that:

- you are thrown out of you normal execution path, losing a lot of context to do any mitigation (close a file, close a connection, tell a caller something went wrong)

- you only get a stack trace from which it can be hard to figure out what went wrong

- there can be big impact on user experience : UIs can stop working, servers that stop responding (for all users).

I have very good experiences with using the defensive coding paradigm, but it takes more work to do it right; for many, especially in the communities that use dynamic typing, such as the JS community, this seems to be a too big a hurdle to take. This is unfortunate because it IMO it could greatly improve software quality.

Any feedback is welcome!

(Edit: formatting to improve readability) (Edit: clarified defensive coding as an opposite approach to fail-fast)

Re: Error Handling in Node.js

#58
post #48
post #33

Earlier quoted context omitted.

Once I got used to it I found I kind of like the Go paradigm of checking for errors every time something could go wrong, and (usually) passing the first one up the chain with some additional context info. However, the fact that "ignore error" is an easy and built-in paradigm that even shows up in the official docs: fragileThing, _ := scary.MightNotWork() that fills me with dread.

Could you elaborate? Assuming that scary.MightNotWork() is some kind of ancillary function that is non-essential, why would I want to let it impact the main program. The example that comes to mind would be logging. If I have set up my own "Write logs into network share" call, I'd never ever expect it to throw errors that took down the app. Share down? Don't care. logfile locked/corrupt. Don't care. Try and log, if yo…

> Try and log, if you can't, fail silently without impacting the main purpose of the application/service/whatever.

Are you being serious? I agree that there can be "some kind of ancillary function that is non-essential" but in the case of failed logging you should try sending an email / showing some warning if you have a GUI / try other outputs / crash with a meaningful error especially if you are running under some sort of supervisor... etc.

Of course that doesn't invalidate your main point.

Re: Error Handling in Node.js

#59
post #21

Some of this looks like horrible advice, particularly the defeatist attitude towards what the article calls "programmer errors". Statements to the effect that you can never anticipate or handle a logic error sensibly so the only thing you should ever do is crash immediately are hard to take seriously in 2016. What about auto-saving recovery data first? Logging diagnostic information? Restarting essential services in…

What about auto-saving recovering data? It really depends upon the language and environment used. I work with C (almost legacy code at this point), and if the program generates a segfault, there is no way to safely store any data (for all I know, it could have been trying to auto-save recovery data when it happened). About the best I can hope for is that it shows itself during testing but hey, things slip into produc…

[deleted]

Re: Error Handling in Node.js

#60
post #54
post #52

Can anyone explain why this pattern doesn't work? Or point me to some resource? function myApiFunc(callback) { /* * This pattern does NOT work! */ try { doSomeAsynchronousOperation(function (err) { if (err) throw (err); /* continue as normal */ }); } catch (ex) { callback(ex); } }

There's a footnote about this: https://www.joyent.com/node-js/production/design/errors#fn:1

much obliged
Post reply on HN