Lazy Variables in a Stimulus Controller

Is there anything available in Stimulus (or JavaScript ES6) to create “lazy” variables? For example, in Ruby we can do something like this:

def user_id
  @user_id ||= compute_user_id #resource intensive
end

The first time #user_id is called it will compute it but subsequent calls will used the “cached” version.

This is usually called memoization. There are many techniques for memoizing functions in ES6, but Stimulus doesn’t (yet?) have one built-in.

https://lodash.com/docs/4.17.10#memoize
https://steelsojka.github.io/lodash-decorators/variable/index.html#static-variable-Memoize

I like this slight variation of MDN’s “Smart / self-overwriting / lazy getters”:

class X {
  // …
  
  get id() {
    console.log("Computing ID!")
    const value = computeId()
    Object.defineProperty(this, "id", { value })
    return value
  }
}
> x = new X()
X {}

> x.id
Computing ID!
123

> x.id
123

> x.id
123
2 Likes

Thanks for the context and background, @sam! I would love to see something like this built in to Stimulus. Especially since we already have the targets declaration.

And thanks for the example, @javan! I ended up going with something like this, and was wondering if there are any pitfalls I may be missing.

get search() {
  if (this._search == undefined) {
    this._search = new mapkit.Search
  }
  return this._search
}
1 Like