-
Notifications
You must be signed in to change notification settings - Fork 164
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
refactor: ♻️ Clean up code initializing
- Loading branch information
Showing
7 changed files
with
139 additions
and
113 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,28 +1,22 @@ | ||
import { OpenAPIRegistry } from "@asteasolutions/zod-to-openapi"; | ||
import express, { type Request, type Response, type Router } from "express"; | ||
import { StatusCodes } from "http-status-codes"; | ||
import { z } from "zod"; | ||
|
||
import { createApiResponse } from "@/api-docs/openAPIResponseBuilders"; | ||
import { ResponseStatus, ServiceResponse } from "@/common/models/serviceResponse"; | ||
import { ServiceResponse } from "@/common/models/serviceResponse"; | ||
import { handleServiceResponse } from "@/common/utils/httpHandlers"; | ||
|
||
export const healthCheckRegistry = new OpenAPIRegistry(); | ||
export const healthCheckRouter: Router = express.Router(); | ||
|
||
export const healthCheckRouter: Router = (() => { | ||
const router = express.Router(); | ||
healthCheckRegistry.registerPath({ | ||
method: "get", | ||
path: "/health-check", | ||
tags: ["Health Check"], | ||
responses: createApiResponse(z.null(), "Success"), | ||
}); | ||
|
||
healthCheckRegistry.registerPath({ | ||
method: "get", | ||
path: "/health-check", | ||
tags: ["Health Check"], | ||
responses: createApiResponse(z.null(), "Success"), | ||
}); | ||
|
||
router.get("/", (_req: Request, res: Response) => { | ||
const serviceResponse = new ServiceResponse(ResponseStatus.Success, "Service is healthy", null, StatusCodes.OK); | ||
handleServiceResponse(serviceResponse, res); | ||
}); | ||
|
||
return router; | ||
})(); | ||
healthCheckRouter.get("/", (_req: Request, res: Response) => { | ||
const serviceResponse = ServiceResponse.success("Service is healthy", null); | ||
return handleServiceResponse(serviceResponse, res); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -6,59 +6,61 @@ import { userRepository } from "@/api/user/userRepository"; | |
import { userService } from "@/api/user/userService"; | ||
|
||
vi.mock("@/api/user/userRepository"); | ||
vi.mock("@/server", () => ({ | ||
...vi.importActual("@/server"), | ||
logger: { | ||
error: vi.fn(), | ||
}, | ||
})); | ||
|
||
describe("userService", () => { | ||
let userServiceInstance: userService; | ||
let userRepositoryInstance: userRepository; | ||
|
||
const mockUsers: User[] = [ | ||
{ id: 1, name: "Alice", email: "[email protected]", age: 42, createdAt: new Date(), updatedAt: new Date() }, | ||
{ id: 2, name: "Bob", email: "[email protected]", age: 21, createdAt: new Date(), updatedAt: new Date() }, | ||
]; | ||
|
||
beforeEach(() => { | ||
userRepositoryInstance = new userRepository(); | ||
userServiceInstance = new userService(userRepositoryInstance); | ||
}); | ||
|
||
describe("findAll", () => { | ||
it("return all users", async () => { | ||
// Arrange | ||
(userRepository.findAllAsync as Mock).mockReturnValue(mockUsers); | ||
(userRepositoryInstance.findAllAsync as Mock).mockReturnValue(mockUsers); | ||
|
||
// Act | ||
const result = await userService.findAll(); | ||
const result = await userServiceInstance.findAll(); | ||
|
||
// Assert | ||
expect(result.statusCode).toEqual(StatusCodes.OK); | ||
expect(result.success).toBeTruthy(); | ||
expect(result.message).toContain("Users found"); | ||
expect(result.message).equals("Users found"); | ||
expect(result.responseObject).toEqual(mockUsers); | ||
}); | ||
|
||
it("returns a not found error for no users found", async () => { | ||
// Arrange | ||
(userRepository.findAllAsync as Mock).mockReturnValue(null); | ||
(userRepositoryInstance.findAllAsync as Mock).mockReturnValue(null); | ||
|
||
// Act | ||
const result = await userService.findAll(); | ||
const result = await userServiceInstance.findAll(); | ||
|
||
// Assert | ||
expect(result.statusCode).toEqual(StatusCodes.NOT_FOUND); | ||
expect(result.success).toBeFalsy(); | ||
expect(result.message).toContain("No Users found"); | ||
expect(result.message).equals("No Users found"); | ||
expect(result.responseObject).toBeNull(); | ||
}); | ||
|
||
it("handles errors for findAllAsync", async () => { | ||
// Arrange | ||
(userRepository.findAllAsync as Mock).mockRejectedValue(new Error("Database error")); | ||
(userRepositoryInstance.findAllAsync as Mock).mockRejectedValue(new Error("Database error")); | ||
|
||
// Act | ||
const result = await userService.findAll(); | ||
const result = await userServiceInstance.findAll(); | ||
|
||
// Assert | ||
expect(result.statusCode).toEqual(StatusCodes.INTERNAL_SERVER_ERROR); | ||
expect(result.success).toBeFalsy(); | ||
expect(result.message).toContain("Error finding all users"); | ||
expect(result.message).equals("An error occurred while retrieving users."); | ||
expect(result.responseObject).toBeNull(); | ||
}); | ||
}); | ||
|
@@ -68,45 +70,45 @@ describe("userService", () => { | |
// Arrange | ||
const testId = 1; | ||
const mockUser = mockUsers.find((user) => user.id === testId); | ||
(userRepository.findByIdAsync as Mock).mockReturnValue(mockUser); | ||
(userRepositoryInstance.findByIdAsync as Mock).mockReturnValue(mockUser); | ||
|
||
// Act | ||
const result = await userService.findById(testId); | ||
const result = await userServiceInstance.findById(testId); | ||
|
||
// Assert | ||
expect(result.statusCode).toEqual(StatusCodes.OK); | ||
expect(result.success).toBeTruthy(); | ||
expect(result.message).toContain("User found"); | ||
expect(result.message).equals("User found"); | ||
expect(result.responseObject).toEqual(mockUser); | ||
}); | ||
|
||
it("handles errors for findByIdAsync", async () => { | ||
// Arrange | ||
const testId = 1; | ||
(userRepository.findByIdAsync as Mock).mockRejectedValue(new Error("Database error")); | ||
(userRepositoryInstance.findByIdAsync as Mock).mockRejectedValue(new Error("Database error")); | ||
|
||
// Act | ||
const result = await userService.findById(testId); | ||
const result = await userServiceInstance.findById(testId); | ||
|
||
// Assert | ||
expect(result.statusCode).toEqual(StatusCodes.INTERNAL_SERVER_ERROR); | ||
expect(result.success).toBeFalsy(); | ||
expect(result.message).toContain(`Error finding user with id ${testId}`); | ||
expect(result.message).equals("An error occurred while finding user."); | ||
expect(result.responseObject).toBeNull(); | ||
}); | ||
|
||
it("returns a not found error for non-existent ID", async () => { | ||
// Arrange | ||
const testId = 1; | ||
(userRepository.findByIdAsync as Mock).mockReturnValue(null); | ||
(userRepositoryInstance.findByIdAsync as Mock).mockReturnValue(null); | ||
|
||
// Act | ||
const result = await userService.findById(testId); | ||
const result = await userServiceInstance.findById(testId); | ||
|
||
// Assert | ||
expect(result.statusCode).toEqual(StatusCodes.NOT_FOUND); | ||
expect(result.success).toBeFalsy(); | ||
expect(result.message).toContain("User not found"); | ||
expect(result.message).equals("User not found"); | ||
expect(result.responseObject).toBeNull(); | ||
}); | ||
}); | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,16 +1,30 @@ | ||
import type { User } from "@/api/user/userModel"; | ||
|
||
export const users: User[] = [ | ||
{ id: 1, name: "Alice", email: "[email protected]", age: 42, createdAt: new Date(), updatedAt: new Date() }, | ||
{ id: 2, name: "Bob", email: "[email protected]", age: 21, createdAt: new Date(), updatedAt: new Date() }, | ||
{ | ||
id: 1, | ||
name: "Alice", | ||
email: "[email protected]", | ||
age: 42, | ||
createdAt: new Date(), | ||
updatedAt: new Date(Date.now() + 5 * 24 * 60 * 60 * 1000), // 5 days later | ||
}, | ||
{ | ||
id: 2, | ||
name: "Robert", | ||
email: "[email protected]", | ||
age: 21, | ||
createdAt: new Date(), | ||
updatedAt: new Date(Date.now() + 5 * 24 * 60 * 60 * 1000), // 5 days later | ||
}, | ||
]; | ||
|
||
export const userRepository = { | ||
findAllAsync: async (): Promise<User[]> => { | ||
export class userRepository { | ||
async findAllAsync(): Promise<User[]> { | ||
return users; | ||
}, | ||
} | ||
|
||
findByIdAsync: async (id: number): Promise<User | null> => { | ||
async findByIdAsync(id: number): Promise<User | null> { | ||
return users.find((user) => user.id === id) || null; | ||
}, | ||
}; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.