Reputation: 2415
I am unable to access objects declared within a class in Typescript from functions. Here's what I have:
export class QUestions {
credentials:mysqlCredentials.MySQLCredentials;
sqlConnector:mysql.Mysql;
constructor() {
this.credentials = new mysqlCredentials.MySQLCredentials('192.168.249.139', 'dev', 'dev', 'test');
this.sqlConnector = new mysql.Mysql(this.credentials);
}
addQuestion(req, res) {
var q = ...<Lot of code over here> ;
this.sqlConnector.query(q, null); //Error shown for this line
res.send();
}
}
Error:
TypeError: Cannot call method 'query' of undefined
If the code is structured as shown above i.e. the sqlConnector variable is defined in the Typescript class, it throws the error. If I place the sqlConnector outside the Typescript class it works fine. I need to fix this as I need the sqlConnector object inside the class.
export class Questions {
credentials:mysqlCredentials.MySQLCredentials;
constructor() {
this.credentials = new mysqlCredentials.MySQLCredentials('192.168.249.139', 'dev', 'dev', 'test');
sqlConnector = new mysql.Mysql(this.credentials);
}
addQuestion(req, res) {
var q = ...<Lot of code over here> ;
sqlConnector.query(q, null); //Error shown for this line
res.send();
}
}
var sqlConnector;
Upvotes: 0
Views: 518
Reputation: 3556
It is also possible to assign class instance to variable, which after compilation will remain within module scope:
var scl:QUestions;
export class QUestions {
credentials:mysqlCredentials.MySQLCredentials;
sqlConnector:mysql.Mysql;
constructor() {
scl = this;
this.credentials = new mysqlCredentials.MySQLCredentials('192.168.249.139', 'dev', 'dev', 'test');
this.sqlConnector = new mysql.Mysql(this.credentials);
}
addQuestion(req, res) {
var q = ...<Lot of code over here> ;
scl.sqlConnector.query(q, null);
res.send();
}
}
Be aware though, that it might cause some problems if you have many instances of the QUestions class within single module. Still in most cases should work fine.
Upvotes: 0
Reputation: 250952
Are you calling the class in a new context (for example using an event handler)?
If so, this
becomes the context of the event, not the class context. This is a common JavaScript problem that can happen in TypeScript too.
You can solve the scope issue in a number of ways:
If you use an arrow function to assign the function to a member on the Questions class, it will always use the class scope.
export class Questions {
credentials:mysqlCredentials.MySQLCredentials;
sqlConnector:mysql.Mysql;
constructor() {
this.credentials = new mysqlCredentials.MySQLCredentials('192.168.249.139', 'dev', 'dev', 'test');
this.sqlConnector = new mysql.Mysql(this.credentials);
}
addQuestion = (req, res) => {
var q = ...<Lot of code over here> ;
this.sqlConnector.query(q, null); //Error shown for this line
res.send();
}
}
call
to set the scope contextThis alternative solution means the Questions class doesn't need to be concerned about scope - if you call the method from a different scope context, you simply use call
to assign the question instance as the scope.
element.onclick = function () {
questions.addQuestion.call(questions, argA, argB);
};
Upvotes: 1