diff --git a/src/models/ProviderProduct.js b/src/models/ProviderProduct.js index bd819c0..d919874 100644 --- a/src/models/ProviderProduct.js +++ b/src/models/ProviderProduct.js @@ -2,7 +2,7 @@ import Price from "./Price"; import Provider from "./Provider"; export class ProviderProduct { - constructor(providerId, productId, priceId, numSeries, price = {}, provider = {}) { + constructor({providerId, productId, priceId, numSeries, price = {}, provider = {}}) { this.providerId = providerId; this.productId = productId; this.priceId = priceId; diff --git a/src/pages/Products/ProductDialog/ModelManager.jsx b/src/pages/Products/ProductDialog/ModelManager.jsx index 1d2cc4e..0fe4710 100644 --- a/src/pages/Products/ProductDialog/ModelManager.jsx +++ b/src/pages/Products/ProductDialog/ModelManager.jsx @@ -14,7 +14,6 @@ import { ProductCarModel } from '../../../models/ProductCarModel'; import Brand from '../../../models/Brand'; import { modifyAndClone } from '../../../util/generalUtils'; - const ModelManagerDisplay = ({ product, brand, @@ -29,10 +28,10 @@ const ModelManagerDisplay = ({ readOnly = false, handleStartYearChange, handleLastYearChange, - handleOnItemAdded + handleOnItemAdded, + isAddButtonDisabled }) => { return ( - {readOnly ? '' : 'Agrega y gestiona los modelos.'} @@ -100,7 +99,12 @@ const ModelManagerDisplay = ({ /> - @@ -186,11 +190,6 @@ const ModelManager = () => { handleSetProduct(modifyAndClone(product, 'carModels', newProductsCarModels)); }; - const handleCarModelCreated = (model) => { - setModels([...models, new CarModel(model)]); - setProductModel({ ...productModel, carModelId: model.id }); - }; - const handleStartYearChange = (year) => { setProductModel({ ...productModel, initialYear: year }); } @@ -212,6 +211,7 @@ const ModelManager = () => { handleSetProduct(modifyAndClone(product, 'carModels', [...product.carModels, productModel])); } + const isAddButtonDisabled = !productModel.carModelId || !productModel.initialYear || !productModel.lastYear; return ( { handleModelChange={handleModelChange} handleDeleteModel={handleDeleteModel} readOnly={false} - handleCarModelCreated={handleCarModelCreated} handleStartYearChange={handleStartYearChange} handleLastYearChange={handleLastYearChange} handleOnItemAdded={handleOnItemAdded} handleCarModelAdded={handleCarModelAdded} + isAddButtonDisabled={isAddButtonDisabled} /> ); }; -export { ModelManager as default, ModelManagerDisplay } - +export { ModelManager as default, ModelManagerDisplay } \ No newline at end of file diff --git a/src/pages/Products/ProductDialog/PriceManager.jsx b/src/pages/Products/ProductDialog/PriceManager.jsx index 3756b1d..5ad0f65 100644 --- a/src/pages/Products/ProductDialog/PriceManager.jsx +++ b/src/pages/Products/ProductDialog/PriceManager.jsx @@ -14,6 +14,7 @@ const PriceManagerDisplay = ({ setPrice, handleDeletePrice, handleAddPrice, + isAddButtonDisabled, readOnly = false }) => { return ( @@ -45,7 +46,12 @@ const PriceManagerDisplay = ({ }} fullWidth /> - @@ -91,6 +97,8 @@ const PriceManagerContainer = () => { handleSetProduct({ ...product, prices: updatedPrices }); }; + const isAddButtonDisabled = !price.description || !price.cost; + return ( { setPrice={setPrice} handleDeletePrice={handleDeletePrice} handleAddPrice={handleAddPrice} + isAddButtonDisabled={isAddButtonDisabled} /> ); }; -export { PriceManagerContainer as default, PriceManagerDisplay } +export { PriceManagerContainer as default, PriceManagerDisplay } \ No newline at end of file diff --git a/src/pages/Products/ProductDialog/ProductDialogContext.jsx b/src/pages/Products/ProductDialog/ProductDialogContext.jsx index ffe7c53..4a82544 100644 --- a/src/pages/Products/ProductDialog/ProductDialogContext.jsx +++ b/src/pages/Products/ProductDialog/ProductDialogContext.jsx @@ -49,6 +49,7 @@ export const ProductDialogProvider = ({ children }) => { const resetState = () => { setSelectedProduct(null); setIsEditable(false); + setActiveStep(0); setProduct(new Product({})); }; diff --git a/src/pages/Products/ProductDialog/ProviderManager.jsx b/src/pages/Products/ProductDialog/ProviderManager.jsx index 21133ae..f646d55 100644 --- a/src/pages/Products/ProductDialog/ProviderManager.jsx +++ b/src/pages/Products/ProductDialog/ProviderManager.jsx @@ -1,20 +1,232 @@ -import { Typography, Box } from '@mui/material'; +import { useState, useEffect } from 'react'; +import { + Button, Table, TableBody, TableCell, TableHead, TableRow, TextField, IconButton, Typography, Grid, + Modal, Box, Card, CardContent +} from '@mui/material'; +import DeleteIcon from '@mui/icons-material/Delete'; import ExpandableCard from '../../../components/ExpandableCard'; +import CustomSelectWithAdd from '../../../components/CustomSelectWithAdd'; +import { useProductDialogContext } from './ProductDialogContext'; +import { getAll, createProvider } from '../../../services/ProviderService'; +import { useSnackbar } from '../../../components/SnackbarContext'; +import { modifyAndClone } from '../../../util/generalUtils'; +import Provider from '../../../models/Provider'; -const ProviderManager = () => { - // Aquí iría el estado y la lógica para manejar proveedores si fuera necesario - // Por ahora, el componente está preparado pero no implementa funcionalidad específica +const ProviderDetailModal = ({ open, onClose, provider }) => ( + + + + + + Detalles del Proveedor + + + Nombre: {provider?.name} + + + Teléfono: {provider?.phoneNumber} + + + Dirección: {provider?.address} + + + Comentarios: {provider?.comments} + + + + + + +); + +const ProviderManagerDisplay = ({ + product, + providers, + selectedProvider, + price, + handleProviderChange, + handlePriceChange, + handleAddProvider, + handleDeleteProvider, + handleOnProviderAdded, + handleProviderClick, + editable +}) => ( + + + {editable ? 'Añade y gestiona los proveedores del producto.' : ''} + + {editable && ( + <> + + + + + + + + + + + )} + + + + Proveedor + Precio de Compra + {editable && Acciones} + + + + {product.providers && product.providers.map((providerProduct, index) => ( + handleProviderClick(providerProduct.provider)} + sx={{ cursor: 'pointer', '&:hover': { backgroundColor: 'rgba(0, 0, 0, 0.04)' } }} + > + {providerProduct.provider.name} + {providerProduct.price.cost} + {editable && ( + + { + e.stopPropagation(); + handleDeleteProvider(index); + }} + aria-label="delete" + > + + + + )} + + ))} + +
+
+); + +const ProviderManager = ({ editable = true }) => { + const [providers, setProviders] = useState([]); + const [selectedProvider, setSelectedProvider] = useState(null); + const [price, setPrice] = useState(''); + const [modalOpen, setModalOpen] = useState(false); + const [selectedModalProvider, setSelectedModalProvider] = useState(null); + const { openSnackbar } = useSnackbar(); + const { product, handleSetProduct } = useProductDialogContext(); + + useEffect(() => { + const fetchProviders = async () => { + try { + const response = await getAll(); + if (response && response.providers) { + setProviders(response.providers); + } + } catch (error) { + openSnackbar(`Error al obtener los proveedores: ${error.message}`, 'error'); + } + }; + fetchProviders(); + }, []); + + const handleProviderChange = (provider) => { + setSelectedProvider(provider); + }; + + const handlePriceChange = (event) => { + setPrice(event.target.value); + }; + + const handleAddProvider = () => { + if (selectedProvider && price) { + const newProviderProduct = { + providerId: selectedProvider.id, + provider: selectedProvider, + price: { + cost: parseFloat(price), + description: `Precio de compra de ${selectedProvider.name}` + } + }; + handleSetProduct(modifyAndClone(product, 'providers', [...(product.providers || []), newProviderProduct])); + setSelectedProvider(null); + setPrice(''); + } + }; + + const handleDeleteProvider = (index) => { + const newProviders = product.providers.filter((_, i) => i !== index); + handleSetProduct(modifyAndClone(product, 'providers', newProviders)); + }; + + const handleOnProviderAdded = async (providers, newProviderData) => { + try { + const newProvider = await createProvider(new Provider(newProviderData)); + setProviders([...providers, newProvider]); + return newProvider.id; + } catch (error) { + openSnackbar(`Error al crear el proveedor: ${error.message}`, 'error'); + } + }; + + const handleProviderClick = (provider) => { + setSelectedModalProvider(provider); + setModalOpen(true); + }; return ( - - - Añade y gestiona tus proveedores. - - - - {/* Aquí iría la lógica para listar y gestionar proveedores */} - + <> + + setModalOpen(false)} + provider={selectedModalProvider} + /> + ); }; -export default ProviderManager; +export { ProviderManager as default, ProviderManagerDisplay }; \ No newline at end of file diff --git a/src/pages/Products/ProductSummary.jsx b/src/pages/Products/ProductSummary.jsx index f28cfc8..1239b0f 100644 --- a/src/pages/Products/ProductSummary.jsx +++ b/src/pages/Products/ProductSummary.jsx @@ -4,6 +4,7 @@ import { ModelManagerDisplay } from "./ProductDialog/ModelManager"; import { PriceManagerDisplay } from "./ProductDialog/PriceManager"; import ImageUpload from './ProductDialog/ImageUpload'; import { ProductTypes } from './ProductsConstants'; +import ProviderManager from './ProductDialog/ProviderManager'; const ProductSummary = ({ productType, product }) => { let images = product.files.map(file => file.fileData); @@ -44,6 +45,9 @@ const ProductSummary = ({ productType, product }) => { + + +