Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat/be/tests user module #1147

Merged
merged 4 commits into from
Nov 14, 2024
Merged

feat/be/tests user module #1147

merged 4 commits into from
Nov 14, 2024

Conversation

ajhollid
Copy link
Collaborator

This PR adds tests for the user module. It also performs some minor refactoring

  • Add tests for user module
  • Inject depdendencies into functions that use them for ease of testing
  • Add return values for two funcitons that previously returned undefined

Copy link

@llamapreview llamapreview bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

=== FINAL PR REVIEW COMMENT FORMAT BEGINS ===

Auto Pull Request Review from LlamaPReview

1. Overview

1.1 PR Summary

  • Business value and requirements alignment: This PR adds tests for the user module and performs some minor refactoring to enhance testability and ensure the robustness of the user module, which aligns with the goal of improving overall system reliability.
  • Key components modified: The primary changes are in Server/db/mongo/modules/userModule.js and the addition of Server/tests/db/userModule.test.js.
  • Impact assessment: The changes mainly impact the user module by introducing dependency injection for better testability and adding comprehensive tests.
  • System dependencies and integration impacts: No significant changes to integration points. The primary impact is on the testability and robustness of the user module.

1.2 Architecture Changes

  • System design modifications: Dependency injection is introduced for better testability.
  • Component interactions: Functions now accept dependencies as parameters, reducing coupling and enhancing testability.
  • Integration points: No significant changes to integration points.

2. Detailed Technical Analysis

2.1 Code Logic Deep-Dive

Core Logic Changes

Server/db/mongo/modules/userModule.js - insertUser
  • Submitted PR Code:
    const insertUser = async (
      userData,
      imageFile,
      generateAvatarImage = GenerateAvatarImage
    ) => {
      try {
        if (imageFile) {
          userData.profileImage = {
            data: imageFile.buffer,
            contentType: imageFile.mimetype,
          };
    
          const avatar = await generateAvatarImage(imageFile);
          userData.avatarImage = avatar;
        }
    
        if (userData.role.includes("superadmin")) {
          const team = new TeamModel({
            email: userData.email,
          });
          userData.teamId = team._id;
          userData.checkTTL = 60 * 60 * 24 * 30;
        }
    
        const newUser = new UserModel(userData);
        return await newUser.save();
      } catch (error) {
        error.service = SERVICE_NAME;
        error.method = "insertUser";
        throw error;
      }
    };
  • Analysis:
    • Current logic and potential issues: The function now accepts generateAvatarImage as a parameter, making it easier to test.
    • Edge cases and error handling: The function handles the case where imageFile is provided and generates an avatar image. It also handles the creation of a team if the user is a superadmin.
    • **Cross-component impact **: No significant cross-component impact.
    • **Business logic considerations **: The business logic remains the same, with the addition of dependency injection for testing purposes.
  • LlamaPReview Suggested Improvements: None for this section.
    • **Improvement rationale **: None needed as the changes are well-structured and enhance testability without altering core functionality.
Server/db/mongo/modules/userModule.js - updateUser
  • Submitted PR Code:
    const updateUser = async (
      req,
      res,
      parseBoolean = ParseBoolean,
      generateAvatarImage = GenerateAvatarImage
    ) => {
      const candidateUserId = req.params.userId;
      try {
        const candidateUser = { ...req.body };
        if (parseBoolean(candidateUser.deleteProfileImage) === true) {
          candidateUser.profileImage = null;
          candidateUser.avatarImage = null;
        } else if (req.file) {
          candidateUser.profileImage = {
            data: req.file.buffer,
            contentType: req.file.mimetype,
          };
    
          const avatar = await generateAvatarImage(req.file);
          candidateUser.avatarImage = avatar;
        }
    
        const updatedUser = await UserModel.findByIdAndUpdate(
          candidateUserId,
          candidateUser,
          { new: true }
        );
        return updatedUser;
      } catch (error) {
        error.service = SERVICE_NAME;
        error.method = "updateUser";
        throw error;
      }
    };
  • Analysis:
    • Current logic and potential issues: The function now accepts parseBoolean and generateAvatarImage as parameters, improving testability.
    • Edge cases and error handling: The function handles the case where the profile image is deleted or updated. It also handles errors by throwing an exception with additional context.
    • **Cross-component impact **: No significant cross-component impact.
    • **Business logic considerations **: The business logic remains the same, with the addition of dependency injection for testing purposes.
  • LlamaPReview Suggested Improvements: None for this section.
    • **Improvement rationale **: None needed as the changes are well-structured and enhance testability without altering core functionality.
