11

I would like to add a one hour timeout to this process so that it will not stay forever in the case of a stream deadlock. The only problem is if I say setTimeout, the process has no opportunity to end ahead of schedule.

Is there a way to put in a forced exit timeout after about an hour, without keeping the process running? Or am I stuck between using process.exit and doing without this timeout?

700 Software
  • 85,281
  • 83
  • 234
  • 341

3 Answers3

21

I don't know when unref was added to Node but this is now one possible solution. Reusing Matt's code:

var timeoutId = setTimeout(callback, 3600000);
timeoutId.unref(); // Now, Node won't wait for this timeout to complete if it needs to exit earlier.

The doc says:

In the case of setTimeout when you unref you create a separate timer that will wakeup the event loop, creating too many of these may adversely effect event loop performance -- use wisely.

Don't go hog wild with it.

Louis
  • 146,715
  • 28
  • 274
  • 320
  • 1
    Nice, I hadn't heard of this. [`unref` was added in Node 0.9.1.](https://github.com/joyent/node/releases/tag/v0.9.1) – Matt Ball Dec 30 '13 at 15:21
8

If you save the value returned by setTimeout you can always cancel it before it fires with clearTimeout, like this:

var timeoutId = setTimeout(callback, 3600000); // 1 hour

// later, before an hour has passed
clearTimeout(timeoutId);
Matt Ball
  • 354,903
  • 100
  • 647
  • 710
  • I was hoping for something that did not require `clearTimeout`. I will do without. – 700 Software Aug 10 '11 at 17:33
  • 1
    Is any reason why not use clearTimeout? Performance or religion? – Romick Oct 17 '19 at 09:33
  • @Romick, there's a very good reason for this. If you create a method, or a library, that uses a timeout (or an interval -- unref() works for intervals too), you don't want consumers of your code to have to know about the internal details of your code, and require them to call close or shutdown methods to clean up your timers. I just created code the keeps track of the ever-changing rules for Daylight Saving Time in countries all over the world. By default, my code polls once per day to look for updates. With unref(), my users don't need to worry about killing the interval I use. – kshetline Dec 25 '20 at 00:40
1

Possible Solution using a new feature that was implemented as process.watchers(), but I don't know whether it was included in a released version yet. The pull request is still open as of this post.

But generally speaking, you would write a custom setTimeout function that add all timeouts to a counter, and right before the timeouts to the callback, it would remove from the counter.

Then create an ongoing interval, and the interval would check and notice when all the walkers are just timeouts set by your custom function.

When it notices this, it would (clear all of its those timeouts, causing an) exit.

This of course is not great, because

  • The concept is not proven. (I do not know what kind of data will be returned by process.watchers(), or if it even works yet)
  • The interval is a polling method. (not nice if you want immediate return at the same time as low CPU usage)
Community
  • 1
  • 1
700 Software
  • 85,281
  • 83
  • 234
  • 341