The live preview of Pens makes developing on CodePen fast and fun. Unfortunately it's easy to create infinite while, for or do loops in JavaScript.

When you create an infinite loop in CodePen the browser tab hangs preventing you from being able to change the code. This makes infinite loops extremely frustrating.

Viewing your public profile page isn't much different. The grid of Pens run each Pen in an iFrame stopping you from deleting the Pen since the infinite loop hangs the tab.

Ideally CodePen would be able to detect an infinite loop and break out of it. Luckily for everyone on CodePen this is exactly what we're able to do.

Instrumenting JavaScript

There is no way to ask JavaScript if it's hung once it's started executing. What we can do is instrument the JavaScript code to check if it's timed out prior executing the code in a for loop.

Instrumenting code is a fancy way of saying rewrite JavaScript code so that it's simple to monitor.

The goal is to take a piece of JavaScript and rewrite it to call a monitoring function prior to executing code inside a function or loop. This would give the monitoring function the ability to check if it's hanging the browser and break out of the loop.

If we could rewrite this infinite for loop:

  for (var i = 0;; i++) {
  console.log("hello for loop.");
}

console.log("We'll never reach this line of code");

To this for loop:

  for (var i = 0;; i++) {
    if (window.CP.shouldStopExecution(1)) {
        break;
    }
    console.log('hello for loop.');
}

console.log('finished because we broke out of the loop');

We would be able to break out of the loop if we detect it is hanging.

The logic to detect a hanging for loop is simple. Possibly too simple (more about that in a later post). That number passed to the shouldStopExecution function is the loop identifier.

shouldStopExecution keeps track of when a function was first called. If the same loop is called for more than 75ms we break out of the loop.

The Tools

Modern JavaScript tools are truly fantastic.

To parse the JavaScript I used Esprima. Esprima creates a data structure called an abstract syntax tree (AST). It's a data structure that represents the code in code (oh my, so meta!).

Our code traverses the AST and finds function calls and loops. We insert a call to shouldStopExecution right before any of the JavaScript code is executed.

To regenarate the JavaScript we use Escodegen.

Esprima and Escodgen make it super simple to solve the infinite loop problem. The tools are solid and extremely well documented.

Infinite loops have been a pain since the day we launched CodePen. I think all CodePen users will appreciate this solution.


14,611 6 19