import Menu from '@/lib/auth/components/Menu';
import { useEffect, useState } from 'react';
import * as XLSX from 'xlsx';
import GenerateRecomendations from '../api/recomendation';
import axios from 'axios';
import { Button, Link } from '@chakra-ui/react';
import Image from 'next/image';
import BottomPopup from '@/core/components/elements/Popup/BottomPopup';
import formatCurrency from '~/libs/formatCurrency';
const exportToExcel = (data) => {
const worksheet = XLSX.utils.json_to_sheet(data);
const workbook = XLSX.utils.book_new();
XLSX.utils.book_append_sheet(workbook, worksheet, 'Results');
// Generate Excel file and trigger download in the browser
XLSX.writeFile(workbook, 'ProductRecommendations.xlsx');
};
const ProductsRecomendation = ({ id }) => {
const [excelData, setExcelData] = useState(null);
const [products, setProducts] = useState([]);
const [isLoading, setIsLoading] = useState(false);
const [isOpen, setIsOpen] = useState(false);
const [variantsOpen, setVariantsOpen] = useState([]);
const [otherRec, setOtherRec] = useState(false);
const mappingProducts = async ({ index, product, result, variants }) => {
const resultMapping = {
index: index,
product: product,
result: {
id: result?.id || '-',
name: result?.nameS || '-',
code: result?.defaultCodeS || '-',
},
};
return resultMapping;
};
const searchRecomendation = async ({ product, index, operator = 'AND' }) => {
let variants = [];
let resultMapping = {};
const searchProduct = await axios.post(
`${process.env.NEXT_PUBLIC_SELF_HOST}/api/shop/generate-recomendation?q=${product}&op=${operator}`
);
if (operator === 'AND') {
const result =
searchProduct.data.response.numFound > 0
? searchProduct.data.response.products[0]
: null;
if (result?.variantTotal > 1) {
const searchVariants = await axios.post(
`${process.env.NEXT_PUBLIC_SELF_HOST}/api/shop/product-detail?id=${result.id}`
);
variants = searchVariants.data[0].variants;
}
resultMapping = await mappingProducts({
index,
product,
result,
variants,
});
} else {
const result =
searchProduct.data.response.numFound > 0
? searchProduct.data.response.products
: null;
result.map((item) => {
if (item.variantTotal > 1) {
const searchVariants = axios.post(
`${process.env.NEXT_PUBLIC_SELF_HOST}/api/shop/product-detail?id=${item.id}`
);
variants = searchVariants.data[0].variants;
}
});
// console.log('ini result', searchProduct.data.response);
}
return resultMapping;
};
const handleSubmit = async (e) => {
setIsLoading(true);
e.preventDefault();
if (excelData) {
const results = await Promise.all(
excelData.map(async (row, i) => {
const index = i + 1;
const product = row['product'];
return await generateProductRecomendation({ product, index });
})
);
const formattedResults = results.map((result) => {
const formattedResult = { product: result.product };
for (let i = 0; i <= 5; i++) {
formattedResult[`recomendation product ${i + 1} - code`] = result.result[i] == null ? '-' : result.result[i]?.code;
formattedResult[`recomendation product ${i + 1} - name`] = result.result[i] == null ? '-' : result.result[i]?.name ;
}
return formattedResult;
});
exportToExcel(formattedResults);
setProducts(results);
setIsLoading(false);
} else {
setIsLoading(false);
// console.log('No excel data available');
}
};
const handleFileChange = (e) => {
setIsLoading(true);
const file = e.target.files[0];
const reader = new FileReader();
reader.onload = (event) => {
const data = new Uint8Array(event.target.result);
const workbook = XLSX.read(data, { type: 'array' });
const firstSheetName = workbook.SheetNames[0];
const worksheet = workbook.Sheets[firstSheetName];
const jsonData = XLSX.utils.sheet_to_json(worksheet);
setExcelData(jsonData);
// console.log('ini json data', jsonData);
setIsLoading(false);
};
reader.readAsArrayBuffer(file);
};
const handleVariantsOpen = ({ variants }) => {
setVariantsOpen(variants);
setIsOpen(true);
};
const hadnliChooseVariants = ({ id, variant }) => {
let foundIndex = products.findIndex((item) => item.result.id === id);
if (foundIndex !== -1) {
products[foundIndex].result.code = variant?.code;
products[foundIndex].result.name = variant?.name;
} else {
// console.log('Data not found.');
}
setIsOpen(false);
};
const handlingOtherRec = ({ product }) => {
// console.log('ini product', product);
const result = async () =>
await searchRecomendation({ product, index: 0, operator: 'OR' });
result();
};
const generateProductRecomendation = async ({ product, index }) => {
let variants = [];
let resultMapping = {};
const searchProduct = await axios.post(
`${process.env.NEXT_PUBLIC_SELF_HOST}/api/shop/generate-recomendation?q=${product}&op=AND`
);
const searchProductOR = await axios.post(
`${process.env.NEXT_PUBLIC_SELF_HOST}/api/shop/generate-recomendation?q=${product}&op=OR`
);
const resultAND =
searchProduct.data.response.numFound > 0
? searchProduct.data.response.docs[0]
: null; // hasil satu
const resultOR =
searchProductOR.data.response.numFound > 0
? searchProductOR.data.response.docs
: []; // hasil 5
resultMapping = {
index: index,
product: product,
result: {},
};
// Add resultAND to resultMapping if it exists
resultMapping.result[0] = resultAND
? {
id: resultAND?.id || '-',
name: resultAND?.nameS || '-',
code: resultAND?.defaultCodeS || '-',
}
: null;
// Add resultOR to resultMapping
if (resultOR.length > 0) {
resultOR.forEach((item, idx) => {
resultMapping.result[idx + 1] = {
id: item?.id || '-',
name: item?.nameS || '-',
code: item?.defaultCodeS || '-',
};
});
} else {
for (let i = 0; i <= 5; i++) {
resultMapping.result[i + 1] = null;
}
}
return resultMapping;
};
return (
<>
setIsOpen(false)}
className='w-full md:!w-[60%]'
title='List Variants'
>
| Part Number |
Variants |
Harga |
|
{variantsOpen?.map((variant, index) => (
| {variant.code} |
{variant.attributes.join(', ') || '-'} |
{variant.price.discountPercentage > 0 && (
{Math.floor(variant.price.discountPercentage)}%
Rp {formatCurrency(variant.price.price)}
)}
{variant.price.priceDiscount > 0 &&
`Rp ${formatCurrency(variant.price.priceDiscount)}`}
{variant.price.priceDiscount === 0 && '-'}
|
|
))}
setOtherRec(false)}
className='w-full md:!w-[60%]'
title='Other Recomendations'
>
| Product |
Item Code |
Description |
Brand |
Price |
Image |
{variantsOpen?.map((variant, index) => (
| {variant.code} |
{variant.attributes.join(', ') || '-'} |
{variant.price.discountPercentage > 0 && (
{Math.floor(variant.price.discountPercentage)}%
Rp {formatCurrency(variant.price.price)}
)}
{variant.price.priceDiscount > 0 &&
`Rp ${formatCurrency(variant.price.priceDiscount)}`}
{variant.price.priceDiscount === 0 && '-'}
|
|
))}
Generate Recomendation
Contoh Excel
| Product |
Qty |
| Tekiro Long Nose Pliers Tang Lancip |
10 |
{/*
{products && products.length > 0 && (
| Product |
Item Code |
Description |
Brand |
Price |
Image |
lainnya |
{products.map((product, index) => (
| {product?.product} |
{product?.result?.code === '-' &&
product.result.variantTotal > 1 && (
)}
{product?.result.code !== '-' &&
product?.result.variantTotal > 1 ? (
<>
{product?.result.code}
>
) : (
<>{product?.result.code}>
)}
|
{product?.result.name} |
{product?.result.manufacture} |
{product?.result.price !== '-'
? `Rp ${formatCurrency(product?.result.price)}`
: '-'}
|
{product?.result.image !== '-' ? (
) : (
'-'
)}
|
{' '}
|
))}
)}
*/}
>
);
};
export default ProductsRecomendation;