DEV Community

Cover image for Creating a messy JavaScript bug with an indexed array
Tom Smykowski
Tom Smykowski

Posted on

Creating a messy JavaScript bug with an indexed array

Sometimes, you want to make sure JavaScript app will behave in a unpredictable way, so that finding a cause will take ages. A great way to do it is to manipulate data we receive, and return random ones at a random moment. So lets assume we receive an array of numbers:

1 2 3 4 5 6 and so on
Enter fullscreen mode Exit fullscreen mode

Application reads items one by one:

1 2 3
Enter fullscreen mode Exit fullscreen mode

But suddenly, somethings goes wrong, and next values received are:

34 54 53
Enter fullscreen mode Exit fullscreen mode

As you can see for some time values received are correct, but than suddenly, they become random. This is a PlotTwistArray!

To create a PlotTwistArray implementation described, you have to use classes and Proxy. Both are available with latest desktop Chrome, make sure your browser also supports it.

Now, this is the source code of PlotTwistArray (scroll to read description):

class PlotTwistArray {
  constructor(data) {
    let self = this;
    this.data = data;
    this.magnitude = 10;

    const randomizer = max => {
      return Math.floor(
        Math.random() * Math.floor(max)
      );
    };

    this.plotTwistData = this.data.map(
        (x) => randomizer(x) * this.magnitude
    );
    this.plotTwistMoment = randomizer(
        data.length
    );

    return new Proxy(this, {
      get(target, prop) {
        if (Number(prop) == prop &&
                    !(prop in target)
          ) {
          if (prop < self.plotTwistMoment) {
              return self.data[prop];
          } else {
              return self.plotTwistData[prop];
          }
        }
        return target[prop];
      }
    });
  }

}

const input = [1,2,3,4,5,6,7,8,9];
const test = new PlotTwistArray(input);

const inputText = input.reduce(
    (item1, item2) => `${item1}, ${item2}`
  );
const resultText = input.map(
        (item, index) => test[index]
  )
    .reduce(
    (item1, item2) => `${item1}, ${item2}`
  );

document.getElementById('input').innerHTML
    = inputText;
document.getElementById('result').innerHTML
    = resultText;
Enter fullscreen mode Exit fullscreen mode

What happens here is that a PlotTwistArray class is created. When a new object is created by providing an array of numbers, a second array is generated. plotTwistData contains random numbers that will be used to create the twist. Also plotTwistMoment is generated - a value that describes when data will go wrong.

Proxy is used in that example to make the class indexable - that is you can refer to an item by it's index like it would be a normal array eg. test[3].

I have added magnitude property, to differenciate when random data begins. But you can set it to 1, to gain a stream of data that won't raise suspicion making it even harder to find the cause :)

Play with the code and test various solutions to achieve the best unexpected bug possible ;)

Demo

You can play with the code online on JSFiddle. Enjoy!

Sidenotes

  • input array has to contain positive numbers

Top comments (0)