Skip to content

Commit

Permalink
feat: fix bugs & update sort
Browse files Browse the repository at this point in the history
  • Loading branch information
conganhhcmus committed Mar 17, 2024
1 parent 9a64039 commit f7ecfb5
Show file tree
Hide file tree
Showing 10 changed files with 75 additions and 31 deletions.
1 change: 1 addition & 0 deletions src/constants/roles.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
export const enum Roles {
Normal = 0,
Admin = 1,
Collaborators = 2,
}
6 changes: 4 additions & 2 deletions src/controllers/payment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -55,19 +55,21 @@ export const getAllTransaction = async (req: Request, res: Response) => {
const page = parseInt(req.query.page as string, 10) || 1;
const option = parseInt(req.query.option as string, 10) || 0;
const status = (req.query.status as string[]).map((x) => parseInt(x, 10) || 0);
const q = (req.query.q as string) || '';

const result = await paymentService.getAllTransaction(option, status, page);
const result = await paymentService.getAllTransaction(option, status, page, q);

return res.status(200).json(result);
};

export const updateTransactionById = async (req: Request, res: Response) => {
const { id } = req.params;
const status = parseInt(req.body.status as string, 10) || 0;
const payload = req['identity'] as UserJwtPayload;

if (status == 0) throw new BadRequestError(INVALID_PARAMETERS);

const result = await paymentService.updateTransactionById(id, status);
const result = await paymentService.updateTransactionById(id, payload._id, status);

return res.status(200).json(result);
};
2 changes: 1 addition & 1 deletion src/helpers/auth.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ export const comparePassword = async (password: string, hashPassword: string) =>
};

export const createToken = (data: string | object) => {
return jwt.sign(data, TOKEN_SECRET_KEY, { expiresIn: '1h' });
return jwt.sign(data, TOKEN_SECRET_KEY, { expiresIn: '5m' });
};

