Let's say I have the following class:
function MyClass(){
this.public = function(){
console.log(private);
};
var private = 10;
}
var test = new MyClass;
test.public(); // logs 10
test.private; // undefined
I want to know if I can access the private variable from the outside. Looking at chrome's console it seems to be possible, since its context is shown:
EDIT: Just to clarify: I know how to properly expose it. Just want to be sure if there isn't some hacky way to access it.
Let's say I have the following class:
function MyClass(){
this.public = function(){
console.log(private);
};
var private = 10;
}
var test = new MyClass;
test.public(); // logs 10
test.private; // undefined
I want to know if I can access the private variable from the outside. Looking at chrome's console it seems to be possible, since its context is shown:
EDIT: Just to clarify: I know how to properly expose it. Just want to be sure if there isn't some hacky way to access it.
Share Improve this question edited May 29, 2016 at 4:34 GBarroso asked May 29, 2016 at 4:23 GBarrosoGBarroso 4772 gold badges9 silver badges19 bronze badges 6-
private
is not a property oftest
object to be accessed using.
notation..Variable inside closure can only be accessed inside closure.. – Rayon Commented May 29, 2016 at 4:26 - First, it's not a good idea to expose private member variables. Second, a function isn't a class. Please don't confuse Javascript with an object oriented language. Third, just create something like an IIFE and return something with a getter function for your private variable. Check out: en.wikipedia/wiki/Immediately-invoked_function_expression – Tad Donaghe Commented May 29, 2016 at 4:27
- Yeah I know it isn't a real class. I'm not using this code I just want to know if it IS possible or not – GBarroso Commented May 29, 2016 at 4:28
- 1 I don't think there's any built in way of doing proper reflection in Javascript. There may be libraries that fake it. Chrome can do it just because the V8 engine probably has hacky stuff built in that would only work with V8. Google "Javascript reflection" – Tad Donaghe Commented May 29, 2016 at 4:33
-
You will have to expose it with a getter like:
this. getPrivate = function() {return private; }
– Irshu Commented May 29, 2016 at 4:34
3 Answers
Reset to default 6Your private
variable is local to that function scope and within Javascript, there is no access to variables inside a scope from outside the scope. You can ONLY access it from within the scope. There are no ways to get around this from Javascript code itself.
What a debugger can do (which has access to the VM internals) is different than what regular Javascript code can do. The debugger can look inside of scopes, but JS code from outside the scope cannot.
Obviously you can make an accessor for it, but without an accessor, there is no way to get to it from the outside.
The variable private
is "trapped" inside MyClass
's closure. You cannot access it unless some code exposes it, like a "getter" function.
function MyClass(){
this.getter= function(){
return private;
};
var private = 10;
}
By the way, private
is a reserved keyword.
There's one hacky, but not super-convenient, method.
Drop a breakpoint somewhere that has access to the scope.
function MyClass(){
this.public = function(){
console.log(private); // <<< BREAKPOINT HERE!
};
var private = 10;
}
Now call the function that is public that'll get you to that breakpoint.
While you're stuck there, pull private
into global scope however you'd like by typing something like this on the console:
var window.foo = private;
Profit. You can now grab foo
from the console whenever you'd like.
And you can do this for anything available in scope there. If you had var private2 = 7;
in there under var private
, you've got access to it, too, even if it's not used in this.public
.
Pros:
- Access the value any time while you're debugging.
- Congrats! You're peak hipster.
Cons:
- Reload the page and you've gotta hack it again.
- If you forget and put two
foo
s into global state, you'll overwrite the second.- Spaghetti scope weirds language.
I keep figuring there's gotta be a sneakier (and more convenient) way, maybe like monkeypatching a public method back into itself with eval
with the scope breaking code like the above (which would eliminate the breakpoint calling), but haven't quite found it yet.