From a0470ed9c5a0eeb8af292b7f667e7c32a066ad29 Mon Sep 17 00:00:00 2001 From: "gpt-engineer-app[bot]" <159125892+gpt-engineer-app[bot]@users.noreply.github.com> Date: Sun, 6 Jul 2025 17:50:07 +0000 Subject: [PATCH] Refactor: Centralize database operations Consolidated database interaction logic into service files. Streamlined job and transaction creation/update processes to minimize database requests, improving efficiency. --- src/components/MaterialsImportExport.tsx | 61 +++--- src/hooks/useDataService.ts | 69 ++++++ src/pages/Index.tsx | 200 +++++------------ src/services/dataService.ts | 261 +++++++++++++++++++++++ src/services/transactionService.ts | 27 +-- 5 files changed, 422 insertions(+), 196 deletions(-) create mode 100644 src/hooks/useDataService.ts create mode 100644 src/services/dataService.ts diff --git a/src/components/MaterialsImportExport.tsx b/src/components/MaterialsImportExport.tsx index d132e01..d0cc244 100644 --- a/src/components/MaterialsImportExport.tsx +++ b/src/components/MaterialsImportExport.tsx @@ -4,13 +4,12 @@ import { Button } from '@/components/ui/button'; import { Textarea } from '@/components/ui/textarea'; import { Label } from '@/components/ui/label'; import { Import, Download, FileText } from 'lucide-react'; -import { IndBillitemRecord } from '@/lib/pbtypes'; +import { IndBillitemRecord, IndBillitemRecordNoId } from '@/lib/pbtypes'; import { IndJob } from '@/lib/types'; -import { addBillItem } from '@/services/billItemService'; -import { updateJob } from '@/services/jobService'; +import { dataService } from '@/services/dataService'; interface MaterialsImportExportProps { - job: IndJob; + job?: IndJob; billOfMaterials: IndBillitemRecord[]; consumedMaterials: IndBillitemRecord[]; onBillOfMaterialsUpdate: (billItems: IndBillitemRecord[]) => void; @@ -27,9 +26,9 @@ const MaterialsImportExport: React.FC = ({ const [bomInput, setBomInput] = useState(''); const [consumedInput, setConsumedInput] = useState(''); - const parseBillOfMaterials = async (text: string): Promise => { + const parseBillOfMaterials = (text: string): IndBillitemRecordNoId[] => { const lines = text.split('\n').filter(line => line.trim()); - const materials: IndBillitemRecord[] = []; + const materials: IndBillitemRecordNoId[] = []; for (const line of lines) { const parts = line.trim().split(/\s+/); @@ -37,20 +36,17 @@ const MaterialsImportExport: React.FC = ({ const name = parts.slice(0, -1).join(' '); const quantity = parseInt(parts[parts.length - 1]); if (name && !isNaN(quantity)) { - const newBillItem = await addBillItem(job.id, { name, quantity }); - materials.push(newBillItem); + materials.push({ name, quantity }); } } } - job.billOfMaterials = materials; - await updateJob(job.id, { billOfMaterials: materials.map(item => item.id) }); - return job; + return materials; }; - const parseConsumedMaterials = async (text: string): Promise => { + const parseConsumedMaterials = (text: string): IndBillitemRecordNoId[] => { const lines = text.split('\n').filter(line => line.trim()); - const materials: IndBillitemRecord[] = []; + const materials: IndBillitemRecordNoId[] = []; for (const line of lines) { const parts = line.trim().split('\t'); @@ -58,15 +54,12 @@ const MaterialsImportExport: React.FC = ({ const name = parts[0]; const quantity = parseInt(parts[1]); if (name && !isNaN(quantity)) { - const newBillItem = await addBillItem(job.id, { name, quantity }); - materials.push(newBillItem); + materials.push({ name, quantity }); } } } - job.consumedMaterials = materials; - await updateJob(job.id, { consumedMaterials: materials.map(item => item.id) }); - return job; + return materials; }; const exportBillOfMaterials = (): string => { @@ -78,15 +71,33 @@ const MaterialsImportExport: React.FC = ({ }; const handleImportBom = async () => { - const parsed = await parseBillOfMaterials(bomInput); - onBillOfMaterialsUpdate(parsed.billOfMaterials); - setBomInput(''); + if (!job) return; + + const materials = parseBillOfMaterials(bomInput); + if (materials.length > 0) { + try { + const updatedJob = await dataService.createMultipleBillItems(job.id, materials, 'billOfMaterials'); + onBillOfMaterialsUpdate(updatedJob.billOfMaterials); + setBomInput(''); + } catch (error) { + console.error('Error importing bill of materials:', error); + } + } }; const handleImportConsumed = async () => { - const parsed = await parseConsumedMaterials(consumedInput); - onConsumedMaterialsUpdate(parsed.consumedMaterials); - setConsumedInput(''); + if (!job) return; + + const materials = parseConsumedMaterials(consumedInput); + if (materials.length > 0) { + try { + const updatedJob = await dataService.createMultipleBillItems(job.id, materials, 'consumedMaterials'); + onConsumedMaterialsUpdate(updatedJob.consumedMaterials); + setConsumedInput(''); + } catch (error) { + console.error('Error importing consumed materials:', error); + } + } }; const handleExportBom = () => { @@ -131,6 +142,7 @@ const MaterialsImportExport: React.FC = ({