0

I have a library which has defined a class as this. I would like to call getMe() function outside class A with my own me.

var me;
var A = function(_me){
  me = _me;
}
A.prototype.getMe = function(){
    me();
}

I have class B where I call it like

A.prototype.getMe.call(this) but this would throw an error as me is not defined. How can I pass me into this ? I would like to make minimum changes to getMe function.

The only way to do this is, I guess to use an if .

A.prototype.getMe = function(){
  if(!me){
    me = this.myMe
  }
  me();
}

So I did A.prototype.getMe.call({myMe: myMe}, args) but would it define the variable in global space ?

6
  • Can you create a working snippet <> which replicate your issue? Commented Nov 13, 2017 at 12:50
  • Your code, as written, makes no sense. For example, A.prototype.getMe should be outside of the constructor. Commented Nov 13, 2017 at 12:50
  • @Andy SOrry about that. Just changed it. Commented Nov 13, 2017 at 13:04
  • The code is still quite problematic, but I've updated my answer for the change. Commented Nov 13, 2017 at 13:21
  • Don't edit questions such that they completely invalidate existing answers. I've rolled back the edit, since your second attempt at posting the code was an accurate reflection of the Map thing (A) [lurkers: no, not the standard Map], and then added back your edit adding to the question (but changed it to be in terms of A/me, not Map/myExec) Commented Nov 13, 2017 at 13:34

1 Answer 1

3

You can't reasonably do this, not least because A is fundamentally broken (see below).

Whether you can do it at all depends entirely on where the A code is: If it's at global scope, you can do what you want but shouldn't. If it isn't at global scope, you can only do it from code within the scope where me is declared (or a scope within it).

If it's at global scope, you'd do it like this (but don't :-) ):

// The "A" Code
var me;
var A = function(_me){
  me = _me;
}
A.prototype.getMe = function(){
  me();
}

// Your code using it
new A(); // Create `A.prototype.getMe`, because unless
         // `A` is called at least once, it doesn't exist
var myMe = function() {
  console.log("myMe called");
};
me = myMe; // Set the global `me`
A.prototype.getMe(); "myMe called"

The only way to do this is, I guess to use an if .

if(!me){
  me = this.myMe
}

So I did A.prototype.getMe.call({myMe: myMe}, args) but would it define the variable in global space ?

Yes, it would. That's what me = this.myMe does.

From that observation, it sounds like you can modify A's code. If so, fix it so that it doesn't define a prototype function in terms of a global variable. Perhaps isolate the code from the function into a function that doesn't expect to be called on an instance and pass in me as a parameter.

I am working on an existing library to make a small change. So I can only change inside getMe function definition. And I cant change var me definition.

In that case, you can add a new optional parameter at the end, and use that if provided and me if not provide:

A.prototype.getMe = function(myMe){
    var meToCall = myMe || me;
    meToCall();
};

Live Example:

// The "A" Code
var me;
var A = function(_me){
  me = _me;
}
A.prototype.getMe = function(myMe){
  var meToCall = myMe || me;
  meToCall();
}

// Your code using it
A.prototype.getMe(function() {
  console.log("My me!");
});


And, separately, A is fundamentally broken if it's really as shown (barring an extremely specific use-case). Having constructor code set a global (global at least to A's code) that's then used by a prototype function is a huge design and maintenance red flag.

Consider the cross-talk horror:

// The "A" Code
var me;
var A = function(_me){
  me = _me;
}
A.prototype.getMe = function(){
  me();
}

// Using it
var a1 = new A(function() {
  console.log("me1");
});
a1.getMe(); // "me1" -- so far so good
var a2 = new A(function() {
  console.log("me2");
});
a2.getMe(); // "me2" -- yup, still fine
a1.getMe(); // "me2" -- what the...?!?!?!!

Sign up to request clarification or add additional context in comments.

5 Comments

I just changed with the right code. I think now it would make much sense.
Thanks. That explains a lot. I am working on an existing library to make a small change. So I can only change inside getMe function definition. And I cant change var me definition. And as var me is defined on top of A.js , wouldnt it be inside the scope of A even if i dont call new A(_me)
@raj: If you can change getMe, you're golden, just add a new optional parameter to it; see updated answer above the line above.
I cant add it as a parameter because it is a public function. If a user accidentally pass an extra argument, it would be considered as myMe instead of existing me.
@raj: That's easily handled, just make the extra parameter complex. For instance: getMe({marker: 42, me: function() { }) then in getMe: var meToCall = theparam && theparam.marker === 42 && typeof theparam.me === "function" ? theparam.me : me;

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.