1

Sorry the title couldn't be more specific. I do this in Javascript sometimes to 'attach' a variable to an anonymous function but I'm not sure of the vocabulary so I don't know how to study more about it or see if what I'm doing is optimal.

I'm using MEAN stack with Mongoose to create a getter function on every member of the schemas.

testPlugin.plugin = function(schema, options){
    schema.set('toObject', { getters: true });
    schema.set('toJSON', { getters: true });

    // Simple counter
    let i = 0;

    schema.eachPath((path, type) => {

        /* Add a *different* getter to each member with a different value of `i` */
        type.getters.push(((i, type)=>{
                return function(value){
                console.log(i + ": " + path + ": " + type);
                return value;
            }
        })(i, type));

        i++;
    });
}

Basically if I were to just pass 'i' to the function without using this factory-like pattern like this:

type.getters.push(function(value){
        console.log(i + ": " + path + ": " + type);
        return value;
    });

If there were 5 members to the schema the output would be like:

'5: path.path: String'
'5: path.path: Integer'
'5: path.path: ObjectID'
'5: path.path: String'

(note the shared number and path as these aren't individually 'stored') Instead of having the value 'stored' as it were in the function which, when executed on a schema would trace out something like

'1: patha: String'
'2: pathint: Integer'
'3: _id: ObjectID'
'4: path.path: String'

So instead I'm returning a new, separate function each time by returning a function from an auto-executed parent function... is this correct or am I going overkill here? The code looks messy either way to me.

Again, just really looking for the name of this pattern or what pattern I should be using. I saw something similar to this but I forgot.

Thanks in advance.

Toby
  • 226
  • 1
  • 11
  • 1
    Is called a self-invokind function, you can also do something like this: `(function(a,b){....}).bind(this,[a,b])`; – Titus Sep 12 '16 at 05:44
  • 2
    If I am not mistaken, what you are looking at is a closure with a self-invoking function. The issue is due to JavaScript's scoping mechanics. See this: http://stackoverflow.com/questions/1451009/javascript-infamous-loop-issue However, you do not have to write this sort of code in ES6 where you can use `let` instead of var. – VanDanic Sep 12 '16 at 05:45
  • 2
    @Titus and VanDanic - "Self-invoking" would mean the function called itself, which isn't the case here. "Immediately invoked function expression" (IIFE) is a more accurate term, but what the OP wants to achieve doesn't necessarily require an IIFE... – nnnnnn Sep 12 '16 at 05:45
  • @VanDanic, how could I use let here? Would I use it in the parent, factory or returned function? Thanks. – Toby Sep 12 '16 at 07:10

0 Answers0