Skip to content

Commit

Permalink
product search feature
Browse files Browse the repository at this point in the history
  • Loading branch information
GSinseswa721 committed May 20, 2024
1 parent 3a38224 commit 780fb11
Show file tree
Hide file tree
Showing 7 changed files with 101 additions and 6 deletions.
21 changes: 21 additions & 0 deletions src/__test__/productStatus.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -229,3 +229,24 @@ describe('Vendor product availability status management tests', () => {
expect(response.body.message).toBe('Product not found in your stock');
});
});


describe('search product by name availability tests', () => {
it('Should search product by name', async () => {
const response = await request(app)
.get(`/product/search?name=testingmkknkkji product4`)
expect(response.statusCode).toBe(200);
expect(response.body.data).toBeDefined;
}, 10000);

it('should return empty array if there is product is not found in the database', async () => {
const response = await request(app)
.put(`/product/search?name=home`)


expect(response.statusCode).toBe(401);
expect(response.body.data).toBeUndefined;
});

});

28 changes: 24 additions & 4 deletions src/controllers/productController.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,9 @@ import {

getRecommendedProductsService,
productStatusServices,
viewSingleProduct
viewSingleProduct,
searchProductService

,
listAllProductsService}
from '../services';
Expand Down Expand Up @@ -54,6 +56,24 @@ export const listAllProducts = async (req: Request, res: Response) => {
};export const productStatus = async (req: Request, res: Response) => {
await productStatusServices(req, res);
};
export const singleProduct = async (req: Request, res: Response) => {
await viewSingleProduct(req, res);
};

export const searchProduct = async (req: Request, res: Response) => {
const { name, sortBy, sortOrder, page, limit } = req.query;

try {
const searchParams = {
name: name as string,
sortBy: sortBy as string,
sortOrder: sortOrder as 'ASC' | 'DESC',
page: parseInt(page as string, 10) || 1,
limit: parseInt(limit as string, 10) || 10,
};

const result = await searchProductService(searchParams);

res.json(result);
} catch (error) {
console.error('Error searching products:', error);
res.status(500).json({ error: 'Internal Server Error' });
}
};
3 changes: 3 additions & 0 deletions src/entities/Product.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,9 @@ import { Order } from './Order';
@Entity()
@Unique(['id'])
export class Product {
static query() {
throw new Error('Method not implemented.');
}
@PrimaryGeneratedColumn('uuid')
@IsNotEmpty()
id!: string;
Expand Down
3 changes: 1 addition & 2 deletions src/routes/ProductRoutes.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { RequestHandler, Router } from 'express';

import { productStatus } from '../controllers/index';
import { productStatus, searchProduct } from '../controllers/index';
import { hasRole } from '../middlewares/roleCheck';
import upload from '../middlewares/multer';
import { authMiddleware } from '../middlewares/verifyToken';
Expand All @@ -14,7 +14,6 @@ import {
deleteProduct,
getRecommendedProducts,
listAllProducts,
singleProduct,
} from '../controllers';
const router = Router();
router.get('/all', listAllProducts);
Expand Down
1 change: 1 addition & 0 deletions src/services/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ export * from './productServices/getRecommendedProductsService';
export * from './productServices/listAllProductsService';
export * from './productServices/productStatus';
export * from './productServices/viewSingleProduct';
export * from './productServices/searchProduct'

// Buyer wishlist services
export * from './wishListServices/addProduct';
Expand Down
6 changes: 6 additions & 0 deletions src/services/productServices/createProduct.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,9 @@ declare module 'express' {
}
}


export const createProductService = async (req: Request, res: Response) => {
try{
const { error } = validateProduct(req.body);
if (error !== undefined) {
return res.status(400).json({ status: 'error', error: error?.details[0].message });
Expand Down Expand Up @@ -98,4 +100,8 @@ export const createProductService = async (req: Request, res: Response) => {
product: { ...savedProduct }
},
});
}
catch(error){
res.status(400).json({'message':(error as Error).message})
}
};
45 changes: 45 additions & 0 deletions src/services/productServices/searchProduct.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
import { Request, Response } from "express";
import { getRepository, Like } from 'typeorm';
import { Product } from '../../entities/Product';

interface SearchProductParams {
name?: string;
sortBy?: string;
sortOrder?: 'ASC' | 'DESC';
page?: number;
limit?: number;
}

export const searchProductService = async (params: SearchProductParams) => {
const { name, sortBy, sortOrder, page = 1, limit = 10 } = params;

const productRepository = getRepository(Product);
let query = productRepository.createQueryBuilder('product');

if (name) {
query = query.where('product.name LIKE :name', { name: `%${name}%` });
}

if (sortBy && sortOrder) {
query = query.orderBy(`product.${sortBy}`, sortOrder as 'ASC' | 'DESC');
}

const skip = (page - 1) * limit;

const [products, total] = await query
.skip(skip)
.take(limit)
.getManyAndCount();

const totalPages = Math.ceil(total / limit);

return {
data: products,
pagination: {
totalItems: total,
currentPage: page,
totalPages,
itemsPerPage: limit,
},
};
};

0 comments on commit 780fb11

Please sign in to comment.