What is the JavaScript version of sleep()?

ID : 192

viewed : 101

Tags : javascriptsleepjavascript





Top 5 Answer for What is the JavaScript version of sleep()?

vote vote

90

2017 — 2021 update

Since 2009 when this question was asked, JavaScript has evolved significantly. All other answers are now obsolete or overly complicated. Here is the current best practice:

function sleep(ms) {   return new Promise(resolve => setTimeout(resolve, ms)); }  async function demo() {   console.log('Taking a break...');   await sleep(2000);   console.log('Two seconds later, showing sleep in a loop...');    // Sleep in loop   for (let i = 0; i < 5; i++) {     if (i === 3)       await sleep(2000);     console.log(i);   } }  demo();

This is it. await sleep(<duration>).

Or as a one-liner:

await new Promise(r => setTimeout(r, 2000)); 

Note that,

  1. await can only be executed in functions prefixed with the async keyword, or at the top level of your script in an increasing number of environments.
  2. await only pauses the current async function. This means it's not blocking the execution of the rest of the script, which is what you want in the vast majority of the cases. If you do want a blocking construct, see this answer using Atomics.wait, but note that most browsers will not allow it on the browser's main thread.

Two new JavaScript features (as of 2017) helped write this "sleep" function:

Compatibility

If for some weird reason you're using Node older than 7 (which has reached end of life), or are targeting old browsers, async/await can still be used via Babel (a tool that will transpile JavaScript + new features into plain old JavaScript), with the transform-async-to-generator plugin.

vote vote

89

(See the updated answer for 2016)

I think it's perfectly reasonable to want to perform an action, wait, and then perform another action. If you are used to writing in multi-threaded languages, you probably have the idea of yielding execution for a set amount of time until your thread wakes up.

The issue here is that JavaScript is a single-thread event-based model. While in a specific case, it might be nice to have the whole engine wait for a few seconds, in general it is bad practice. Suppose I wanted to make use of your functions while writing my own? When I called your method, my methods would all freeze up. If JavaScript could somehow preserve your function's execution context, store it somewhere, then bring it back and continue later, then sleep could happen, but that would basically be threading.

So you are pretty much stuck with what others have suggested -- you'll need to break your code up into multiple functions.

Your question is a bit of a false choice, then. There is no way to sleep in the way you want, nor should you pursue the solution you suggest.

vote vote

75

In JavaScript, I rewrite every function so that it can end as soon as possible. You want the browser back in control so it can make your DOM changes.

Every time I've wanted a sleep in the middle of my function, I refactored to use a setTimeout().

Edit

The infamous sleep, or delay, function within any language is much debated. Some will say that there should always be a signal or callback to fire a given functionality, others will argue that sometimes an arbitrary moment of delay is useful. I say that to each their own and one rule can never dictate anything in this industry.

Writing a sleep function is simple and made even more usable with JavaScript Promises:

// sleep time expects milliseconds function sleep (time) {   return new Promise((resolve) => setTimeout(resolve, time)); }  // Usage! sleep(500).then(() => {     // Do something after the sleep! }); 
vote vote

68

In Firebug (and probably other JavaScript consoles), nothing happen after hitting enter, only after the sleep duration specified (...)

function sleepFor(sleepDuration){     var now = new Date().getTime();     while(new Date().getTime() < now + sleepDuration){ /* Do nothing */ } } 

Example of use:

function sleepFor(sleepDuration){     var now = new Date().getTime();     while(new Date().getTime() < now + sleepDuration){          /* Do nothing */      } }  function sleepThenAct(){     sleepFor(2000);     console.log("Hello, JavaScript sleep!"); }  sleepThenAct()

Note: Only for debugging and development

vote vote

53

I agree with the other posters. A busy sleep is just a bad idea.

However, setTimeout does not hold up execution. It executes the next line of the function immediately after the timeout is SET, not after the timeout expires, so that does not accomplish the same task that a sleep would accomplish.

The way to do it is to breakdown your function into before and after parts.

function doStuff() {   // Do some things   setTimeout(continueExecution, 10000) // Wait ten seconds before continuing }  function continueExecution() {    // Finish doing things after the pause } 

Make sure your function names still accurately describe what each piece is doing (i.e., GatherInputThenWait and CheckInput, rather than funcPart1 and funcPart2)

This method achieves the purpose of not executing the lines of code you decide until after your timeout, while still returning control back to the client PC to execute whatever else it has queued up.

As pointed out in the comments this will absolutely not work in a loop. You could do some fancy (ugly) hacking to make it work in a loop, but in general that will just make for disastrous spaghetti code.

Top 3 video Explaining What is the JavaScript version of sleep()?







Related QUESTION?