export const createRefreshToken = (data: string | object) => {
Expand Down
9 changes: 9 additions & 0 deletions src/middlewares/usersValidation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,15 @@ export const isAdmin = (req: Request, res: Response, next: NextFunction) => {
next();
};

export const isAdminOrCollaborator = (req: Request, res: Response, next: NextFunction) => {
const payload = req['identity'] as UserJwtPayload;

if (payload.role !== Roles.Admin && payload.role !== Roles.Collaborators) {
throw new ForbiddenError(USER_HAVE_NOT_PERMISSION);
}
next();
};

export const isAdminOrOwner = (req: Request, res: Response, next: NextFunction) => {
const { id: userId } = req.params;
const payload = req['identity'] as UserJwtPayload;
Expand Down
1 change: 1 addition & 0 deletions src/models/transaction.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ const TransactionSchema = new mongoose.Schema({
status: { type: Number, required: true },
createTime: { type: Date, required: true },
updateTime: { type: Date, required: false, default: moment().utc().toDate() },
updateBy: { type: Types.ObjectId, required: false },
});

export default mongoose.model('Transaction', TransactionSchema);
21 changes: 15 additions & 6 deletions src/repositories/comics.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import ComicsModel from '@/models/comics';
import { Types } from 'mongoose';
import { Comic } from '@/types/comics';

const getComicByPageAndQuery = async (page: number, query: {}, pageSize: number = DEFAULT_COMIC_PAGE_SIZE) => {
const getComicByPageAndQuery = async (page: number, query: {}, sort: {}, pageSize: number = DEFAULT_COMIC_PAGE_SIZE) => {
const total = await ComicsModel.countDocuments().exec();
const comics = await ComicsModel.aggregate([
{
Expand All @@ -29,32 +29,41 @@ const getComicByPageAndQuery = async (page: number, query: {}, pageSize: number
as: 'genres',
},
},
{ $match: query },
{ $sort: sort },
{ $skip: pageSize * page - pageSize },
{ $limit: pageSize },
{ $match: query },
]);

return { data: comics, totalPage: Math.ceil(total / pageSize), currentPage: page };
};

export const getComics = async (page: number, q: string) => {
const query = !!q ? { name: { $regex: '.*' + q + '.*', $options: 'i' } } : {};
return getComicByPageAndQuery(page, query, DEFAULT_PAGE_SIZE);
const sort = { createTime: -1, updateTime: -1 };

return getComicByPageAndQuery(page, query, sort, DEFAULT_PAGE_SIZE);
};

export const getComicsByGenres = async (type: string, page: number) => {
const query = type == 'all' ? {} : { 'genres._id': new Types.ObjectId(type) };
return getComicByPageAndQuery(page, query);
const sort = { createTime: -1, updateTime: -1 };

return getComicByPageAndQuery(page, query, sort);
};

export const getRecommendComics = async (page: number) => {
const query = { recommend: true };
return getComicByPageAndQuery(page, query);
const sort = { createTime: -1, updateTime: -1 };

return getComicByPageAndQuery(page, query, sort);
};

export const getRecentUpdatedComics = async (page: number) => {
const query = {};
return getComicByPageAndQuery(page, query);
const sort = { createTime: -1, updateTime: -1 };

return getComicByPageAndQuery(page, query, sort);
};

export const getComicById = async (id: string) => {
Expand Down
45 changes: 31 additions & 14 deletions src/repositories/transaction.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,14 @@ import { Types } from 'mongoose';
export const createTransaction = (values: Record<string, any>): Promise<TransactionResponse> =>
new TransactionModel(values).save().then((trans) => trans.toObject());

export const getAllTransaction = async (option: number, status: number[], page: number) => {
const date = moment().utc().subtract(option, 'months').toDate();
const query = option !== 0 ? { status: { $in: status }, createTime: { $gt: date } } : { status: { $in: status } };
const total = await TransactionModel.countDocuments().exec();
const transaction = await TransactionModel.aggregate([
export const getAllTransaction = async (option: number, status: number[], page: number, q: string, sort: {}) => {
const date = moment().utc().subtract(option, 'days').toDate();
const query =
option !== 0
? { status: { $in: status }, updateTime: { $gt: date }, 'users.username': { $regex: '.*' + q + '.*', $options: 'i' } }
: { status: { $in: status }, 'users.username': { $regex: '.*' + q + '.*', $options: 'i' } };
const total = await TransactionModel.countDocuments(query).exec();
let transaction = await TransactionModel.aggregate([
{
$lookup: {
from: 'users',
Expand All @@ -21,22 +24,32 @@ export const getAllTransaction = async (option: number, status: number[], page:
as: 'users',
},
},
{ $skip: DEFAULT_PAGE_SIZE * page - DEFAULT_PAGE_SIZE },
{ $limit: DEFAULT_PAGE_SIZE },
{
$lookup: {
from: 'users',
localField: 'updateBy',
foreignField: '_id',
as: 'updateUsers',
},
},
{ $match: query },
{ $sort: sort },
{ $skip: DEFAULT_PAGE_SIZE * page - DEFAULT_PAGE_SIZE },
]);
const limit = Math.min(DEFAULT_PAGE_SIZE, transaction.length);

return { data: transaction, totalPage: Math.ceil(total / DEFAULT_PAGE_SIZE), currentPage: page };
return { data: transaction.slice(0, limit), totalPage: Math.ceil(total / DEFAULT_PAGE_SIZE), currentPage: page };
};

export const getAllTransactionByUserId = async (userId: string, option: number, status: number[], page: number) => {
const date = moment().utc().subtract(option, 'months').toDate();
export const getAllTransactionByUserId = async (userId: string, option: number, status: number[], page: number, sort: {}) => {
const date = moment().utc().subtract(option, 'days').toDate();
const query =
option !== 0
? { status: { $in: status }, targetId: new Types.ObjectId(userId), createTime: { $gt: date } }
? { status: { $in: status }, targetId: new Types.ObjectId(userId), updateTime: { $gt: date } }
: { status: { $in: status }, targetId: new Types.ObjectId(userId) };
const total = await TransactionModel.countDocuments().exec();
const total = await TransactionModel.countDocuments(query).exec();
const transaction = await TransactionModel.find(query)
.sort(sort)
.skip(DEFAULT_PAGE_SIZE * page - DEFAULT_PAGE_SIZE)
.limit(DEFAULT_PAGE_SIZE);

Expand All @@ -55,5 +68,9 @@ export const getAllBuyTransactionByUserId = async (userId: string) => {
return transaction;
};

export const updateTransactionById = (id: string, status: number) =>
TransactionModel.findOneAndUpdate({ _id: new Types.ObjectId(id) }, { $set: { status: status } }, { new: true });
export const updateTransactionById = (id: string, updateById: string, status: number) =>
TransactionModel.findOneAndUpdate(
{ _id: new Types.ObjectId(id) },
{ $set: { status: status, updateBy: new Types.ObjectId(updateById) } },
{ new: true },
);
6 changes: 3 additions & 3 deletions src/routers/payment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import {
updateTransactionById,
} from '@/controllers/payment';
import { verifyAccessToken } from '@/middlewares/authToken';
import { isAdmin } from '@/middlewares/usersValidation';
import { isAdminOrCollaborator } from '@/middlewares/usersValidation';
import { Router } from 'express';

export default (router: Router) => {
Expand All @@ -19,7 +19,7 @@ export default (router: Router) => {

router.get('/transaction/buy/:id', verifyAccessToken, getAllBuyTransactionByUserId);

router.get('/transaction', verifyAccessToken, isAdmin, getAllTransaction);
router.get('/transaction', verifyAccessToken, isAdminOrCollaborator, getAllTransaction);

router.post('/transaction/:id', verifyAccessToken, isAdmin, updateTransactionById);
router.post('/transaction/:id', verifyAccessToken, isAdminOrCollaborator, updateTransactionById);
};
13 changes: 8 additions & 5 deletions src/services/payment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,9 @@ export const buyChapter = async (amount: number, userId: string, chapterId: stri
};

export const getAllTransactionByUserId = async (userId: string, option: number, status: number[], page: number) => {
const result = await transactionRepository.getAllTransactionByUserId(userId, option, status, page);
const sort = { updateTime: -1, createTime: -1 };

const result = await transactionRepository.getAllTransactionByUserId(userId, option, status, page, sort);

return result;
};
Expand All @@ -47,14 +49,15 @@ export const getAllBuyTransactionByUserId = async (userId: string) => {
return result;
};

export const getAllTransaction = async (option: number, status: number[], page: number) => {
const result = await transactionRepository.getAllTransaction(option, status, page);
export const getAllTransaction = async (option: number, status: number[], page: number, q: string) => {
const sort = { updateTime: -1, createTime: -1 };
const result = await transactionRepository.getAllTransaction(option, status, page, q, sort);

return result;
};

export const updateTransactionById = async (id: string, status: number) => {
const result = await transactionRepository.updateTransactionById(id, status);
export const updateTransactionById = async (id: string, updateById: string, status: number) => {
const result = await transactionRepository.updateTransactionById(id, updateById, status);
if (result.status === TransactionStatus.success) {
await usersRepository.updateWalletById(result.targetId as string, result.amount);
}
Expand Down
2 changes: 2 additions & 0 deletions src/types/transaction.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ export interface Transaction {
status: number;
createTime: Date;
updateTime: Date;
updateBy: string;
}

export interface TransactionResponse {
Expand All @@ -18,6 +19,7 @@ export interface TransactionResponse {
status: number;
createTime: Date;
updateTime: Date;
updateBy: string;
}

export interface TransactionData {
Expand Down

0 comments on commit f7ecfb5

Please sign in to comment.