Added manufacturing index
This commit is contained in:
parent
d7bd261cea
commit
3bcd609ce3
@ -1 +0,0 @@
|
|||||||
|
|
||||||
@ -1180,6 +1180,14 @@ const CompanyProfile = () => {
|
|||||||
pattern="[0-9]*"
|
pattern="[0-9]*"
|
||||||
readOnly={modalMode === 'view'}
|
readOnly={modalMode === 'view'}
|
||||||
/>
|
/>
|
||||||
|
<TextField
|
||||||
|
label="Zone (Area name)"
|
||||||
|
value={form.contactZone || ''}
|
||||||
|
onChange={handleFormChange('contactZone')}
|
||||||
|
placeholder="Enter zone"
|
||||||
|
width="100%"
|
||||||
|
readOnly={modalMode === 'view'}
|
||||||
|
/>
|
||||||
<TextField
|
<TextField
|
||||||
label="PO Box"
|
label="PO Box"
|
||||||
value={form.contactPoBox}
|
value={form.contactPoBox}
|
||||||
|
|||||||
@ -1574,7 +1574,7 @@ const handleExportCSV = () => {
|
|||||||
|
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
<div className="grid grid-cols-1 md:grid-cols-2 gap-4 mt-4">
|
<div className="grid grid-cols-2 gap-4 mt-4">
|
||||||
<div>
|
<div>
|
||||||
<label className="block text-sm font-medium text-[#374151] mb-1">
|
<label className="block text-sm font-medium text-[#374151] mb-1">
|
||||||
Unit <span className="text-[#EF4444]">*</span>
|
Unit <span className="text-[#EF4444]">*</span>
|
||||||
@ -1606,32 +1606,30 @@ const handleExportCSV = () => {
|
|||||||
|
|
||||||
<div>
|
<div>
|
||||||
<label className="block text-sm font-medium text-[#374151] mb-1">
|
<label className="block text-sm font-medium text-[#374151] mb-1">
|
||||||
Description
|
Weight
|
||||||
</label>
|
</label>
|
||||||
<textarea
|
<input
|
||||||
value={form.description || ''}
|
type="text"
|
||||||
onChange={handleFormChange("description")}
|
value={form.weight || ''}
|
||||||
disabled={modalMode === "view"}
|
onChange={handleFormChange("weight")}
|
||||||
rows={1}
|
|
||||||
className="w-full px-3 py-2 text-sm border border-[#CBA344] rounded-md focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] min-h-[38px] resize-y"
|
|
||||||
placeholder="Enter product description"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
{/* <div>
|
|
||||||
<label className="block text-sm font-medium text-[#374151] mb-1">
|
|
||||||
Status <span className="text-[#EF4444]">*</span>
|
|
||||||
</label>
|
|
||||||
<select
|
|
||||||
value={form.status}
|
|
||||||
onChange={handleFormChange("status")}
|
|
||||||
disabled={modalMode === "view"}
|
disabled={modalMode === "view"}
|
||||||
className="w-full px-3 py-2 text-sm border border-[#CBA344] rounded-md focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A]"
|
className="w-full px-3 py-2 text-sm border border-[#CBA344] rounded-md focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A]"
|
||||||
>
|
placeholder="Enter weight"
|
||||||
<option value="">Select</option>
|
/>
|
||||||
<option value="Active">Active</option>
|
</div>
|
||||||
<option value="Inactive">Inactive</option>
|
</div>
|
||||||
</select>
|
<div className="mt-4">
|
||||||
</div> */}
|
<label className="block text-sm font-medium text-[#374151] mb-1">
|
||||||
|
Description
|
||||||
|
</label>
|
||||||
|
<textarea
|
||||||
|
value={form.description || ''}
|
||||||
|
onChange={handleFormChange("description")}
|
||||||
|
disabled={modalMode === "view"}
|
||||||
|
rows={2}
|
||||||
|
className="w-full px-3 py-2 text-sm border border-[#CBA344] rounded-md focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] min-h-[38px] resize-y"
|
||||||
|
placeholder="Enter product description"
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@ -121,6 +121,11 @@ const ManufacturingIndex = () => {
|
|||||||
dataArray = [];
|
dataArray = [];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Debug: Log the actual data structure
|
||||||
|
console.log('API Response:', response);
|
||||||
|
console.log('Data Array:', dataArray);
|
||||||
|
console.log('Sample item:', dataArray[0]);
|
||||||
|
|
||||||
// Format the data
|
// Format the data
|
||||||
const formattedData = dataArray.map((item, index) => {
|
const formattedData = dataArray.map((item, index) => {
|
||||||
// Create a date object from reference_date or other date fields
|
// Create a date object from reference_date or other date fields
|
||||||
@ -151,17 +156,17 @@ const ManufacturingIndex = () => {
|
|||||||
monthName: monthName,
|
monthName: monthName,
|
||||||
year: year,
|
year: year,
|
||||||
monthNumber: monthNumber,
|
monthNumber: monthNumber,
|
||||||
index: item.manufacturing_index?.toString() || item.index?.toString() || item.manufacturingIndex?.toString() || 'N/A',
|
index: item.manufacturing_index?.toString() || item.index?.toString() || item.manufacturingIndex?.toString() || '-',
|
||||||
mom: item.mom_change || item.mom || item.momChange ?
|
mom: item.mom_change || item.mom || item.momChange ?
|
||||||
(parseFloat(item.mom_change || item.mom || item.momChange) > 0 ?
|
(parseFloat(item.mom_change || item.mom || item.momChange) > 0 ?
|
||||||
`+${item.mom_change || item.mom || item.momChange}` :
|
`+${item.mom_change || item.mom || item.momChange}` :
|
||||||
(item.mom_change || item.mom || item.momChange).toString()) :
|
(item.mom_change || item.mom || item.momChange).toString()) :
|
||||||
'N/A',
|
'-',
|
||||||
yoy: item.yoy_change || item.yoy || item.yoyChange ?
|
yoy: item.yoy_change || item.yoy || item.yoyChange ?
|
||||||
(parseFloat(item.yoy_change || item.yoy || item.yoyChange) > 0 ?
|
(parseFloat(item.yoy_change || item.yoy || item.yoyChange) > 0 ?
|
||||||
`+${item.yoy_change || item.yoy || item.yoyChange}` :
|
`+${item.yoy_change || item.yoy || item.yoyChange}` :
|
||||||
(item.yoy_change || item.yoy || item.yoyChange).toString()) :
|
(item.yoy_change || item.yoy || item.yoyChange).toString()) :
|
||||||
'N/A',
|
'-',
|
||||||
generated: item.generated_on || item.generatedOn || item.generated_at ?
|
generated: item.generated_on || item.generatedOn || item.generated_at ?
|
||||||
new Date(item.generated_on || item.generatedOn || item.generated_at).toLocaleString('en-US', {
|
new Date(item.generated_on || item.generatedOn || item.generated_at).toLocaleString('en-US', {
|
||||||
year: 'numeric',
|
year: 'numeric',
|
||||||
@ -171,7 +176,9 @@ const ManufacturingIndex = () => {
|
|||||||
minute: '2-digit',
|
minute: '2-digit',
|
||||||
timeZone: 'Asia/Dubai',
|
timeZone: 'Asia/Dubai',
|
||||||
timeZoneName: 'short'
|
timeZoneName: 'short'
|
||||||
}) : 'N/A',
|
}) : '-',
|
||||||
|
quarter: item.quarter || item.quarter_name || '-',
|
||||||
|
totalWeight: item.total_weight || '-',
|
||||||
status: item.status || 'Completed',
|
status: item.status || 'Completed',
|
||||||
rawData: item
|
rawData: item
|
||||||
};
|
};
|
||||||
@ -242,7 +249,7 @@ const ManufacturingIndex = () => {
|
|||||||
setApiLoading(true);
|
setApiLoading(true);
|
||||||
|
|
||||||
// API CALL
|
// API CALL
|
||||||
const apiResponse = await getManufacturingMonthlyOverview(yearNumber, monthNumber);
|
const apiResponse = await getManufacturingMonthlyOverview(yearNumber, row.quarter);
|
||||||
|
|
||||||
// Extract data from the response structure
|
// Extract data from the response structure
|
||||||
// Note: Your API returns {status, message, manufacturing_total, isic_2digit, isic_3digit, isic_4digit}
|
// Note: Your API returns {status, message, manufacturing_total, isic_2digit, isic_3digit, isic_4digit}
|
||||||
@ -309,12 +316,14 @@ const ManufacturingIndex = () => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const handleExportCSV = () => {
|
const handleExportCSV = () => {
|
||||||
const headers = ['Month', 'Index', 'MoM Change', 'YoY Change', 'Generated On', 'Status'];
|
const headers = ['Month', 'Quarter', 'Index', 'Total Weight', 'MoM Change', 'YoY Change', 'Generated On', 'Status'];
|
||||||
const csvContent = [
|
const csvContent = [
|
||||||
headers.join(','),
|
headers.join(','),
|
||||||
...filteredMonths.map(month => [
|
...filteredMonths.map(month => [
|
||||||
`"${month.month}"`,
|
`"${month.month}"`,
|
||||||
|
`"${month.quarter}"`,
|
||||||
month.index,
|
month.index,
|
||||||
|
month.totalWeight,
|
||||||
month.mom,
|
month.mom,
|
||||||
month.yoy,
|
month.yoy,
|
||||||
`"${month.generated}"`,
|
`"${month.generated}"`,
|
||||||
@ -391,8 +400,7 @@ const ManufacturingIndex = () => {
|
|||||||
className="relative"
|
className="relative"
|
||||||
>
|
>
|
||||||
<DialogTitle className="bg-[#F9F5E8] text-[#92722A] flex justify-between items-center pr-2">
|
<DialogTitle className="bg-[#F9F5E8] text-[#92722A] flex justify-between items-center pr-2">
|
||||||
<span>Monthly ISIC breakdown
|
<span>Monthly ISIC breakdown {selectedMonth?.quarter} - {selectedMonth?.month}</span>
|
||||||
- {selectedMonth?.month}</span>
|
|
||||||
<IconButton
|
<IconButton
|
||||||
onClick={handleClosePopup}
|
onClick={handleClosePopup}
|
||||||
size="small"
|
size="small"
|
||||||
@ -591,7 +599,9 @@ const ManufacturingIndex = () => {
|
|||||||
<Table
|
<Table
|
||||||
headers={[
|
headers={[
|
||||||
'Reference Month',
|
'Reference Month',
|
||||||
|
'Quarter',
|
||||||
'Manufacturing Index',
|
'Manufacturing Index',
|
||||||
|
'Total Weight',
|
||||||
'MOM Change',
|
'MOM Change',
|
||||||
'YOY Change',
|
'YOY Change',
|
||||||
'Generated On',
|
'Generated On',
|
||||||
@ -604,9 +614,15 @@ const ManufacturingIndex = () => {
|
|||||||
<div key="month" className={`${isSelected ? 'font-medium' : ''}`}>
|
<div key="month" className={`${isSelected ? 'font-medium' : ''}`}>
|
||||||
{row.month}
|
{row.month}
|
||||||
</div>,
|
</div>,
|
||||||
|
<span className={isSelected ? 'font-medium' : ''} key="quarter">
|
||||||
|
{row.quarter}
|
||||||
|
</span>,
|
||||||
<span className={isSelected ? 'font-medium' : ''} key="index">
|
<span className={isSelected ? 'font-medium' : ''} key="index">
|
||||||
{row.index} (2022=100)
|
{row.index} (2022=100)
|
||||||
</span>,
|
</span>,
|
||||||
|
<span className={isSelected ? 'font-medium' : ''} key="totalWeight">
|
||||||
|
{row.totalWeight}
|
||||||
|
</span>,
|
||||||
<span className={`${parseFloat(row.mom) >= 0 ? 'text-green-600' : 'text-red-600'} ${isSelected ? 'font-medium' : ''}`} key="mom">
|
<span className={`${parseFloat(row.mom) >= 0 ? 'text-green-600' : 'text-red-600'} ${isSelected ? 'font-medium' : ''}`} key="mom">
|
||||||
{row.mom}%
|
{row.mom}%
|
||||||
</span>,
|
</span>,
|
||||||
@ -636,7 +652,7 @@ const ManufacturingIndex = () => {
|
|||||||
</div>
|
</div>
|
||||||
];
|
];
|
||||||
})}
|
})}
|
||||||
columnWidths={['180px', '190px', '130px', '130px', '200px', '120px', '80px']}
|
columnWidths={['180px', '100px', '190px', '120px', '130px', '130px', '200px', '120px', '80px']}
|
||||||
getRowClass={(index) => {
|
getRowClass={(index) => {
|
||||||
const isSelected = selectedMonth?.month === filteredMonths[index]?.month;
|
const isSelected = selectedMonth?.month === filteredMonths[index]?.month;
|
||||||
return isSelected ? 'bg-[#F5F0E1]' : 'hover:bg-gray-50';
|
return isSelected ? 'bg-[#F5F0E1]' : 'hover:bg-gray-50';
|
||||||
|
|||||||
@ -35,15 +35,15 @@ const ISIC2Digit = ({ setActiveTab, apiData }) => {
|
|||||||
if (filteredData.length === 0) return;
|
if (filteredData.length === 0) return;
|
||||||
|
|
||||||
// Create CSV content
|
// Create CSV content
|
||||||
const headers = ['ISIC Code', 'Sector', 'Index', 'Weight (%)'];
|
const headers = ['ISIC Code', 'Index', 'Weight (%)', 'Weighted Index'];
|
||||||
const csvRows = [
|
const csvRows = [
|
||||||
headers.join(','),
|
headers.join(','),
|
||||||
...filteredData.map(item =>
|
...filteredData.map(item =>
|
||||||
[
|
[
|
||||||
`"${item.isic_2digit_code || ''}"`,
|
`"${item.isic_2digit_code || ''}"`,
|
||||||
`"${item.isic_description || ''}"`,
|
|
||||||
item.isic_2digit_index || '',
|
item.isic_2digit_index || '',
|
||||||
item.total_weight || ''
|
item.total_weight || '',
|
||||||
|
item.weighted_index_sum || ''
|
||||||
].join(',')
|
].join(',')
|
||||||
)
|
)
|
||||||
];
|
];
|
||||||
@ -62,7 +62,7 @@ const ISIC2Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
// Format number with 2 decimal places if needed
|
// Format number with 2 decimal places if needed
|
||||||
const formatNumber = (value) => {
|
const formatNumber = (value) => {
|
||||||
if (value === null || value === undefined || value === '' || value === 'N/A') return 'N/A';
|
if (value === null || value === undefined || value === '' || value === '-') return '-';
|
||||||
|
|
||||||
const num = parseFloat(value);
|
const num = parseFloat(value);
|
||||||
if (isNaN(num)) return value;
|
if (isNaN(num)) return value;
|
||||||
@ -81,7 +81,14 @@ const ISIC2Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="-mt-4">
|
<div className="-mt-4">
|
||||||
<h3 className="text-lg font-semibold text-gray-900">ISIC 2-digit breakdown</h3>
|
<div className="flex items-center justify-between mb-4">
|
||||||
|
<h3 className="text-lg font-semibold text-gray-900">ISIC 2-digit breakdown</h3>
|
||||||
|
{/* <div className="bg-gray-100 px-3 py-1 rounded-full">
|
||||||
|
<span className="text-sm font-medium text-gray-700">
|
||||||
|
Quarter: {apiData?.[0]?.quarter || '-'}
|
||||||
|
</span>
|
||||||
|
</div> */}
|
||||||
|
</div>
|
||||||
<p className="text-sm mt-2 text-gray-600 mb-4">
|
<p className="text-sm mt-2 text-gray-600 mb-4">
|
||||||
The manufacturing index is calculated as a weighted average of ISIC 2-digit groups,
|
The manufacturing index is calculated as a weighted average of ISIC 2-digit groups,
|
||||||
using their relative weights in the manufacturing sector.
|
using their relative weights in the manufacturing sector.
|
||||||
@ -117,7 +124,7 @@ const ISIC2Digit = ({ setActiveTab, apiData }) => {
|
|||||||
</div>
|
</div>
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
placeholder="Search by sector or code..."
|
placeholder="Search by code or index..."
|
||||||
className="block w-full pl-10 pr-3 py-2 border border-gray-300 rounded-md leading-5 bg-white placeholder-gray-500 focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] sm:text-sm"
|
className="block w-full pl-10 pr-3 py-2 border border-gray-300 rounded-md leading-5 bg-white placeholder-gray-500 focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] sm:text-sm"
|
||||||
value={searchTerm}
|
value={searchTerm}
|
||||||
onChange={(e) => setSearchTerm(e.target.value)}
|
onChange={(e) => setSearchTerm(e.target.value)}
|
||||||
@ -142,13 +149,10 @@ const ISIC2Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
<div className="-mx-6">
|
<div className="-mx-6">
|
||||||
<Table
|
<Table
|
||||||
headers={['ISIC Code', 'Sector', 'Index', 'Weight (%)']}
|
headers={['ISIC Code', 'Index', 'Weight (%)', 'Weighted Index']}
|
||||||
rows={filteredData.map((item, index) => [
|
rows={filteredData.map((item, index) => [
|
||||||
<span className="font-medium" key={`code-${item.isic_2digit_code || index}`}>
|
<span className="font-medium" key={`code-${item.isic_2digit_code || index}`}>
|
||||||
{item.isic_2digit_code || 'N/A'}
|
{item.isic_2digit_code || '-'}
|
||||||
</span>,
|
|
||||||
<span key={`name-${item.isic_2digit_code || index}`}>
|
|
||||||
{item.isic_description || 'N/A'}
|
|
||||||
</span>,
|
</span>,
|
||||||
<span
|
<span
|
||||||
key={`index-${item.isic_2digit_code || index}`}
|
key={`index-${item.isic_2digit_code || index}`}
|
||||||
@ -158,10 +162,13 @@ const ISIC2Digit = ({ setActiveTab, apiData }) => {
|
|||||||
</span>,
|
</span>,
|
||||||
<span key={`weight-${item.isic_2digit_code || index}`}>
|
<span key={`weight-${item.isic_2digit_code || index}`}>
|
||||||
{formatNumber(item.total_weight)}%
|
{formatNumber(item.total_weight)}%
|
||||||
|
</span>,
|
||||||
|
<span key={`weighted-index-${item.isic_2digit_code || index}`}>
|
||||||
|
{formatNumber(item.weighted_index_sum)}
|
||||||
</span>
|
</span>
|
||||||
])}
|
])}
|
||||||
className="w-full"
|
className="w-full"
|
||||||
columnWidths={['15%', '55%', '15%', '15%']}
|
columnWidths={['15%', '30%', '25%', '30%']}
|
||||||
getCellClass={(rowIndex, colIndex) => {
|
getCellClass={(rowIndex, colIndex) => {
|
||||||
const baseClasses = 'px-6 py-4 whitespace-nowrap text-sm';
|
const baseClasses = 'px-6 py-4 whitespace-nowrap text-sm';
|
||||||
return colIndex === 0
|
return colIndex === 0
|
||||||
|
|||||||
@ -34,15 +34,15 @@ const ISIC3Digit = ({ setActiveTab, apiData }) => {
|
|||||||
if (filteredData.length === 0) return;
|
if (filteredData.length === 0) return;
|
||||||
|
|
||||||
// Create CSV content
|
// Create CSV content
|
||||||
const headers = ['ISIC Code', 'Sector', 'Index', 'Weight (%)'];
|
const headers = ['ISIC Code', 'Index', 'Weight (%)', 'Weighted Index'];
|
||||||
const csvRows = [
|
const csvRows = [
|
||||||
headers.join(','),
|
headers.join(','),
|
||||||
...filteredData.map(item =>
|
...filteredData.map(item =>
|
||||||
[
|
[
|
||||||
`"${item.isic_3digit_code || ''}"`,
|
`"${item.isic_3digit_code || ''}"`,
|
||||||
`"${item.isic_description || ''}"`,
|
|
||||||
item.isic_3digit_index || '',
|
item.isic_3digit_index || '',
|
||||||
item.total_weight || ''
|
item.total_weight || '',
|
||||||
|
item.weighted_index_sum || ''
|
||||||
].join(',')
|
].join(',')
|
||||||
)
|
)
|
||||||
];
|
];
|
||||||
@ -61,7 +61,7 @@ const ISIC3Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
// Format number with 2 decimal places if needed
|
// Format number with 2 decimal places if needed
|
||||||
const formatNumber = (value) => {
|
const formatNumber = (value) => {
|
||||||
if (value === null || value === undefined || value === '' || value === 'N/A') return 'N/A';
|
if (value === null || value === undefined || value === '' || value === '') return '-';
|
||||||
|
|
||||||
const num = parseFloat(value);
|
const num = parseFloat(value);
|
||||||
if (isNaN(num)) return value;
|
if (isNaN(num)) return value;
|
||||||
@ -71,7 +71,10 @@ const ISIC3Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="-mt-4">
|
<div className="-mt-4">
|
||||||
<h3 className="text-lg font-semibold text-gray-900">ISIC 3-digit breakdown</h3>
|
<div className="flex items-center justify-between mb-4">
|
||||||
|
<h3 className="text-lg font-semibold text-gray-900">ISIC 3-digit breakdown</h3>
|
||||||
|
|
||||||
|
</div>
|
||||||
<p className="text-sm mt-2 text-gray-600 mb-4">
|
<p className="text-sm mt-2 text-gray-600 mb-4">
|
||||||
Detailed breakdown of manufacturing index by ISIC 3-digit classification.
|
Detailed breakdown of manufacturing index by ISIC 3-digit classification.
|
||||||
</p>
|
</p>
|
||||||
@ -105,7 +108,7 @@ const ISIC3Digit = ({ setActiveTab, apiData }) => {
|
|||||||
</div>
|
</div>
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
placeholder="Search by sector or code..."
|
placeholder="Search by code or index..."
|
||||||
className="block w-full pl-10 pr-3 py-2 border border-gray-300 rounded-md leading-5 bg-white placeholder-gray-500 focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] sm:text-sm"
|
className="block w-full pl-10 pr-3 py-2 border border-gray-300 rounded-md leading-5 bg-white placeholder-gray-500 focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] sm:text-sm"
|
||||||
value={searchTerm}
|
value={searchTerm}
|
||||||
onChange={(e) => setSearchTerm(e.target.value)}
|
onChange={(e) => setSearchTerm(e.target.value)}
|
||||||
@ -130,13 +133,10 @@ const ISIC3Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
<div className="-mx-6">
|
<div className="-mx-6">
|
||||||
<Table
|
<Table
|
||||||
headers={['ISIC Code', 'Sector', 'Index', 'Weight (%)']}
|
headers={['ISIC Code', 'Index', 'Weight (%)', 'Weighted Index']}
|
||||||
rows={filteredData.map((item, index) => [
|
rows={filteredData.map((item, index) => [
|
||||||
<span className="font-medium" key={`code-${item.isic_3digit_code || index}`}>
|
<span className="font-medium" key={`code-${item.isic_3digit_code || index}`}>
|
||||||
{item.isic_3digit_code || 'N/A'}
|
{item.isic_3digit_code || '-'}
|
||||||
</span>,
|
|
||||||
<span key={`name-${item.isic_3digit_code || index}`}>
|
|
||||||
{item.isic_description || 'N/A'}
|
|
||||||
</span>,
|
</span>,
|
||||||
<span
|
<span
|
||||||
key={`index-${item.isic_3digit_code || index}`}
|
key={`index-${item.isic_3digit_code || index}`}
|
||||||
@ -146,10 +146,13 @@ const ISIC3Digit = ({ setActiveTab, apiData }) => {
|
|||||||
</span>,
|
</span>,
|
||||||
<span key={`weight-${item.isic_3digit_code || index}`}>
|
<span key={`weight-${item.isic_3digit_code || index}`}>
|
||||||
{formatNumber(item.total_weight)}%
|
{formatNumber(item.total_weight)}%
|
||||||
|
</span>,
|
||||||
|
<span key={`weighted-index-${item.isic_3digit_code || index}`}>
|
||||||
|
{formatNumber(item.weighted_index_sum)}
|
||||||
</span>
|
</span>
|
||||||
])}
|
])}
|
||||||
className="w-full"
|
className="w-full"
|
||||||
columnWidths={['20%', '50%', '15%', '15%']}
|
columnWidths={['15%', '30%', '25%', '30%']}
|
||||||
getCellClass={(rowIndex, colIndex) => {
|
getCellClass={(rowIndex, colIndex) => {
|
||||||
const baseClasses = 'px-6 py-4 whitespace-nowrap text-sm text-gray-900';
|
const baseClasses = 'px-6 py-4 whitespace-nowrap text-sm text-gray-900';
|
||||||
return colIndex === 0
|
return colIndex === 0
|
||||||
|
|||||||
@ -34,15 +34,15 @@ const ISIC4Digit = ({ setActiveTab, apiData }) => {
|
|||||||
if (filteredData.length === 0) return;
|
if (filteredData.length === 0) return;
|
||||||
|
|
||||||
// Create CSV content
|
// Create CSV content
|
||||||
const headers = ['ISIC Code', 'Sector', 'Index', 'Weight (%)'];
|
const headers = ['ISIC Code', 'Index', 'Weight (%)', 'Weighted Index'];
|
||||||
const csvRows = [
|
const csvRows = [
|
||||||
headers.join(','),
|
headers.join(','),
|
||||||
...filteredData.map(item =>
|
...filteredData.map(item =>
|
||||||
[
|
[
|
||||||
`"${item.isic_4digit_code || ''}"`,
|
`"${item.isic_4digit_code || ''}"`,
|
||||||
`"${item.isic_description || ''}"`,
|
|
||||||
item.isic_4digit_index || '',
|
item.isic_4digit_index || '',
|
||||||
item.total_weight || ''
|
item.total_weight || '',
|
||||||
|
item.weighted_index_sum || ''
|
||||||
].join(',')
|
].join(',')
|
||||||
)
|
)
|
||||||
];
|
];
|
||||||
@ -61,7 +61,7 @@ const ISIC4Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
// Format number with 2 decimal places if needed
|
// Format number with 2 decimal places if needed
|
||||||
const formatNumber = (value) => {
|
const formatNumber = (value) => {
|
||||||
if (value === null || value === undefined || value === '' || value === 'N/A') return 'N/A';
|
if (value === null || value === undefined || value === '' || value === '-') return '-';
|
||||||
|
|
||||||
const num = parseFloat(value);
|
const num = parseFloat(value);
|
||||||
if (isNaN(num)) return value;
|
if (isNaN(num)) return value;
|
||||||
@ -71,7 +71,10 @@ const ISIC4Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="-mt-4">
|
<div className="-mt-4">
|
||||||
<h3 className="text-lg font-semibold text-gray-900">ISIC 4-digit breakdown</h3>
|
<div className="flex items-center justify-between mb-4">
|
||||||
|
<h3 className="text-lg font-semibold text-gray-900">ISIC 4-digit breakdown</h3>
|
||||||
|
|
||||||
|
</div>
|
||||||
<p className="text-sm mt-2 text-gray-600 mb-4">
|
<p className="text-sm mt-2 text-gray-600 mb-4">
|
||||||
Detailed breakdown of manufacturing index by ISIC 4-digit classification.
|
Detailed breakdown of manufacturing index by ISIC 4-digit classification.
|
||||||
</p>
|
</p>
|
||||||
@ -105,7 +108,7 @@ const ISIC4Digit = ({ setActiveTab, apiData }) => {
|
|||||||
</div>
|
</div>
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
placeholder="Search by sector or code..."
|
placeholder="Search by code or index..."
|
||||||
className="block w-full pl-10 pr-3 py-2 border border-gray-300 rounded-md leading-5 bg-white placeholder-gray-500 focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] sm:text-sm"
|
className="block w-full pl-10 pr-3 py-2 border border-gray-300 rounded-md leading-5 bg-white placeholder-gray-500 focus:outline-none focus:ring-1 focus:ring-[#92722A] focus:border-[#92722A] sm:text-sm"
|
||||||
value={searchTerm}
|
value={searchTerm}
|
||||||
onChange={(e) => setSearchTerm(e.target.value)}
|
onChange={(e) => setSearchTerm(e.target.value)}
|
||||||
@ -130,13 +133,10 @@ const ISIC4Digit = ({ setActiveTab, apiData }) => {
|
|||||||
|
|
||||||
<div className="-mx-6">
|
<div className="-mx-6">
|
||||||
<Table
|
<Table
|
||||||
headers={['ISIC Code', 'Sector', 'Index', 'Weight (%)']}
|
headers={['ISIC Code', 'Index', 'Weight (%)', 'Weighted Index']}
|
||||||
rows={filteredData.map((item, index) => [
|
rows={filteredData.map((item, index) => [
|
||||||
<span className="font-medium" key={`code-${item.isic_4digit_code || index}`}>
|
<span className="font-medium" key={`code-${item.isic_4digit_code || index}`}>
|
||||||
{item.isic_4digit_code || 'N/A'}
|
{item.isic_4digit_code || '-'}
|
||||||
</span>,
|
|
||||||
<span key={`name-${item.isic_4digit_code || index}`}>
|
|
||||||
{item.isic_description || 'N/A'}
|
|
||||||
</span>,
|
</span>,
|
||||||
<span
|
<span
|
||||||
key={`index-${item.isic_4digit_code || index}`}
|
key={`index-${item.isic_4digit_code || index}`}
|
||||||
@ -146,10 +146,13 @@ const ISIC4Digit = ({ setActiveTab, apiData }) => {
|
|||||||
</span>,
|
</span>,
|
||||||
<span key={`weight-${item.isic_4digit_code || index}`}>
|
<span key={`weight-${item.isic_4digit_code || index}`}>
|
||||||
{formatNumber(item.total_weight)}%
|
{formatNumber(item.total_weight)}%
|
||||||
|
</span>,
|
||||||
|
<span key={`weighted-index-${item.isic_4digit_code || index}`}>
|
||||||
|
{formatNumber(item.weighted_index_sum)}
|
||||||
</span>
|
</span>
|
||||||
])}
|
])}
|
||||||
className="w-full"
|
className="w-full"
|
||||||
columnWidths={['20%', '50%', '15%', '15%']}
|
columnWidths={['15%', '30%', '25%', '30%']}
|
||||||
getCellClass={(rowIndex, colIndex) => {
|
getCellClass={(rowIndex, colIndex) => {
|
||||||
const baseClasses = 'px-6 py-4 whitespace-nowrap text-sm text-gray-900';
|
const baseClasses = 'px-6 py-4 whitespace-nowrap text-sm text-gray-900';
|
||||||
return colIndex === 0
|
return colIndex === 0
|
||||||
|
|||||||
@ -23,18 +23,18 @@ const ManufacturingTotal = ({ selectedMonthData, setActiveTab, monthlyOverviewDa
|
|||||||
if (apiData) {
|
if (apiData) {
|
||||||
// API data has different structure
|
// API data has different structure
|
||||||
switch(key) {
|
switch(key) {
|
||||||
case 'index': return apiData.index || apiData.manufacturing_index || 'N/A';
|
case 'index': return apiData.index || apiData.manufacturing_index || '-';
|
||||||
case 'mom':
|
case 'mom':
|
||||||
const momVal = apiData.mom || apiData.mom_change || 0;
|
const momVal = apiData.mom || apiData.mom_change || 0;
|
||||||
return momVal > 0 ? `+${momVal}%` : `${momVal}%`;
|
return momVal > 0 ? `+${momVal}%` : `${momVal}%`;
|
||||||
case 'yoy':
|
case 'yoy':
|
||||||
const yoyVal = apiData.yoy || apiData.yoy_change || 0;
|
const yoyVal = apiData.yoy || apiData.yoy_change || 0;
|
||||||
return yoyVal > 0 ? `+${yoyVal}%` : `${yoyVal}%`;
|
return yoyVal > 0 ? `+${yoyVal}%` : `${yoyVal}%`;
|
||||||
default: return 'N/A';
|
default: return '-';
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// Table data
|
// Table data
|
||||||
return dataSource[key] || 'N/A';
|
return dataSource[key] || '-';
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -48,9 +48,16 @@ const ManufacturingTotal = ({ selectedMonthData, setActiveTab, monthlyOverviewDa
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="space-y-5">
|
<div className="space-y-5">
|
||||||
<p className="text-xs font-semibold uppercase tracking-wider text-medium-500">
|
<div className="flex items-center justify-between">
|
||||||
Manufacturing Index (Headline)
|
<p className="text-xs font-semibold uppercase tracking-wider text-medium-500">
|
||||||
</p>
|
Manufacturing Index (Headline)
|
||||||
|
</p>
|
||||||
|
{/* <div className="bg-gray-100 px-3 py-1 rounded-full"> */}
|
||||||
|
{/* <span className="text-sm font-medium text-gray-700">
|
||||||
|
Quarter: {selectedMonthData?.quarter || '-'}
|
||||||
|
</span> */}
|
||||||
|
{/* </div> */}
|
||||||
|
</div>
|
||||||
|
|
||||||
<div className="flex items-baseline gap-2">
|
<div className="flex items-baseline gap-2">
|
||||||
<h3 className="text-3xl font-semibold text-gray-900">
|
<h3 className="text-3xl font-semibold text-gray-900">
|
||||||
|
|||||||
@ -57,7 +57,7 @@ export const getSubmissions = async (params = {}) => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
/** 🔹 Fetch a single submission by ID */
|
/** Fetch a single submission by ID */
|
||||||
export const getSubmissionById = async (id) => {
|
export const getSubmissionById = async (id) => {
|
||||||
const response = await apiClient.get(`/submissions/view/${id}`);
|
const response = await apiClient.get(`/submissions/view/${id}`);
|
||||||
return response.data;
|
return response.data;
|
||||||
|
|||||||
@ -12,7 +12,7 @@ export const getManufacturingIndex = async () => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
export const getManufacturingMonthlyOverview = async (year, month) => {
|
export const getManufacturingMonthlyOverview = async (year, quarter) => {
|
||||||
try {
|
try {
|
||||||
|
|
||||||
const response = await getRequest(
|
const response = await getRequest(
|
||||||
@ -20,7 +20,7 @@ export const getManufacturingMonthlyOverview = async (year, month) => {
|
|||||||
{
|
{
|
||||||
params: {
|
params: {
|
||||||
year: year.toString(),
|
year: year.toString(),
|
||||||
month: month.toString(),
|
quarter: quarter.toString(),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user