Server/db/mongo/modules/userModule.js - deleteAllOtherUsers
  • Submitted PR Code:
    const deleteAllOtherUsers = async () => {
      try {
        await UserModel.deleteMany({ role: { $ne: "superadmin" } });
        return true;
      } catch (error) {
        error.service = SERVICE_NAME;
        error.method = "deleteAllOtherUsers";
        throw error;
      }
    };
  • Analysis:
    • Current logic and potential issues: The function now returns true after deleting all non-superadmin users.
    • Edge cases and error handling: The function handles errors by throwing an exception with additional context.
    • **Cross-component impact **: No significant cross-component impact.
    • **Business logic considerations **: The business logic remains the same, with the addition of a return value for better testability.
  • LlamaPReview Suggested Improvements: None for this section.
    • **Improvement rationale **: None needed as the changes are well-structured and enhance testability without altering core functionality.

Cross-cutting Concerns

  • Data flow analysis: The data flow is correctly handled, with proper error handling and input validation.
  • State management implications: No significant state management implications are identified.
  • Error propagation paths: Errors are propagated with additional context, aiding in debugging and monitoring.
  • Edge case handling across components: The functions handle various edge cases, including image file handling and role-based operations.

Algorithm & Data Structure Analysis

  • Complexity analysis: The functions have a straightforward structure with clear error handling.
  • Performance implications: No significant impact on performance.
  • Memory usage considerations: No potential memory leaks are identified.

2.2 Implementation Quality

  • Code organization and structure: The code is well-organized and modular, with clear separation of concerns.
  • Design patterns usage: The use of dependency injection improves adherence to design patterns for testability.
  • Error handling approach: The functions handle exceptions by throwing them with additional context.
  • Resource management: No significant impact on resource utilization.

3. Critical Findings

3.1 Potential Issues

Critical Issues

  • 🔴 Critical Issues
    • Issue description: None identified.
    • Impact: N/A
    • Recommendation: N/A

Warnings

  • 🟡 Warnings
    • Warning description: Ensure error handling consistency across all functions.
    • Potential risks: Inconsistent error handling can lead to reduced maintainability and debuggability.
    • Suggested improvements: Standardize error handling across all functions, ensuring consistent error messages and context.

3.2 Code Quality Concerns

  • Maintainability aspects: The code is more maintainable with improved testability.
  • Readability issues: The code is well-structured and readable.
  • Performance bottlenecks: No significant performance bottlenecks are identified.

4. Security Assessment

4.1 Security Considerations

  • Authentication/Authorization impacts: No significant changes to authentication or authorization.
  • Data handling concerns: No new data handling concerns are introduced.
  • Input validation: Proper input validation is maintained.
  • Security best practices: The changes adhere to security best practices.

4.2 Vulnerability Analysis

  • Potential security risks: No potential security risks are identified.
  • Mitigation strategies: Continue adhering to security best practices.
  • Security testing requirements: Ensure comprehensive security testing is conducted.

5. Testing Strategy

5.1 Test Coverage

  • Unit test analysis: The PR adds unit tests for the user module, covering various scenarios.
  • Integration test requirements: No integration tests are added, but the unit tests cover interactions with the database.
  • Edge cases coverage: The tests cover various edge cases, including error handling and data integrity.

5.2 Test Recommendations

Suggested Test Cases

