mirror of
https://git.v0id.ovh/n3wt-innov/n3wt-school.git
synced 2026-01-29 07:53:23 +00:00
fix: Remplacement des enum par des modèles pour les payementModes et les
payementPlans
This commit is contained in:
@ -1,281 +1,62 @@
|
||||
import React, { useState, useEffect } from 'react';
|
||||
import { Calendar, Eye, EyeOff, Clock, Check } from 'lucide-react';
|
||||
import { Calendar } from 'lucide-react';
|
||||
import Table from '@/components/Table';
|
||||
import DateTab from '@/components/DateTab';
|
||||
import InputTextIcon from '@/components/InputTextIcon';
|
||||
import Popup from '@/components/Popup';
|
||||
import logger from '@/utils/logger';
|
||||
import { useEstablishment } from '@/context/EstablishmentContext';
|
||||
import CheckBox from '@/components/CheckBox';
|
||||
|
||||
const paymentPlansOptions = [
|
||||
{ id: 0, name: '1 fois', frequency: 1 },
|
||||
{ id: 1, name: '3 fois', frequency: 3 },
|
||||
{ id: 2, name: '10 fois', frequency: 10 },
|
||||
{ id: 3, name: '12 fois', frequency: 12 },
|
||||
{ id: 1, name: '1 fois', frequency: 1 },
|
||||
{ id: 2, name: '3 fois', frequency: 3 },
|
||||
{ id: 3, name: '10 fois', frequency: 10 },
|
||||
{ id: 4, name: '12 fois', frequency: 12 },
|
||||
];
|
||||
|
||||
const PaymentPlanSelector = ({
|
||||
paymentPlans,
|
||||
setPaymentPlans,
|
||||
handleEdit,
|
||||
handleCreate,
|
||||
handleDelete,
|
||||
type,
|
||||
}) => {
|
||||
const [dates, setDates] = useState({});
|
||||
const [selectedFrequency, setSelectedFrequency] = useState(null);
|
||||
const [activeFrequencies, setActiveFrequencies] = useState([]);
|
||||
const [defaultDay, setDefaultDay] = useState('-');
|
||||
const [isDefaultDayModified, setIsDefaultDayModified] = useState(false);
|
||||
const [popupVisible, setPopupVisible] = useState(false);
|
||||
const [popupMessage, setPopupMessage] = useState('');
|
||||
const [errorMsg, setErrorMsg] = useState('');
|
||||
const [resetModifiedDates, setResetModifiedDates] = useState(false);
|
||||
const { selectedEstablishmentId } = useEstablishment();
|
||||
const [checkedPlans, setCheckedPlans] = useState([]);
|
||||
|
||||
// Vérifie si un plan existe pour ce type (par id)
|
||||
const isChecked = (planOption) => checkedPlans.includes(planOption.id);
|
||||
|
||||
// Création ou suppression du plan
|
||||
const handlePlanToggle = (planOption) => {
|
||||
const updatedPlan = paymentPlans.find(
|
||||
(plan) => plan.plan_type === planOption.id
|
||||
);
|
||||
if (isChecked(planOption)) {
|
||||
setCheckedPlans((prev) => prev.filter((id) => id !== planOption.id));
|
||||
handleDelete(updatedPlan.id, null);
|
||||
} else {
|
||||
setCheckedPlans((prev) => [...prev, planOption.id]);
|
||||
handleCreate({
|
||||
plan_type: planOption.id,
|
||||
type,
|
||||
establishment: selectedEstablishmentId,
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
if (paymentPlans && paymentPlans.length > 0) {
|
||||
const activePlans = paymentPlans.filter((plan) => plan.is_active);
|
||||
const frequencies = activePlans
|
||||
.map((plan) => {
|
||||
const paymentPlanOption = paymentPlansOptions.find(
|
||||
(p) => p.frequency === plan.frequency
|
||||
);
|
||||
return paymentPlanOption ? paymentPlanOption.id : null;
|
||||
})
|
||||
.filter((id) => id !== null);
|
||||
setActiveFrequencies(frequencies);
|
||||
|
||||
if (activePlans.length > 0) {
|
||||
const firstDueDate = new Date(activePlans[0].due_dates[0]);
|
||||
setDefaultDay(firstDueDate.getDate());
|
||||
}
|
||||
|
||||
const initialDates = {};
|
||||
paymentPlans.forEach((plan) => {
|
||||
const paymentPlanOption = paymentPlansOptions.find(
|
||||
(p) => p.frequency === plan.frequency
|
||||
);
|
||||
if (paymentPlanOption) {
|
||||
initialDates[paymentPlanOption.id] = plan.due_dates;
|
||||
}
|
||||
});
|
||||
setDates(initialDates);
|
||||
setCheckedPlans(
|
||||
paymentPlans.map((plan) =>
|
||||
typeof plan.plan_type === 'object'
|
||||
? plan.plan_type.id
|
||||
: plan.plan_type
|
||||
)
|
||||
);
|
||||
}
|
||||
}, [paymentPlans]);
|
||||
|
||||
useEffect(() => {
|
||||
updateDefaultDay();
|
||||
}, [dates, selectedFrequency]);
|
||||
|
||||
const updateDefaultDay = () => {
|
||||
const currentDates = dates[selectedFrequency];
|
||||
if (currentDates && currentDates.length > 0) {
|
||||
const days = currentDates.map((date) => new Date(date).getDate());
|
||||
const allSameDay = days.every((day) => day === days[0]);
|
||||
if (allSameDay) {
|
||||
setDefaultDay(days[0]);
|
||||
} else {
|
||||
setDefaultDay('-');
|
||||
setIsDefaultDayModified(false);
|
||||
}
|
||||
} else {
|
||||
setDefaultDay('-');
|
||||
}
|
||||
};
|
||||
|
||||
const handleActivationChange = (value) => {
|
||||
const selectedPlan = paymentPlans.find(
|
||||
(plan) =>
|
||||
plan.frequency ===
|
||||
paymentPlansOptions.find((p) => p.id === value)?.frequency
|
||||
);
|
||||
if (!selectedPlan) return;
|
||||
|
||||
const updatedData = {
|
||||
...selectedPlan,
|
||||
is_active: !selectedPlan.is_active,
|
||||
};
|
||||
|
||||
handleEdit(selectedPlan.id, updatedData)
|
||||
.then(() => {
|
||||
setPaymentPlans((prevPlans) =>
|
||||
prevPlans.map((plan) =>
|
||||
plan.id === selectedPlan.id
|
||||
? { ...plan, is_active: updatedData.is_active }
|
||||
: plan
|
||||
)
|
||||
);
|
||||
setActiveFrequencies((prevFrequencies) => {
|
||||
if (updatedData.is_active) {
|
||||
setPopupMessage(
|
||||
`L'option de paiement en ${paymentPlansOptions.find((p) => p.id === value).name} a été activée.`
|
||||
);
|
||||
setPopupVisible(true);
|
||||
return [...prevFrequencies, value];
|
||||
} else {
|
||||
setPopupMessage(
|
||||
`L'option de paiement en ${paymentPlansOptions.find((p) => p.id === value).name} a été désactivée.`
|
||||
);
|
||||
setPopupVisible(true);
|
||||
return prevFrequencies.filter((item) => item !== value);
|
||||
}
|
||||
});
|
||||
})
|
||||
.catch((error) => {
|
||||
logger.error(error);
|
||||
});
|
||||
};
|
||||
|
||||
const handleRowClick = (row) => {
|
||||
const value = row.id;
|
||||
|
||||
if (selectedFrequency === value) {
|
||||
setSelectedFrequency(null); // Désélectionner l'onglet si la ligne est déjà sélectionnée
|
||||
} else {
|
||||
setSelectedFrequency(value);
|
||||
|
||||
if (!dates[value]) {
|
||||
const frequencyValue =
|
||||
paymentPlansOptions.find((plan) => plan.id === value)?.frequency || 1;
|
||||
|
||||
const newDates = Array(frequencyValue)
|
||||
.fill('')
|
||||
.map((_, index) => {
|
||||
const newDate = new Date();
|
||||
|
||||
// Validate defaultDay
|
||||
const day =
|
||||
typeof defaultDay === 'number' &&
|
||||
defaultDay >= 1 &&
|
||||
defaultDay <= 31
|
||||
? defaultDay
|
||||
: 1; // Fallback to 1 if defaultDay is invalid
|
||||
|
||||
newDate.setDate(day);
|
||||
|
||||
if (value === 1) {
|
||||
newDate.setMonth(newDate.getMonth() + index * 4); // Espacer de 4 mois pour le paiement en 3 fois
|
||||
} else {
|
||||
newDate.setMonth(newDate.getMonth() + index);
|
||||
}
|
||||
|
||||
return newDate.toISOString().split('T')[0];
|
||||
});
|
||||
|
||||
setDates((prevDates) => ({ ...prevDates, [value]: newDates }));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const handleDateChange = (planId, index, date) => {
|
||||
setDates((prevDates) => {
|
||||
const newDates = { ...prevDates };
|
||||
newDates[planId][index] = date;
|
||||
return newDates;
|
||||
});
|
||||
};
|
||||
|
||||
const handleDefaultDayChange = (e) => {
|
||||
const value = e.target.value;
|
||||
if (value === '') {
|
||||
setDefaultDay('-');
|
||||
setErrorMsg('');
|
||||
setIsDefaultDayModified(false);
|
||||
return;
|
||||
}
|
||||
|
||||
const day = parseInt(value, 10);
|
||||
setDefaultDay(day);
|
||||
|
||||
if (day < 1 || day > 31) {
|
||||
setErrorMsg('Le jour doit être compris entre 1 et 31.');
|
||||
setIsDefaultDayModified(false);
|
||||
return;
|
||||
}
|
||||
|
||||
setErrorMsg('');
|
||||
setIsDefaultDayModified(true);
|
||||
setResetModifiedDates(true);
|
||||
setTimeout(() => setResetModifiedDates(false), 0);
|
||||
|
||||
// Mettre à jour les dates d'échéance en fonction du jour sélectionné
|
||||
const updatedDates = dates[selectedFrequency].map((date) => {
|
||||
const newDate = new Date(date);
|
||||
newDate.setDate(day);
|
||||
return newDate.toISOString().split('T')[0];
|
||||
});
|
||||
setDates((prevDates) => ({
|
||||
...prevDates,
|
||||
[selectedFrequency]: updatedDates,
|
||||
}));
|
||||
};
|
||||
|
||||
const handleSubmitDefaultDay = () => {
|
||||
const selectedPlan = paymentPlans.find(
|
||||
(plan) =>
|
||||
plan.frequency ===
|
||||
paymentPlansOptions.find((p) => p.id === selectedFrequency)?.frequency
|
||||
);
|
||||
if (!selectedPlan) return;
|
||||
|
||||
const updatedData = {
|
||||
...selectedPlan,
|
||||
due_dates: dates[selectedFrequency],
|
||||
};
|
||||
|
||||
handleEdit(selectedPlan.id, updatedData)
|
||||
.then(() => {
|
||||
setPopupMessage(
|
||||
"Mise à jour des dates d'échéances effectuée avec succès"
|
||||
);
|
||||
setPopupVisible(true);
|
||||
setIsDefaultDayModified(false);
|
||||
})
|
||||
.catch((error) => {
|
||||
logger.error(error);
|
||||
});
|
||||
};
|
||||
|
||||
const columns = [
|
||||
{ name: 'OPTIONS', label: 'Option' },
|
||||
{ name: 'ACTIONS', label: 'Action' },
|
||||
];
|
||||
|
||||
const renderCell = (row, column) => {
|
||||
switch (column) {
|
||||
case 'OPTIONS':
|
||||
return (
|
||||
<span className="text-sm font-medium text-gray-900">{row.name}</span>
|
||||
);
|
||||
case 'ACTIONS':
|
||||
return (
|
||||
<button
|
||||
type="button"
|
||||
onClick={(e) => {
|
||||
e.stopPropagation();
|
||||
handleActivationChange(row.id);
|
||||
}}
|
||||
className={
|
||||
activeFrequencies.includes(row.id)
|
||||
? 'text-emerald-500 hover:text-emerald-700'
|
||||
: 'text-orange-500 hover:text-orange-700'
|
||||
}
|
||||
>
|
||||
{activeFrequencies.includes(row.id) ? (
|
||||
<Eye className="w-5 h-5" />
|
||||
) : (
|
||||
<EyeOff className="w-5 h-5" />
|
||||
)}
|
||||
</button>
|
||||
);
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
const selectedPaymentPlan = paymentPlans.find(
|
||||
(plan) =>
|
||||
plan.frequency ===
|
||||
paymentPlansOptions.find((p) => p.id === selectedFrequency)?.frequency
|
||||
);
|
||||
|
||||
return (
|
||||
<div className="space-y-4">
|
||||
<div className="flex items-center mb-4">
|
||||
@ -285,49 +66,34 @@ const PaymentPlanSelector = ({
|
||||
<div className="grid grid-cols-2 gap-4">
|
||||
<Table
|
||||
data={paymentPlansOptions}
|
||||
columns={columns}
|
||||
renderCell={renderCell}
|
||||
isSelectable={true}
|
||||
onRowClick={handleRowClick}
|
||||
selectedRows={selectedFrequency !== null ? [selectedFrequency] : []}
|
||||
columns={[
|
||||
{ name: 'OPTION', label: 'Option' },
|
||||
{ name: 'ACTIF', label: 'Actif' },
|
||||
]}
|
||||
renderCell={(row, column) => {
|
||||
switch (column) {
|
||||
case 'OPTION':
|
||||
return (
|
||||
<span className="text-sm font-medium text-gray-900">
|
||||
{row.name}
|
||||
</span>
|
||||
);
|
||||
case 'ACTIF':
|
||||
return (
|
||||
<CheckBox
|
||||
item={{ id: row.id }}
|
||||
formData={{ checked: isChecked(row) }}
|
||||
handleChange={() => handlePlanToggle(row)}
|
||||
fieldName="checked"
|
||||
itemLabelFunc={() => ''}
|
||||
horizontal={true}
|
||||
/>
|
||||
);
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
}}
|
||||
/>
|
||||
{selectedFrequency !== null && selectedPaymentPlan && (
|
||||
<div>
|
||||
<div className="flex items-center space-x-3">
|
||||
<div className="flex-grow">
|
||||
<InputTextIcon
|
||||
name="defaultDay"
|
||||
type="number"
|
||||
IconItem={Clock}
|
||||
label="Jour d'échéance"
|
||||
value={defaultDay}
|
||||
onChange={handleDefaultDayChange}
|
||||
placeholder="Jour d'échéance"
|
||||
errorMsg={errorMsg}
|
||||
/>
|
||||
</div>
|
||||
{isDefaultDayModified && defaultDay && (
|
||||
<button
|
||||
type="button"
|
||||
onClick={handleSubmitDefaultDay}
|
||||
className="text-emerald-500 hover:text-emerald-700 ml-2 cursor-pointer"
|
||||
style={{ marginTop: errorMsg ? '3.5rem' : '1.75rem' }}
|
||||
>
|
||||
<Check className="w-5 h-5" />
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
<DateTab
|
||||
dates={dates}
|
||||
activeTab={selectedFrequency}
|
||||
handleDateChange={handleDateChange}
|
||||
handleEdit={handleEdit}
|
||||
type={type}
|
||||
paymentPlanId={selectedPaymentPlan.id}
|
||||
resetModifiedDates={resetModifiedDates}
|
||||
/>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
<Popup
|
||||
isOpen={popupVisible}
|
||||
|
||||
Reference in New Issue
Block a user