/** * This file is part of Sharenet. * * Sharenet is licensed under the Creative Commons Attribution-NonCommercial-ShareAlike 4.0 International License. * * You may obtain a copy of the license at: * https://creativecommons.org/licenses/by-nc-sa/4.0/ * * Copyright (c) 2024 Continuist */ 'use client'; import { useState, useEffect } from 'react'; import { productApi, Product } from '@/lib/api'; import { Button } from '@/components/ui/button'; import { ResponsiveTable } from '@/components/ui/responsive-table'; import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogTrigger, } from '@/components/ui/dialog'; import { Input } from '@/components/ui/input'; import { Label } from '@/components/ui/label'; export default function ProductsPage() { const [products, setProducts] = useState([]); const [isDialogOpen, setIsDialogOpen] = useState(false); const [editingProduct, setEditingProduct] = useState(null); const [formData, setFormData] = useState({ name: '', description: '', }); const [errors, setErrors] = useState({ name: '', description: '', }); useEffect(() => { loadProducts(); }, []); const loadProducts = async () => { try { const response = await productApi.getAll(); setProducts(response.data); } catch (error) { console.error('Error loading products:', error); } }; const validateForm = () => { const newErrors = { name: '', description: '', }; // Product name cannot be empty if (!formData.name.trim()) { newErrors.name = 'Product name is required'; } // Description can be empty, no validation needed setErrors(newErrors); return !newErrors.name; }; const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); if (!validateForm()) { return; } try { if (editingProduct) { await productApi.update(editingProduct.id, formData); } else { await productApi.create(formData); } setIsDialogOpen(false); setEditingProduct(null); setFormData({ name: '', description: '' }); setErrors({ name: '', description: '' }); loadProducts(); } catch (error) { console.error('Error saving product:', error); } }; const handleEdit = (product: Product) => { setEditingProduct(product); setFormData({ name: product.name, description: product.description, }); setErrors({ name: '', description: '' }); setIsDialogOpen(true); }; const handleDelete = async (id: string) => { if (confirm('Are you sure you want to delete this product?')) { try { await productApi.delete(id); loadProducts(); } catch (error) { console.error('Error deleting product:', error); } } }; const handleInputChange = (field: 'name' | 'description', value: string) => { setFormData({ ...formData, [field]: value }); // Clear error when user starts typing if (errors[field]) { setErrors({ ...errors, [field]: '' }); } }; const columns = [ { key: 'name', header: 'Name', mobilePriority: true, }, { key: 'description', header: 'Description', mobilePriority: true, render: (value: unknown) => String(value || 'No description'), }, { key: 'actions', header: 'Actions', mobilePriority: true, render: (_: unknown, product: Record) => (
), }, ]; return (

Products

{editingProduct ? 'Edit Product' : 'Add Product'}
handleInputChange('name', e.target.value)} className={errors.name ? 'border-red-500' : ''} /> {errors.name && (

{errors.name}

)}
handleInputChange('description', e.target.value)} />
[]} />
); }