Error guides

Fix "StopIteration is not defined" on V8

ReferenceError: StopIteration is not defined
SyntaxError: Unexpected number            (legacy `yield` in a plain function)

Why it happens

Rhino supported JavaScript 1.7 iterators: an __iterator__ method, the global Iterator() helper, and ending iteration with throw StopIteration. Old-style generators used yield inside a normal function. None of these exist in standard JavaScript.

The fix

// Rhino
myList.__iterator__ = function () {
  var i = 0, a = this.items;
  return { next: function () { if (i >= a.length) throw StopIteration; return a[i++]; } };
};
for (var x in myList) Logger.log(x);

// V8
myList[Symbol.iterator] = function* () {
  for (var i = 0; i < this.items.length; i++) yield this.items[i];
};
for (var x of myList) Logger.log(x);

Hand-written iterators return { value, done } instead of throwing:

function rangeIterator(n) {
  var i = 0;
  return { next: function () { return i < n ? { value: i++, done: false } : { value: undefined, done: true }; } };
}

Also Rhino-only

obj.__count__ → Object.keys(obj).length. __parent__ has no equivalent. __noSuchMethod__ → a Proxy with a get trap.

How V8Shift handles it

All iterator-protocol uses, legacy generators and __count__/__parent__/__noSuchMethod__ are flagged as errors with file and line.

Have a whole project to migrate? Paste your .gs or upload a zip for a free V8 compatibility report — every occurrence of this pattern with file and line, plus an auto-rewritten project.
Related errors