describe("insertUser", () => {
  it("should insert a regular user", async () => {
    userSaveStub.resolves(mockUser);
    userFindOneStub.returns({
      select: sinon.stub().returns({
        select: sinon.stub().resolves(mockUser),
      }),
    });
    const result = await insertUser(mockUser, imageFile, generateAvatarImageStub);
    expect(result).to.deep.equal(mockUser);
  });
  it("should insert a superadmin user", async () => {
    userSaveStub.resolves(mockSuperUser);
    userFindOneStub.returns({
      select: sinon.stub().returns({
        select: sinon.stub().resolves(mockSuperUser),
      }),
    });
    const result = await insertUser(mockSuperUser, imageFile, generateAvatarImageStub);
    expect(result).to.deep.equal(mockSuperUser);
  });
  it("should handle an error", async () => {
    const err = new Error("test error");
    userSaveStub.rejects(err);
    try {
      await insertUser(mockUser, imageFile, generateAvatarImageStub);
    } catch (error) {
      expect(error).to.exist;
      expect(error).to.deep.equal(err);
    }
  });
  it("should handle a duplicate key error", async () => {
    const err = new Error("test error");
    err.code = 11000;
    userSaveStub.rejects(err);
    try {
      await insertUser(mockUser, imageFile, generateAvatarImageStub);
    } catch (error) {
      expect(error).to.exist;
      expect(error).to.deep.equal(err);
    }
  });
});
  • Coverage improvements: Ensure all edge cases are covered, including partial updates or invalid input scenarios.
  • Performance testing needs: No performance tests are provided, but the changes do not impact performance.

6. Documentation & Maintenance

  • Documentation updates needed (API, architecture, configuration): Provide detailed documentation for each function, including parameters, return values, and error handling.
  • Long-term maintenance considerations: The code is more maintainable with improved testability.
  • Technical debt and monitoring requirements: Continue monitoring for technical debt and ensure comprehensive testing is conducted.

8. Summary & Recommendations

8.1 Key Action Items

  1. Critical changes required: None identified.
  2. Important improvements suggested: Ensure error handling consistency across all functions.
  3. Best practices to implement: Continue adhering to security best practices.
  4. Cross-cutting concerns to address: Standardize error handling across all functions.

8.2 Future Considerations

  • Technical evolution path: The current refactoring sets a good foundation for future extensibility.
  • Business capability evolution: Consider future requirements, such as adding new user roles or additional user attributes.
  • System integration impacts: No significant integration impacts are identified.

=== FINAL PR REVIEW COMMENT FORMAT ENDS ===

Copy link

coderabbitai bot commented Nov 12, 2024

Walkthrough

This pull request introduces modifications to the userModule.js file, enhancing the insertUser and updateUser functions to accept additional parameters for improved configurability. The insertUser function now allows for an injected avatar generation function, while updateUser accepts a boolean parsing function. Additionally, the deleteTeam and deleteAllOtherUsers functions have been updated to return a boolean value upon successful execution. A new test file, userModule.test.js, is also added to cover various user management operations, ensuring robust testing of the updated functionalities.

Changes

File Path Change Summary
Server/db/mongo/modules/userModule.js - Updated insertUser and updateUser to accept additional parameters for flexibility.
- Modified deleteTeam and deleteAllOtherUsers to return true on success.
Server/tests/db/userModule.test.js - Introduced a new test suite for user management functionalities, covering insert, update, delete, and error handling scenarios.

Possibly related PRs

Suggested reviewers

  • shyna92
  • jennifer-gan
  • marcelluscaio

Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

‼️ IMPORTANT
Auto-reply has been disabled for this repository in the CodeRabbit settings. The CodeRabbit bot will not respond to your replies unless it is explicitly tagged.

  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

🧹 Outside diff range and nitpick comments (6)
Server/db/mongo/modules/userModule.js (1)

97-102: Mom's spaghetti alert! This function's doing too much, fam!

The updateUser function is getting heavy with multiple responsibilities - it's handling boolean parsing, image processing, and user updates all in one place. Let's split this up to make it more maintainable.

Consider breaking this into smaller, focused functions:

