I came across some issues with async await when instantiating a class. I have a class user, and when instantiated I wish to automatically hash the password and assign it to the password.
class User {
public userId: string;
public password: string = '';
constructor(public userName: string, public plainPassword: string, public email: string) {
this.userId = uuidv4()
this.userName = userName;
this.email = email.toLowerCase();
this.hashPassword();
}
private async hashPassword(): Promise<void> {
try {
const salt = await bcrypt.genSalt(10);
this.password = await bcrypt.hash(this.plainPassword, salt);
}
catch (error) {
throw error
}
}
The hash password returns nothing. But is a promise function, so when I do tests, I dont get any of the User keys… email, password, userId and username are undefined…
Can you help me?
2
Answers
You’re not waiting for the asynchronous function to finish, and there’s no way to do so in a constructor (since a constructor can’t be async).
If you really want hashing to occur asynchronously "in" the constructor, the
password
field would have to be a promise of a password that will get eventually fulfilled:and to access it, you’d then do
As @akx mentioned, having async constructors in JavaScript/TypeScript is impossible. However, we can circumvent this limitation by leveraging design patterns.
Let’s explore two quick alternatives:
Builder pattern
Factory pattern
In essence, both patterns allow you to control the instantiation process, enhancing the readability and maintainability of your code. While these patterns may not offer a direct solution to the absence of async constructors in JavaScript/TypeScript, they effectively address the underlying problem.