Assuming I have two files. One file with a class where the method hello
just console.logs this
:
// Class.js
class Test {
constructor() {
this.inside = true;
}
hello() {
console.log('inside hello')
console.log(this);
}
}
module.exports = new Test();
and another file which executes the method hello
of this class:
// index.js
const Test = require('./Class.js');
Test.hello();
// -> 'inside hello'
// -> { inside: true }
Everything works as expected, the this
in the hello()
method has the correct scope.
But, when I make a new instance of the class and export just hello
of this new instance:
// Class.js
class Test {
constructor() {
this.inside = true;
}
hello() {
console.log('inside hello')
console.log(this);
}
}
module.exports = (new Test()).hello; // <- just hello is exported
then the scoping of the hello()
changed and it seems it is not a part of the class anymore:
// index.js
const hello = require('./index.js');
hello();
// -> 'inside hello'
// -> undefined
Is there a reason, why this single exported function acts so differently?
I tried it in Python, and it worked (maybe it does in other languages as well):
# Class.py
class Class:
def __init__(self):
self.test = 'hello'
def hello(self):
print('inside hello')
print(self)
hello = Class().hello
# index.py
from Class import hello
hello()
# -> 'inside hello'
# -> <Class.Class instance at 0x10e26e488>
When you call hello()
standalone, it has no calling context - it's not being called from an object, when said object would ordinarily be its calling context. (such as Test.hello();
- the calling context would be Test
in that line)
If you want to bind its calling context so that it's usable as a standalone function, you should export the bound function, such as:
const test = new Test();
module.exports = test.hello.bind(test);