+ const handleProfileImage = async (candidateUser, file, parseBoolean, generateAvatarImage) => {
+   if (parseBoolean(candidateUser.deleteProfileImage) === true) {
+     return { profileImage: null, avatarImage: null };
+   }
+   if (!file) return {};
+   
+   const avatar = await generateAvatarImage(file);
+   return {
+     profileImage: { data: file.buffer, contentType: file.mimetype },
+     avatarImage: avatar
+   };
+ };

 const updateUser = async (
   req,
   res,
   parseBoolean = ParseBoolean,
   generateAvatarImage = GenerateAvatarImage
 ) => {
   const candidateUserId = req.params.userId;
   try {
     const candidateUser = { ...req.body };
-    // Handle profile image...
+    const imageUpdates = await handleProfileImage(
+      candidateUser,
+      req.file,
+      parseBoolean,
+      generateAvatarImage
+    );
+    Object.assign(candidateUser, imageUpdates);

Also applies to: 110-110, 120-121

Server/tests/db/userModule.test.js (5)

16-28: Yo dawg, let's make these mocks more realistic!

The mock data could use some improvements to better reflect real-world scenarios:

  • Password should follow your password policy (e.g., minimum length, complexity)
  • imageFile mock is too basic and should include more realistic properties like filename, size, and proper MIME types
 const mockUser = {
   email: "[email protected]",
-  password: "password",
+  password: "P@ssw0rd123!",
   role: ["user"],
 };
 const mockSuperUser = {
   email: "[email protected]",
-  password: "password",
+  password: "P@ssw0rd123!",
   role: ["superadmin"],
 };
 const imageFile = {
-  image: 1,
+  fieldname: 'profileImage',
+  originalname: 'avatar.jpg',
+  encoding: '7bit',
+  mimetype: 'image/jpeg',
+  buffer: Buffer.from('mock-image-data'),
+  size: 1024
 };

143-143: Yo, this afterEach is emptier than my wallet after a Steam sale!

The empty afterEach block should be removed since we're already using sinon.restore() in the parent describe block.

-    afterEach(() => {});

185-185: Yo, that async keyword is looking kinda lost there!

Remove the unnecessary async keyword from the describe block. The describe function doesn't support async callbacks.

-  describe("deleteUser", async () => {
+  describe("deleteUser", () => {

211-245: These tests are fire, but let's make them straight fire! 🔥

Add edge cases to both deleteTeam and deleteAllOtherUsers test suites:

  • Test case where team has associated users
  • Test case where some users can't be deleted due to constraints
it("should handle team with associated users", async () => {
  const err = new Error("Cannot delete team with active users");
  err.code = 'TEAM_HAS_USERS';
  teamFindByIdAndDeleteStub.rejects(err);
  try {
    await deleteTeam("testId");
  } catch (error) {
    expect(error.code).to.equal('TEAM_HAS_USERS');
  }
});

it("should handle partial deletion of users", async () => {
  const err = new Error("Some users could not be deleted");
  err.code = 'PARTIAL_DELETE';
  userDeleteManyStub.rejects(err);
  try {
    await deleteAllOtherUsers();
  } catch (error) {
    expect(error.code).to.equal('PARTIAL_DELETE');
  }
});

269-269: Another async keyword trying to sneak into the party!

Remove the unnecessary async keyword from the describe block.

-  describe("logoutUser", async () => {
+  describe("logoutUser", () => {
📜 Review details

Configuration used: .coderabbit.yaml
Review profile: CHILL

📥 Commits

Reviewing files that changed from the base of the PR and between b554074 and 1733918.

📒 Files selected for processing (2)
  • Server/db/mongo/modules/userModule.js (6 hunks)
  • Server/tests/db/userModule.test.js (1 hunks)

Comment on lines +18 to +22
const insertUser = async (
userData,
imageFile,
generateAvatarImage = GenerateAvatarImage
) => {
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion

Yo dawg, we need to validate that generateAvatarImage function!

The dependency injection is dope, but we should add some validation to ensure the injected function is actually callable. A TypeError could make our palms sweaty if someone passes in something that ain't a function.

Here's a quick fix to make it more robust:

 const insertUser = async (
   userData,
   imageFile,
   generateAvatarImage = GenerateAvatarImage
 ) => {
+  if (typeof generateAvatarImage !== 'function') {
+    throw new Error('generateAvatarImage must be a function');
+  }
   try {

Also applies to: 32-32

@@ -164,6 +173,7 @@ const deleteUser = async (userId) => {
const deleteTeam = async (teamId) => {
try {
await TeamModel.findByIdAndDelete(teamId);
return true;
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Knees weak! These operations need some serious audit logging!

These are high-impact operations that could cause major disruption. The deleteAllOtherUsers function especially is like dropping mom's spaghetti all over the production environment - we need to track who's doing this and when.

Consider:

  1. Adding audit logging
  2. Requiring additional confirmation/verification
  3. Rate limiting these operations

Here's a suggested implementation:

 const deleteTeam = async (teamId) => {
   try {
+    await auditLog.create({
+      action: 'DELETE_TEAM',
+      targetId: teamId,
+      timestamp: new Date()
+    });
     await TeamModel.findByIdAndDelete(teamId);
     return true;
   } catch (error) {

Would you like me to create a GitHub issue to track the implementation of these security enhancements?

Also applies to: 187-187

Comment on lines +60 to +102
describe("insertUser", () => {
it("should insert a regular user", async () => {
userSaveStub.resolves(mockUser);
userFindOneStub.returns({
select: sinon.stub().returns({
select: sinon.stub().resolves(mockUser),
}),
});
const result = await insertUser(mockUser, imageFile, generateAvatarImageStub);
expect(result).to.deep.equal(mockUser);
});
it("should insert a superadmin user", async () => {
userSaveStub.resolves(mockSuperUser);
userFindOneStub.returns({
select: sinon.stub().returns({
select: sinon.stub().resolves(mockSuperUser),
}),
});
const result = await insertUser(mockSuperUser, imageFile, generateAvatarImageStub);
expect(result).to.deep.equal(mockSuperUser);
});
it("should handle an error", async () => {
const err = new Error("test error");
userSaveStub.rejects(err);
try {
await insertUser(mockUser, imageFile, generateAvatarImageStub);
} catch (error) {
expect(error).to.exist;
expect(error).to.deep.equal(err);
}
});
it("should handle a duplicate key error", async () => {
const err = new Error("test error");
err.code = 11000;
userSaveStub.rejects(err);
try {
await insertUser(mockUser, imageFile, generateAvatarImageStub);
} catch (error) {
expect(error).to.exist;
expect(error).to.deep.equal(err);
}
});
});
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion

Mom's spaghetti... I mean, we need more test coverage!

The insertUser test suite should include additional test cases:

  • Verify that generateAvatarImage is called with correct parameters
  • Test handling of invalid image files (wrong format, too large, etc.)
  • Test case where image generation fails

Add these test cases:

it("should call generateAvatarImage with correct parameters", async () => {
  userSaveStub.resolves(mockUser);
  userFindOneStub.returns({
    select: sinon.stub().returns({
      select: sinon.stub().resolves(mockUser),
    }),
  });
  await insertUser(mockUser, imageFile, generateAvatarImageStub);
  expect(generateAvatarImageStub.calledOnce).to.be.true;
  expect(generateAvatarImageStub.calledWith(imageFile)).to.be.true;
});

it("should handle invalid image file", async () => {
  const invalidImageFile = { ...imageFile, mimetype: 'application/pdf' };
  try {
    await insertUser(mockUser, invalidImageFile, generateAvatarImageStub);
  } catch (error) {
    expect(error.message).to.include('Invalid image format');
  }
});

Comment on lines +124 to +184
describe("updateUser", () => {
let req, res;
beforeEach(() => {
req = {
params: {
userId: "testId",
},
body: {
deleteProfileImage: "false",
email: "[email protected]",
},
file: {
buffer: "test",
mimetype: "test",
},
};
res = {};
});

afterEach(() => {});
it("should update a user", async () => {
parseBooleanStub.returns(false);
userFindByIdAndUpdateStub.returns({
select: sinon.stub().returns({
select: sinon.stub().resolves(mockUser),
}),
});
const result = await updateUser(
req,
res,
parseBooleanStub,
generateAvatarImageStub
);
expect(result).to.deep.equal(mockUser);
});
it("should delete a user profile image", async () => {
req.body.deleteProfileImage = "true";
userFindByIdAndUpdateStub.returns({
select: sinon.stub().returns({
select: sinon.stub().resolves(mockUser),
}),
});
const result = await updateUser(
req,
res,
parseBooleanStub,
generateAvatarImageStub
);
expect(result).to.deep.equal(mockUser);
});
it("should handle an error", async () => {
const err = new Error("test error");
userFindByIdAndUpdateStub.throws(err);
try {
await updateUser(req, res, parseBooleanStub, generateAvatarImageStub);
} catch (error) {
expect(error).to.exist;
expect(error).to.deep.equal(err);
}
});
});
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion

These tests are heavy, but we can make them stronger!

The updateUser test suite needs additional coverage:

  • Validate response object modifications
  • Test email format validation
  • Test case where avatar generation fails during update

Add these test cases:

it("should handle invalid email format", async () => {
  req.body.email = "invalid-email";
  try {
    await updateUser(req, res, parseBooleanStub, generateAvatarImageStub);
  } catch (error) {
    expect(error.message).to.include('Invalid email format');
  }
});

it("should handle avatar generation failure", async () => {
  generateAvatarImageStub.rejects(new Error('Avatar generation failed'));
  try {
    await updateUser(req, res, parseBooleanStub, generateAvatarImageStub);
  } catch (error) {
    expect(error.message).to.include('Avatar generation failed');
  }
});

Comment on lines +103 to +123
describe("getUserByEmail", () => {
it("should return a user", async () => {
userFindOneStub.returns({
select: sinon.stub().resolves(mockUser),
});
const result = await getUserByEmail(mockUser.email);
expect(result).to.deep.equal(mockUser);
});
});
describe("getUserByEmail", () => {
it("throw an error if a user is not found", async () => {
userFindOneStub.returns({
select: sinon.stub().resolves(null),
});
try {
await getUserByEmail(mockUser.email);
} catch (error) {
expect(error.message).to.equal(errorMessages.DB_USER_NOT_FOUND);
}
});
});
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Bruh, why we got duplicate describe blocks? That's sus!

Merge the two getUserByEmail describe blocks into one for better organization and readability.

 describe("getUserByEmail", () => {
   it("should return a user", async () => {
     userFindOneStub.returns({
       select: sinon.stub().resolves(mockUser),
     });
     const result = await getUserByEmail(mockUser.email);
     expect(result).to.deep.equal(mockUser);
   });
-});
-describe("getUserByEmail", () => {
   it("throw an error if a user is not found", async () => {
     userFindOneStub.returns({
       select: sinon.stub().resolves(null),
     });
     try {
       await getUserByEmail(mockUser.email);
     } catch (error) {
       expect(error.message).to.equal(errorMessages.DB_USER_NOT_FOUND);
     }
   });
 });
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
describe("getUserByEmail", () => {
it("should return a user", async () => {
userFindOneStub.returns({
select: sinon.stub().resolves(mockUser),
});
const result = await getUserByEmail(mockUser.email);
expect(result).to.deep.equal(mockUser);
});
});
describe("getUserByEmail", () => {
it("throw an error if a user is not found", async () => {
userFindOneStub.returns({
select: sinon.stub().resolves(null),
});
try {
await getUserByEmail(mockUser.email);
} catch (error) {
expect(error.message).to.equal(errorMessages.DB_USER_NOT_FOUND);
}
});
});
describe("getUserByEmail", () => {
it("should return a user", async () => {
userFindOneStub.returns({
select: sinon.stub().resolves(mockUser),
});
const result = await getUserByEmail(mockUser.email);
expect(result).to.deep.equal(mockUser);
});
it("throw an error if a user is not found", async () => {
userFindOneStub.returns({
select: sinon.stub().resolves(null),
});
try {
await getUserByEmail(mockUser.email);
} catch (error) {
expect(error.message).to.equal(errorMessages.DB_USER_NOT_FOUND);
}
});
});

@ajhollid ajhollid merged commit d34f45f into develop Nov 14, 2024
3 checks passed
@ajhollid ajhollid deleted the feat/be/tests-user-module branch November 14, 2024 07:05
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

1 participant