diff --git a/apps/web-client/src/app/layout.tsx b/apps/web-client/src/app/layout.tsx
index 1596f0e9..85d3590b 100644
--- a/apps/web-client/src/app/layout.tsx
+++ b/apps/web-client/src/app/layout.tsx
@@ -1,17 +1,29 @@
import type { Metadata } from 'next';
import './globals.css';
+/**
+ * EN: Metadata for the application
+ * VI: Metadata cho ứng dụng
+ */
export const metadata: Metadata = {
title: 'GoodGo Platform',
- description: 'Enterprise microservices platform',
+ description: 'Enterprise microservices platform / Nền tảng microservices doanh nghiệp',
};
+/**
+ * EN: Root layout component for the entire application
+ * VI: Component layout gốc cho toàn bộ ứng dụng
+ *
+ * @param children - Child components to render / Components con để render
+ */
export default function RootLayout({
children,
}: {
children: React.ReactNode;
}) {
return (
+ // EN: Root HTML structure with English language
+ // VI: Cấu trúc HTML gốc với ngôn ngữ tiếng Anh
{children}
diff --git a/apps/web-client/src/app/login/page.tsx b/apps/web-client/src/app/login/page.tsx
index 2759230c..4d4d8c68 100644
--- a/apps/web-client/src/app/login/page.tsx
+++ b/apps/web-client/src/app/login/page.tsx
@@ -4,31 +4,57 @@ import { useState } from 'react';
import { useRouter } from 'next/navigation';
import { useAuthStore } from '@/stores/auth.store';
+/**
+ * EN: Login page component for user authentication
+ * VI: Component trang đăng nhập để xác thực người dùng
+ */
export default function LoginPage() {
+ // EN: Next.js router for navigation
+ // VI: Next.js router để điều hướng
const router = useRouter();
+
+ // EN: Auth store hooks for login functionality
+ // VI: Auth store hooks cho chức năng đăng nhập
const { login, isLoading } = useAuthStore();
+
+ // EN: Form state management
+ // VI: Quản lý trạng thái form
const [email, setEmail] = useState('');
const [password, setPassword] = useState('');
const [error, setError] = useState('');
+ /**
+ * EN: Handle form submission for login
+ * VI: Xử lý submit form để đăng nhập
+ */
const handleSubmit = async (e: React.FormEvent) => {
e.preventDefault();
setError('');
try {
+ // EN: Attempt login through auth store
+ // VI: Thử đăng nhập thông qua auth store
await login(email, password);
+ // EN: Redirect to home page on successful login
+ // VI: Chuyển hướng về trang chủ khi đăng nhập thành công
router.push('/');
} catch (err: any) {
- setError(err.message || 'Login failed');
+ setError(err.message || 'Login failed / Đăng nhập thất bại');
}
};
return (
+ // EN: Centered login form layout
+ // VI: Layout form đăng nhập được căn giữa
diff --git a/apps/web-client/src/app/page.tsx b/apps/web-client/src/app/page.tsx
index d935839e..0a00b41c 100644
--- a/apps/web-client/src/app/page.tsx
+++ b/apps/web-client/src/app/page.tsx
@@ -3,30 +3,46 @@
import { useAuthStore } from '@/stores/auth.store';
import { useEffect } from 'react';
+/**
+ * EN: Home page component - main application entry point
+ * VI: Component trang chủ - điểm vào chính của ứng dụng
+ */
export default function Home() {
+ // EN: Get authentication state from store
+ // VI: Lấy trạng thái xác thực từ store
const { user, isAuthenticated, isLoading, fetchUser } = useAuthStore();
+ // EN: Fetch user data on component mount if not authenticated
+ // VI: Fetch dữ liệu user khi component mount nếu chưa xác thực
useEffect(() => {
if (!isAuthenticated && !isLoading) {
fetchUser();
}
}, [isAuthenticated, isLoading, fetchUser]);
+ // EN: Show loading state while checking authentication
+ // VI: Hiển thị trạng thái loading trong khi kiểm tra xác thực
if (isLoading) {
- return Loading...
;
+ return Loading... / Đang tải...
;
}
return (
+ // EN: Main content area with responsive padding
+ // VI: Khu vực nội dung chính với padding responsive
- GoodGo Platform
+ GoodGo Platform / Nền tảng GoodGo
+
+ {/* EN: Conditional rendering based on authentication status / VI: Render có điều kiện dựa trên trạng thái xác thực */}
{isAuthenticated && user ? (
+ // EN: Authenticated user welcome message / VI: Thông báo chào mừng người dùng đã xác thực
-
Welcome, {user.email}!
-
Role: {user.role}
+
Welcome, {user.email}! / Chào mừng, {user.email}!
+
Role: {user.role} / Vai trò: {user.role}
) : (
+ // EN: Login prompt for unauthenticated users / VI: Nhắc đăng nhập cho người dùng chưa xác thực
-
Please log in to continue.
+
Please log in to continue. / Vui lòng đăng nhập để tiếp tục.
)}
diff --git a/apps/web-client/src/services/api/auth.api.ts b/apps/web-client/src/services/api/auth.api.ts
index bdfc446c..c15e2046 100644
--- a/apps/web-client/src/services/api/auth.api.ts
+++ b/apps/web-client/src/services/api/auth.api.ts
@@ -1,13 +1,27 @@
import { apiClient } from './client';
import { LoginDto, RegisterDto, AuthResponse, ApiResponse, UserResponse } from '@goodgo/types';
+/**
+ * EN: Authentication API service for frontend
+ * VI: Service API xác thực cho frontend
+ */
export const authApi = {
+ /**
+ * EN: Register new user account
+ * VI: Đăng ký tài khoản người dùng mới
+ */
register: async (data: RegisterDto): Promise> => {
return apiClient.post('/auth/register', data);
},
+ /**
+ * EN: Login user and store tokens
+ * VI: Đăng nhập người dùng và lưu tokens
+ */
login: async (data: LoginDto): Promise> => {
const response = await apiClient.post('/auth/login', data);
+ // EN: Store tokens in client and localStorage on successful login
+ // VI: Lưu tokens trong client và localStorage khi đăng nhập thành công
if (response.success && response.data) {
apiClient.setAuthToken(response.data.accessToken);
if (typeof window !== 'undefined') {
@@ -17,9 +31,17 @@ export const authApi = {
return response;
},
+ /**
+ * EN: Logout user and clear tokens
+ * VI: Đăng xuất người dùng và xóa tokens
+ */
logout: async (): Promise => {
+ // EN: Get refresh token from localStorage for logout request
+ // VI: Lấy refresh token từ localStorage cho request logout
const refreshToken = typeof window !== 'undefined' ? localStorage.getItem('refreshToken') : null;
const response = await apiClient.post('/auth/logout', { refreshToken });
+ // EN: Clear tokens from client and localStorage
+ // VI: Xóa tokens khỏi client và localStorage
apiClient.removeAuthToken();
if (typeof window !== 'undefined') {
localStorage.removeItem('refreshToken');
@@ -27,18 +49,32 @@ export const authApi = {
return response;
},
+ /**
+ * EN: Refresh access token using refresh token
+ * VI: Làm mới access token sử dụng refresh token
+ */
refreshToken: async (refreshToken: string): Promise> => {
const response = await apiClient.post('/auth/refresh', { refreshToken });
+ // EN: Update access token in client on successful refresh
+ // VI: Cập nhật access token trong client khi refresh thành công
if (response.success && response.data) {
apiClient.setAuthToken(response.data.accessToken);
}
return response;
},
+ /**
+ * EN: Get current authenticated user profile
+ * VI: Lấy hồ sơ người dùng đã xác thực hiện tại
+ */
getMe: async (): Promise> => {
return apiClient.get('/users/me');
},
+ /**
+ * EN: Change user password
+ * VI: Thay đổi mật khẩu người dùng
+ */
changePassword: async (currentPassword: string, newPassword: string): Promise => {
return apiClient.put('/auth/password', { currentPassword, newPassword });
},
diff --git a/apps/web-client/src/services/api/client.ts b/apps/web-client/src/services/api/client.ts
index 79caf82e..479d55d9 100644
--- a/apps/web-client/src/services/api/client.ts
+++ b/apps/web-client/src/services/api/client.ts
@@ -1,8 +1,14 @@
import { createHttpClient } from '@goodgo/http-client';
+// EN: Get API base URL from environment or use default
+// VI: Lấy API base URL từ environment hoặc sử dụng mặc định
const API_URL = process.env.NEXT_PUBLIC_API_URL || 'http://localhost/api/v1';
+/**
+ * EN: HTTP client instance configured for API calls
+ * VI: Instance HTTP client đã cấu hình cho API calls
+ */
export const apiClient = createHttpClient({
baseURL: API_URL,
- timeout: 30000,
+ timeout: 30000, // EN: 30 second timeout / VI: Timeout 30 giây
});
diff --git a/apps/web-client/src/stores/auth.store.ts b/apps/web-client/src/stores/auth.store.ts
index c4b6c931..1fc88ed2 100644
--- a/apps/web-client/src/stores/auth.store.ts
+++ b/apps/web-client/src/stores/auth.store.ts
@@ -3,16 +3,31 @@ import { persist } from 'zustand/middleware';
import { UserResponse } from '@goodgo/types';
import { authApi } from '../services/api/auth.api';
+/**
+ * EN: Authentication state interface for Zustand store
+ * VI: Interface trạng thái xác thực cho Zustand store
+ */
interface AuthState {
+ /** EN: Current authenticated user / VI: Người dùng đã xác thực hiện tại */
user: UserResponse | null;
+ /** EN: Authentication status / VI: Trạng thái xác thực */
isAuthenticated: boolean;
+ /** EN: Loading state for async operations / VI: Trạng thái loading cho async operations */
isLoading: boolean;
+ /** EN: Login method / VI: Method đăng nhập */
login: (email: string, password: string) => Promise;
+ /** EN: Register method / VI: Method đăng ký */
register: (email: string, password: string, confirmPassword: string) => Promise;
+ /** EN: Logout method / VI: Method đăng xuất */
logout: () => Promise;
+ /** EN: Fetch current user method / VI: Method lấy thông tin user hiện tại */
fetchUser: () => Promise;
}
+/**
+ * EN: Zustand store for authentication state management with persistence
+ * VI: Zustand store để quản lý trạng thái xác thực với persistence
+ */
export const useAuthStore = create()(
persist(
(set) => ({
@@ -20,6 +35,10 @@ export const useAuthStore = create()(
isAuthenticated: false,
isLoading: false,
+ /**
+ * EN: Login user and update store state
+ * VI: Đăng nhập người dùng và cập nhật trạng thái store
+ */
login: async (email: string, password: string) => {
set({ isLoading: true });
try {
@@ -31,7 +50,7 @@ export const useAuthStore = create()(
isLoading: false,
});
} else {
- throw new Error(response.error?.message || 'Login failed');
+ throw new Error(response.error?.message || 'Login failed / Đăng nhập thất bại');
}
} catch (error) {
set({ isLoading: false });
@@ -39,6 +58,10 @@ export const useAuthStore = create()(
}
},
+ /**
+ * EN: Register new user and update store state
+ * VI: Đăng ký người dùng mới và cập nhật trạng thái store
+ */
register: async (email: string, password: string, confirmPassword: string) => {
set({ isLoading: true });
try {
@@ -50,7 +73,7 @@ export const useAuthStore = create()(
isLoading: false,
});
} else {
- throw new Error(response.error?.message || 'Registration failed');
+ throw new Error(response.error?.message || 'Registration failed / Đăng ký thất bại');
}
} catch (error) {
set({ isLoading: false });
@@ -58,6 +81,10 @@ export const useAuthStore = create()(
}
},
+ /**
+ * EN: Logout user and clear store state
+ * VI: Đăng xuất người dùng và xóa trạng thái store
+ */
logout: async () => {
try {
await authApi.logout();
@@ -69,6 +96,10 @@ export const useAuthStore = create()(
}
},
+ /**
+ * EN: Fetch current user profile from API
+ * VI: Lấy hồ sơ người dùng hiện tại từ API
+ */
fetchUser: async () => {
set({ isLoading: true });
try {
@@ -87,6 +118,8 @@ export const useAuthStore = create()(
});
}
} catch (error) {
+ // EN: Clear user state on fetch failure
+ // VI: Xóa trạng thái user khi fetch thất bại
set({
user: null,
isAuthenticated: false,
@@ -96,7 +129,11 @@ export const useAuthStore = create()(
},
}),
{
+ // EN: Persist auth state to localStorage
+ // VI: Persist trạng thái auth vào localStorage
name: 'auth-storage',
+ // EN: Only persist user and isAuthenticated, exclude isLoading
+ // VI: Chỉ persist user và isAuthenticated, loại trừ isLoading
partialize: (state) => ({ user: state.user, isAuthenticated: state.isAuthenticated }),
}
)
diff --git a/packages/types/src/api.types.ts b/packages/types/src/api.types.ts
index f21ca0f9..62397fe2 100644
--- a/packages/types/src/api.types.ts
+++ b/packages/types/src/api.types.ts
@@ -1,29 +1,62 @@
+/**
+ * EN: Standardized API response interface
+ * VI: Interface phản hồi API chuẩn hóa
+ */
export interface ApiResponse {
+ /** EN: Operation success status / VI: Trạng thái thành công của thao tác */
success: boolean;
+ /** EN: Response data payload / VI: Payload dữ liệu phản hồi */
data?: T;
+ /** EN: Success message / VI: Thông báo thành công */
message?: string;
+ /** EN: Error details (if failed) / VI: Chi tiết lỗi (nếu thất bại) */
error?: ApiError;
+ /** EN: Response timestamp / VI: Timestamp phản hồi */
timestamp: string;
}
+/**
+ * EN: API error structure
+ * VI: Cấu trúc lỗi API
+ */
export interface ApiError {
+ /** EN: Error code identifier / VI: Mã định danh lỗi */
code: string;
+ /** EN: Human-readable error message / VI: Thông báo lỗi dễ đọc */
message: string;
+ /** EN: Additional error details / VI: Chi tiết lỗi bổ sung */
details?: Record;
}
+/**
+ * EN: Paginated API response interface
+ * VI: Interface phản hồi API có phân trang
+ */
export interface PaginatedResponse extends ApiResponse {
+ /** EN: Pagination metadata / VI: Metadata phân trang */
pagination: {
+ /** EN: Current page number / VI: Số trang hiện tại */
page: number;
+ /** EN: Items per page / VI: Số items mỗi trang */
limit: number;
+ /** EN: Total number of items / VI: Tổng số items */
total: number;
+ /** EN: Total number of pages / VI: Tổng số trang */
totalPages: number;
};
}
+/**
+ * EN: Query parameters for pagination and sorting
+ * VI: Tham số query cho phân trang và sắp xếp
+ */
export interface PaginationQuery {
+ /** EN: Page number (1-based) / VI: Số trang (bắt đầu từ 1) */
page?: number;
+ /** EN: Items per page / VI: Số items mỗi trang */
limit?: number;
+ /** EN: Field to sort by / VI: Trường để sắp xếp */
sortBy?: string;
+ /** EN: Sort order / VI: Thứ tự sắp xếp */
sortOrder?: 'asc' | 'desc';
}
diff --git a/packages/types/src/index.ts b/packages/types/src/index.ts
index 0fe2e7bc..3592a69a 100644
--- a/packages/types/src/index.ts
+++ b/packages/types/src/index.ts
@@ -1,3 +1,9 @@
+// EN: Re-export all user-related types
+// VI: Re-export tất cả types liên quan đến user
export * from './user.types';
+// EN: Re-export all authentication-related types
+// VI: Re-export tất cả types liên quan đến authentication
export * from './auth.types';
+// EN: Re-export all API-related types
+// VI: Re-export tất cả types liên quan đến API
export * from './api.types';
diff --git a/services/auth-service/src/modules/auth/auth.module.ts b/services/auth-service/src/modules/auth/auth.module.ts
index ec0038b4..88235317 100644
--- a/services/auth-service/src/modules/auth/auth.module.ts
+++ b/services/auth-service/src/modules/auth/auth.module.ts
@@ -2,13 +2,26 @@ import { Router } from 'express';
import { AuthController } from './auth.controller';
import { authenticate } from '../../middlewares/auth.middleware';
+/**
+ * EN: Create and configure authentication routes
+ * VI: Tạo và cấu hình routes xác thực
+ *
+ * @returns Configured Express router for auth endpoints / Router Express đã cấu hình cho auth endpoints
+ */
export const createAuthRouter = (): Router => {
+ // EN: Create router instance
+ // VI: Tạo instance router
const router = Router();
const authController = new AuthController();
+ // EN: Public authentication routes (no auth required)
+ // VI: Routes xác thực công khai (không yêu cầu auth)
router.post('/register', authController.register);
router.post('/login', authController.login);
router.post('/refresh', authController.refresh);
+
+ // EN: Protected routes (authentication required)
+ // VI: Routes được bảo vệ (yêu cầu authentication)
router.post('/logout', authenticate, authController.logout);
router.put('/password', authenticate, authController.changePassword);
diff --git a/services/auth-service/src/modules/user/user.controller.ts b/services/auth-service/src/modules/user/user.controller.ts
index db10fca6..50d4b686 100644
--- a/services/auth-service/src/modules/user/user.controller.ts
+++ b/services/auth-service/src/modules/user/user.controller.ts
@@ -4,13 +4,29 @@ import { updateUserDtoSchema } from './user.dto';
import { AuthRequest } from '../../middlewares/auth.middleware';
import { ApiResponse, PaginatedResponse, UserResponse } from '@goodgo/types';
+/**
+ * EN: User management controller handling user-related HTTP requests
+ * VI: Controller quản lý người dùng xử lý các yêu cầu HTTP liên quan đến người dùng
+ */
export class UserController {
+ /** EN: User service instance / VI: Instance user service */
private userService: UserService;
+ /**
+ * EN: Initialize user controller with service dependency
+ * VI: Khởi tạo user controller với dependency service
+ */
constructor() {
this.userService = new UserService();
}
+ /**
+ * EN: Get current authenticated user profile
+ * VI: Lấy hồ sơ người dùng đã xác thực hiện tại
+ *
+ * @param req - Authenticated request with user info / Request đã xác thực với thông tin người dùng
+ * @param res - Express response object / Đối tượng response của Express
+ */
getMe = async (req: AuthRequest, res: Response): Promise => {
try {
const user = await this.userService.getCurrentUser(req.user!.userId);
@@ -34,8 +50,17 @@ export class UserController {
}
};
+ /**
+ * EN: Get paginated list of users (admin endpoint)
+ * VI: Lấy danh sách người dùng có phân trang (endpoint admin)
+ *
+ * @param req - Express request with query parameters / Request Express với query parameters
+ * @param res - Express response object / Đối tượng response của Express
+ */
getUsers = async (req: Request, res: Response): Promise => {
try {
+ // EN: Parse pagination parameters from query
+ // VI: Parse tham số phân trang từ query
const page = parseInt(req.query.page as string) || 1;
const limit = parseInt(req.query.limit as string) || 20;
@@ -54,13 +79,20 @@ export class UserController {
success: false,
error: {
code: 'USER_002',
- message: error.message || 'Failed to fetch users',
+ message: error.message || 'Failed to fetch users / Lấy danh sách người dùng thất bại',
},
timestamp: new Date().toISOString(),
});
}
};
+ /**
+ * EN: Get user by ID (admin endpoint)
+ * VI: Lấy người dùng theo ID (endpoint admin)
+ *
+ * @param req - Express request with user ID in params / Request Express với user ID trong params
+ * @param res - Express response object / Đối tượng response của Express
+ */
getUserById = async (req: Request, res: Response): Promise => {
try {
const user = await this.userService.getUserById(req.params.id);
@@ -84,15 +116,24 @@ export class UserController {
}
};
+ /**
+ * EN: Update user information (admin endpoint)
+ * VI: Cập nhật thông tin người dùng (endpoint admin)
+ *
+ * @param req - Express request with user ID in params and update data in body / Request Express với user ID trong params và dữ liệu cập nhật trong body
+ * @param res - Express response object / Đối tượng response của Express
+ */
updateUser = async (req: Request, res: Response): Promise => {
try {
+ // EN: Validate update data using Zod schema
+ // VI: Xác thực dữ liệu cập nhật sử dụng Zod schema
const data = updateUserDtoSchema.parse(req.body);
const user = await this.userService.updateUser(req.params.id, data);
const response: ApiResponse = {
success: true,
data: user,
- message: 'User updated successfully',
+ message: 'User updated successfully / Người dùng đã cập nhật thành công',
timestamp: new Date().toISOString(),
};
@@ -102,20 +143,29 @@ export class UserController {
success: false,
error: {
code: 'USER_004',
- message: error.message || 'Failed to update user',
+ message: error.message || 'Failed to update user / Cập nhật người dùng thất bại',
},
timestamp: new Date().toISOString(),
});
}
};
+ /**
+ * EN: Delete user (admin endpoint)
+ * VI: Xóa người dùng (endpoint admin)
+ *
+ * @param req - Express request with user ID in params / Request Express với user ID trong params
+ * @param res - Express response object / Đối tượng response của Express
+ */
deleteUser = async (req: Request, res: Response): Promise => {
try {
+ // EN: Delete user through service
+ // VI: Xóa người dùng thông qua service
await this.userService.deleteUser(req.params.id);
const response: ApiResponse = {
success: true,
- message: 'User deleted successfully',
+ message: 'User deleted successfully / Người dùng đã xóa thành công',
timestamp: new Date().toISOString(),
};
@@ -125,7 +175,7 @@ export class UserController {
success: false,
error: {
code: 'USER_005',
- message: error.message || 'Failed to delete user',
+ message: error.message || 'Failed to delete user / Xóa người dùng thất bại',
},
timestamp: new Date().toISOString(),
});
diff --git a/services/auth-service/src/modules/user/user.dto.ts b/services/auth-service/src/modules/user/user.dto.ts
index 689f82a5..d21fbd56 100644
--- a/services/auth-service/src/modules/user/user.dto.ts
+++ b/services/auth-service/src/modules/user/user.dto.ts
@@ -1,9 +1,17 @@
import { z } from 'zod';
+/**
+ * EN: Zod schema for user update validation
+ * VI: Schema Zod để xác thực cập nhật người dùng
+ */
export const updateUserDtoSchema = z.object({
+ /** EN: Optional email update / VI: Cập nhật email tùy chọn */
email: z.string().email().optional(),
+ /** EN: Optional role update / VI: Cập nhật vai trò tùy chọn */
role: z.enum(['USER', 'ADMIN', 'SUPER_ADMIN']).optional(),
+ /** EN: Optional active status update / VI: Cập nhật trạng thái hoạt động tùy chọn */
isActive: z.boolean().optional(),
});
+/** EN: TypeScript type inferred from update user schema / VI: Type TypeScript suy ra từ schema cập nhật người dùng */
export type UpdateUserDto = z.infer;
diff --git a/services/auth-service/src/modules/user/user.module.ts b/services/auth-service/src/modules/user/user.module.ts
index d57bc0fa..5ae0c3dc 100644
--- a/services/auth-service/src/modules/user/user.module.ts
+++ b/services/auth-service/src/modules/user/user.module.ts
@@ -2,11 +2,24 @@ import { Router } from 'express';
import { UserController } from './user.controller';
import { authenticate, authorize } from '../../middlewares/auth.middleware';
+/**
+ * EN: Create and configure user management routes
+ * VI: Tạo và cấu hình routes quản lý người dùng
+ *
+ * @returns Configured Express router for user endpoints / Router Express đã cấu hình cho user endpoints
+ */
export const createUserRouter = (): Router => {
+ // EN: Create router instance
+ // VI: Tạo instance router
const router = Router();
const userController = new UserController();
+ // EN: Public route for authenticated user profile
+ // VI: Route công khai cho hồ sơ người dùng đã xác thực
router.get('/me', authenticate, userController.getMe);
+
+ // EN: Admin-only routes for user management
+ // VI: Routes chỉ dành cho admin để quản lý người dùng
router.get('/', authenticate, authorize('ADMIN', 'SUPER_ADMIN'), userController.getUsers);
router.get('/:id', authenticate, authorize('ADMIN', 'SUPER_ADMIN'), userController.getUserById);
router.put('/:id', authenticate, authorize('ADMIN', 'SUPER_ADMIN'), userController.updateUser);
diff --git a/services/auth-service/src/modules/user/user.service.ts b/services/auth-service/src/modules/user/user.service.ts
index 7a0d91a4..1ab86d2d 100644
--- a/services/auth-service/src/modules/user/user.service.ts
+++ b/services/auth-service/src/modules/user/user.service.ts
@@ -3,7 +3,19 @@ import { logger } from '@goodgo/logger';
import { UpdateUserDto } from './user.dto';
import { UserResponse, Role as TypeRole } from '@goodgo/types';
+/**
+ * EN: User management service handling CRUD operations
+ * VI: Service quản lý người dùng xử lý các thao tác CRUD
+ */
export class UserService {
+ /**
+ * EN: Get current authenticated user information
+ * VI: Lấy thông tin người dùng đã xác thực hiện tại
+ *
+ * @param userId - Unique user identifier / Mã định danh duy nhất người dùng
+ * @returns User response data / Dữ liệu phản hồi người dùng
+ * @throws Error if user not found / Lỗi nếu không tìm thấy người dùng
+ */
async getCurrentUser(userId: string): Promise {
const user = await prisma.user.findUnique({
where: { id: userId },
@@ -23,13 +35,23 @@ export class UserService {
};
}
+ /**
+ * EN: Get user by ID (admin function)
+ * VI: Lấy người dùng theo ID (hàm admin)
+ *
+ * @param id - User identifier / Mã định danh người dùng
+ * @returns User response data / Dữ liệu phản hồi người dùng
+ * @throws Error if user not found / Lỗi nếu không tìm thấy người dùng
+ */
async getUserById(id: string): Promise {
+ // EN: Find user in database
+ // VI: Tìm người dùng trong database
const user = await prisma.user.findUnique({
where: { id },
});
if (!user) {
- throw new Error('User not found');
+ throw new Error('User not found / Không tìm thấy người dùng');
}
return {
@@ -42,6 +64,14 @@ export class UserService {
};
}
+ /**
+ * EN: Get paginated list of users (admin function)
+ * VI: Lấy danh sách người dùng có phân trang (hàm admin)
+ *
+ * @param page - Page number (default: 1) / Số trang (mặc định: 1)
+ * @param limit - Items per page (default: 20) / Số items mỗi trang (mặc định: 20)
+ * @returns Paginated user list / Danh sách người dùng có phân trang
+ */
async getUsers(page: number = 1, limit: number = 20) {
const skip = (page - 1) * limit;
@@ -72,7 +102,17 @@ export class UserService {
};
}
+ /**
+ * EN: Update user information (admin function)
+ * VI: Cập nhật thông tin người dùng (hàm admin)
+ *
+ * @param id - User identifier / Mã định danh người dùng
+ * @param data - Update data / Dữ liệu cập nhật
+ * @returns Updated user response / Phản hồi người dùng đã cập nhật
+ */
async updateUser(id: string, data: UpdateUserDto): Promise {
+ // EN: Update user in database
+ // VI: Cập nhật người dùng trong database
const user = await prisma.user.update({
where: { id },
data: {
@@ -82,7 +122,7 @@ export class UserService {
},
});
- logger.info('User updated', { userId: id });
+ logger.info('User updated / Người dùng đã cập nhật', { userId: id });
return {
id: user.id,
@@ -94,11 +134,19 @@ export class UserService {
};
}
+ /**
+ * EN: Delete user (admin function)
+ * VI: Xóa người dùng (hàm admin)
+ *
+ * @param id - User identifier to delete / Mã định danh người dùng cần xóa
+ */
async deleteUser(id: string): Promise {
+ // EN: Delete user from database
+ // VI: Xóa người dùng khỏi database
await prisma.user.delete({
where: { id },
});
- logger.info('User deleted', { userId: id });
+ logger.info('User deleted / Người dùng đã xóa', { userId: id });
}
}