Trying to test a nodejs backend using jest.
this test is passing 70% of the time but sometimes fails.
my test:
both userInput and copycatUserInput are saved to the database and create a duplicate email.
test("Register with the same email twice shoud throw an error.", async () => {
const userInput: ICreateUserInput = {
email: "same-email@gmail.com",
username: "username",
password: "tesT$1234",
};
const copycatUserInput: ICreateUserInput = {
email: "same-email@gmail.com",
username: "differentUsername",
password: "tesT$1234",
};
> await registerUser(userInput);
> await expect(registerUser(copycatUserInput)).rejects.toThrow(/(Email address is already exists)/);
});
the fail reason:
expect(received).rejects.toThrow()
Received promise resolved instead of rejected
Resolved to value: {"token": "eyJhb...
here is my mongoose schema:
both username and email fields are unique
const schemaOptions: SchemaOptions = { timestamps: true };
const userSchema = new Schema(
{
username: {
type: String,
required: true,
unique: true,
},
email: {
type: String,
required: true,
unique: true,
lowercase: true,
},
password: {
type: String,
required: true,
},
status: String,
},
schemaOptions,
);
export default model<IUser>("User", userSchema);
and registerUser function:
export default async (registerInput: ICreateUserInput): Promise<ILoginUserResult> => {
/**
* validate props.
*/
if (!isEmail(registerInput.email)) throw new Error("Email address is not valid.");
if (!isValidUsername(registerInput.username)) throw new Error("Username is not valid.");
if (!isStrongPassword(registerInput.password)) throw new Error("Password is not valid.");
/**
* gnerate hashed password.
*/
try {
const hashPassword = await createHashedPassword(registerInput.password);
/**
* create new user.
*/
const doc: ICreateUserInput = {
email: registerInput.email,
username: registerInput.username,
password: hashPassword,
status: registerInput.status ? registerInput.status : "",
};
/**
* save the user in the database.
*/
const user = await new User(doc).save();
return {
user,
token: getAuthToken(user),
};
} catch (error) {
/**
* throws a duplicate email error.
*/
if (error.message && `${error.message}`.includes("email_1 dup key:")) {
throw new Error("Email address is already exists");
}
/**
* throws a duplicate username error.
*/
if (error.message && `${error.message}`.includes("username_1 dup key:")) {
throw new Error("Username is already exists");
}
/**
* may be that mongoose or bcrypt are throwing..
*/
Logger.error(`auth.registerUser => ${error}`);
throw new Error(`Error: Failed to register user: ${error.message}`);
}
i also got useCreateIndex: true in the connection options
and tried to wait for the indexes to be created:
user.once("index", () => {
user = await new User(doc).save();
});
Thank you for your help
EDIT:
ended up running tests separately, make a new connection on each testsuit (beforeAll) can knock things out :(
"scripts": {
"test": "jest --runInBand",
},