import {useLoadingSwitcher} from "../../../hooks/useLoading.jsx";
import {useFetch} from "../../../hooks/useFetch.js";
import {useEffect, useReducer, useState} from "react";
import {FontAwesomeIcon} from "@fortawesome/react-fontawesome";
import {faInfo, faPen} from "@fortawesome/free-solid-svg-icons";
import {AxiosError} from "../../../components/AxiosError.jsx";
import {apiAxios, getSaison, getToastMessage} from "../../../utils/Tools.js";
import {toast} from "react-toastify";
import {ColoredText} from "../../../components/ColoredCircle.jsx";
import {useTranslation} from "react-i18next";

function licenceReducer(licences, action) {
    switch (action.type) {
        case 'REMOVE':
            return licences.filter(licence => licence.id !== action.payload)
        case 'UPDATE_OR_ADD':
            const index = licences.findIndex(licence => licence.id === action.payload.id)
            if (index === -1) {
                return [
                    ...licences,
                    action.payload
                ]
            } else {
                licences[index] = action.payload
                return [...licences]
            }
        case 'SORT':
            return licences.sort((a, b) => b.saison - a.saison)
        default:
            throw new Error()
    }
}

export function LicenceCard({userData}) {
    const defaultLicence = {id: -1, membre: userData.id, validate: false, saison: getSaison(), certificate: false}
    const {t} = useTranslation();

    const setLoading = useLoadingSwitcher()
    const {data, error} = useFetch(`/licence/${userData.id}`, setLoading, 1)
    const [modalLicence, setModal] = useState(defaultLicence)
    const [licences, dispatch] = useReducer(licenceReducer, [])

    useEffect(() => {
        if (!data) return
        for (const dataKey of data) {
            dispatch({type: 'UPDATE_OR_ADD', payload: dataKey})
        }
        dispatch({type: 'SORT'})
    }, [data]);

    return <div className="card mb-4 mb-md-0">
        <div className="card-header container-fluid">
            <div className="row">
                <div className="col">{t('licence')}</div>
                <div className="col" style={{textAlign: 'right'}}>
                    <button className="btn btn-primary btn-sm" data-bs-toggle="modal" data-bs-target="#LicenceModal"
                            onClick={() => setModal(defaultLicence)}
                            disabled={licences.some(licence => licence.saison === getSaison())}>{t('demander')}
                    </button>
                </div>
            </div>
        </div>
        <div className="card-body">
            <ul className="list-group">
                {licences.map((licence, index) => {
                    return <div key={index}
                                className={"list-group-item d-flex justify-content-between align-items-start list-group-item-" +
                                    (licence.validate ? "success" : (licence.certificate?.length > 1 ? "warning" : "danger"))}>
                        <div className="me-auto">{licence?.saison}-{licence?.saison + 1}</div>
                        <button className="badge btn btn-primary rounded-pill" data-bs-toggle="modal"
                                data-bs-target="#LicenceModal" onClick={_ => setModal(licence)}>
                            {licence.saison === getSaison() && !licence.validate ? <FontAwesomeIcon icon={faPen}/> :
                                <FontAwesomeIcon icon={faInfo}/>}</button>
                    </div>
                })}
                {error && <AxiosError error={error}/>}
            </ul>
        </div>

        <div className="modal fade" id="LicenceModal" tabIndex="-1" aria-labelledby="LicenceModalLabel"
             aria-hidden="true">
            <div className="modal-dialog">
                <div className="modal-content">
                    <ModalContent licence={modalLicence} dispatch={dispatch}/>
                </div>
            </div>
        </div>
    </div>;
}

function sendLicence(event, dispatch) {
    event.preventDefault();

    const formData = new FormData(event.target);
    formData.set('certificate', `${event.target.certificateBy?.value}¤${event.target.certificateDate?.value}`)

    toast.promise(
        apiAxios.post(`/licence/club/${formData.get('membre')}`, formData), getToastMessage("membre.toast.licence.ask")
    ).then(data => {
        dispatch({type: 'UPDATE_OR_ADD', payload: data.data})
        dispatch({type: 'SORT'})
    })

}

function removeLicence(id, dispatch) {
    toast.promise(
        apiAxios.delete(`/licence/club/${id}`), getToastMessage("membre.toast.licence.ask.del")
    ).then(_ => {
        dispatch({type: 'REMOVE', payload: id})
    })
}

function ModalContent({licence, dispatch}) {
    const [certificateBy, setCertificateBy] = useState("")
    const [certificateDate, setCertificateDate] = useState("")
    const [isNew, setNew] = useState(true)
    const {t} = useTranslation();

    const handleCertificateByChange = (event) => {
        setCertificateBy(event.target.value.replaceAll('¤', ''));
    }
    const handleCertificateDateChange = (event) => {
        setCertificateDate(event.target.value.replaceAll('¤', ''));
    }

    useEffect(() => {
        if (licence.id !== -1) {
            setNew(false)
            if (licence.certificate === null) {
                setCertificateBy("")
                setCertificateDate("")
            } else {
                setCertificateBy(licence.certificate.split('¤')[0])
                setCertificateDate(licence.certificate.split('¤')[1])
            }
        } else {
            setNew(true)
            setCertificateBy("")
            setCertificateDate("")
        }
    }, [licence]);

    const currentSaison = licence.saison === getSaison();

    return <form onSubmit={e => sendLicence(e, dispatch)}>
        <input name="id" value={licence.id} readOnly hidden/>
        <input name="membre" value={licence.membre} readOnly hidden/>
        <div className="modal-header">
            <h1 className="modal-title fs-5" id="LicenceModalLabel">
                {isNew ? t('demandeDeLicence') : t('editionDeLaDemande')}
                ({t('saison')} {licence.saison}-{licence.saison + 1})</h1>
            <button type="button" className="btn-close" data-bs-dismiss="modal"
                    aria-label="Close"></button>
        </div>
        <div className="modal-body">
            <span>{t('certificatMédical')}</span>
            <div className="input-group mb-3 ">
                <span className="input-group-text" id="basic-addon2">{t('faitPar')}</span>
                <input type="text" className="form-control" placeholder={t('faitPar')} name="certificateBy" disabled={licence.validate}
                       aria-label={t('faitPar')} aria-describedby="basic-addon2" value={certificateBy} onChange={handleCertificateByChange}/>
                <span className="input-group-text" id="basic-addon2">, {t('le')}</span>
                <input type="date" className="form-control" placeholder="jj/mm/aaaa" name="certificateDate" disabled={licence.validate}
                       aria-describedby="basic-addon2" value={certificateDate} onChange={handleCertificateDateChange}/>
            </div>

            <div className="input-group mb-3 justify-content-md-center">
                <div>{t('paiementDeLaLicence')}: <ColoredText boolean={licence.pay}/></div>
            </div>
            <div className="input-group mb-3 justify-content-md-center">
                <div>{t('validationDeLaLicence')}: <ColoredText boolean={licence.validate}/></div>
            </div>
        </div>
        <div className="modal-footer">
            {currentSaison && !licence.validate &&
                <button type="submit" className="btn btn-primary" data-bs-dismiss="modal">{t('button.enregistrer')}</button>}
            <button type="button" className="btn btn-secondary" data-bs-dismiss="modal">{t('button.fermer')}</button>
            {currentSaison && !licence.validate && licence.id !== -1 && !licence.pay &&
                <button type="button" className="btn btn-danger" data-bs-dismiss="modal"
                        onClick={() => removeLicence(licence.id, dispatch)}>{t('button.annuler')}</button>}
        </div>
    </form>
}
