import {isLoginRequiredError} from '@_api/apiClient';
import {fetchSidoList, fetchSigunguList} from '@_api/region/regionAPI';
import type {SidoResponse, SigunguResponse} from '@_api/region/regionTypes';
import {createStore, deleteStore, getStoreDetail, getStores, updateStore} from '@_api/store/storeAPI';
import {
    type SimpleStoreResponse,
    type StoreDetailResponse,
    type StoreRegisterRequest,
    type UpdateStoreRequest
} from '@_api/store/storeTypes';
import {useAdminAuth} from '@_context/AdminAuthContext';
import '@_css/admin-store-page.css';
import {formatDisplayDateTime} from '@_util/DateTimeFormatter';
import React, {Fragment, useEffect, useState} from 'react';
import {useLocation, useNavigate} from 'react-router-dom';

const AdminStorePage: React.FC = () => {
    const [stores, setStores] = useState<SimpleStoreResponse[]>([]);
    const [isAdding, setIsAdding] = useState(false);
    const [newStore, setNewStore] = useState<StoreRegisterRequest>({
        name: '',
        address: '',
        contact: '',
        businessRegNum: '',
        regionCode: ''
    });

    const [expandedStoreId, setExpandedStoreId] = useState<string | null>(null);
    const [detailedStores, setDetailedStores] = useState<{ [key: string]: StoreDetailResponse }>({});
    const [isLoadingDetails, setIsLoadingDetails] = useState<boolean>(false);
    const [isEditing, setIsEditing] = useState(false);
    const [editingStore, setEditingStore] = useState<UpdateStoreRequest | null>(null);

    const [sidoList, setSidoList] = useState<SidoResponse[]>([]);
    const [sigunguList, setSigunguList] = useState<SigunguResponse[]>([]);
    const [selectedSido, setSelectedSido] = useState('');
    const [selectedSigungu, setSelectedSigungu] = useState('');

    const navigate = useNavigate();
    const location = useLocation();
    const { type: adminType } = useAdminAuth();

    const handleError = (err: any) => {
        if (isLoginRequiredError(err)) {
            alert('로그인이 필요합니다.');
            navigate('/admin/login', { state: { from: location } });
        } else {
            const message = err.response?.data?.message || '알 수 없는 오류가 발생했습니다.';
            alert(message);
            console.error(err);
        }
    };

    const fetchStores = async () => {
        try {
            const storesData = (await getStores(selectedSido || undefined, selectedSigungu || undefined)).stores;
            setStores(storesData);
        } catch (error) {
            handleError(error);
        };
    }

    useEffect(() => {
        if (adminType !== 'HQ') {
            alert('접근 권한이 없습니다.');
            navigate('/admin');
            return;
        }

        const fetchInitialData = async () => {
            try {
                const sidoRes = await fetchSidoList();
                setSidoList(sidoRes.sidoList);
            } catch (error) {
                handleError(error);
            }
        };

        fetchInitialData();
    }, [adminType, navigate]);

    useEffect(() => {
        const fetchSigungu = async () => {
            if (selectedSido) {
                try {
                    const sigunguRes = await fetchSigunguList(selectedSido);
                    setSigunguList(sigunguRes.sigunguList);
                } catch (error) {
                    handleError(error);
                }
            } else {
                setSigunguList([]);
            }
            setSelectedSigungu('');
        };
        fetchSigungu();
    }, [selectedSido]);

    useEffect(() => { fetchStores();}, [selectedSido, selectedSigungu]);

    const handleInputChange = (e: React.ChangeEvent<HTMLInputElement>) => {
        const { name, value } = e.target;
        setNewStore(prev => ({ ...prev, [name]: value }));
    };

    const handleAddStore = async () => {
        if (Object.values(newStore).some(val => val === '')) {
            alert('모든 필드를 입력해주세요.');
            return;
        }
        try {
            await createStore(newStore);
            const storesData = (await getStores(selectedSido || undefined, selectedSigungu || undefined)).stores;
            setStores(storesData);
            setIsAdding(false);
            setNewStore({ name: '', address: '', contact: '', businessRegNum: '', regionCode: '' });
        } catch (error) {
            handleError(error);
        }
    };

    const handleToggleDetails = async (storeId: string) => {
        const isAlreadyExpanded = expandedStoreId === storeId;
        setIsEditing(false);
        if (isAlreadyExpanded) {
            setExpandedStoreId(null);
        } else {
            setExpandedStoreId(storeId);
            if (!detailedStores[storeId]) {
                setIsLoadingDetails(true);
                try {
                    const details = await getStoreDetail(storeId);
                    setDetailedStores(prev => ({ ...prev, [storeId]: details }));
                } catch (error) {
                    handleError(error);
                } finally {
                    setIsLoadingDetails(false);
                }
            }
        }
    };

    const handleDeleteStore = async (storeId: string) => {
        if (window.confirm('정말 이 매장을 삭제하시겠습니까? 관련 데이터가 모두 삭제될 수 있습니다.')) {
            try {
                await deleteStore(storeId);
                fetchStores();
                setExpandedStoreId(null);
            } catch (error) {
                handleError(error);
            }
        }
    };

    const handleEditClick = (store: StoreDetailResponse) => {
        setEditingStore({ name: store.name, address: store.address, contact: store.contact });
        setIsEditing(true);
    };

    const handleCancelEdit = () => {
        setIsEditing(false);
        setEditingStore(null);
    };

    const handleEditChange = (e: React.ChangeEvent<HTMLInputElement>) => {
        const { name, value } = e.target;
        if (editingStore) {
            setEditingStore(prev => ({ ...prev!, [name]: value }));
        }
    };

    const handleSave = async (storeId: string) => {
        if (!editingStore) return;
        try {
            await updateStore(storeId, editingStore);
            const updatedStore = await getStoreDetail(storeId);
            setDetailedStores(prev => ({ ...prev, [storeId]: updatedStore }));
            setStores(prev => prev.map(s => s.id === String(storeId) ? { ...s, name: updatedStore.name } : s));
            setIsEditing(false);
            setEditingStore(null);
            alert('매장 정보가 성공적으로 업데이트되었습니다.');
        } catch (error) {
            handleError(error);
        }
    };

    return (
        <div className="admin-store-container">
            <h2 className="page-title">매장 관리</h2>

            <div className="filter-controls">
                <div className="form-group">
                    <label className="form-label">시/도</label>
                    <select className="form-select" value={selectedSido} onChange={e => setSelectedSido(e.target.value)}>
                        <option value="">전체</option>
                        {sidoList.map(s => <option key={s.code} value={s.code}>{s.name}</option>)}
                    </select>
                </div>
                <div className="form-group">
                    <label className="form-label">시/군/구</label>
                    <select className="form-select" value={selectedSigungu} onChange={e => setSelectedSigungu(e.target.value)} disabled={!selectedSido}>
                        <option value="">전체</option>
                        {sigunguList.map(s => <option key={s.code} value={s.code}>{s.name}</option>)}
                    </select>
                </div>
            </div>

            <div className="section-card">
                <div className="table-header">
                    <button className="btn btn-primary" onClick={() => setIsAdding(!isAdding)}>
                        {isAdding ? '취소' : '매장 추가'}
                    </button>
                </div>

                {isAdding && (
                    <div className="add-store-form">
                        <div className="form-row">
                            <div className="form-group"><label className="form-label">매장명</label><input type="text"
                                name="name"
                                className="form-input"
                                value={newStore.name}
                                onChange={handleInputChange} />
                            </div>
                            <div className="form-group"><label className="form-label">주소</label><input type="text"
                                name="address"
                                className="form-input"
                                value={newStore.address}
                                onChange={handleInputChange} />
                            </div>
                        </div>
                        <div className="form-row">
                            <div className="form-group"><label className="form-label">연락처</label><input type="text"
                                name="contact"
                                className="form-input"
                                value={newStore.contact}
                                onChange={handleInputChange} />
                            </div>
                            <div className="form-group"><label className="form-label">사업자등록번호</label><input type="text"
                                name="businessRegNum"
                                className="form-input"
                                value={newStore.businessRegNum}
                                onChange={handleInputChange} />
                            </div>
                            <div className="form-group"><label className="form-label">지역 코드</label><input type="text"
                                name="regionCode"
                                className="form-input"
                                value={newStore.regionCode}
                                onChange={handleInputChange} />
                            </div>
                        </div>
                        <div className="button-group">
                            <button className="btn btn-primary" onClick={handleAddStore}>저장</button>
                        </div>
                    </div>
                )}

                <div className="table-container">
                    <table>
                        <thead>
                            <tr>
                                <th>ID</th>
                                <th>매장명</th>
                                <th>관리</th>
                            </tr>
                        </thead>
                        <tbody>
                            {stores.map(store => (
                                <Fragment key={store.id}>
                                    <tr>
                                        <td>{store.id}</td>
                                        <td>{store.name}</td>
                                        <td className="action-buttons">
                                            <button className="btn btn-secondary"
                                                onClick={() => handleToggleDetails(store.id)}>
                                                {expandedStoreId === store.id ? '닫기' : '상세'}
                                            </button>
                                        </td>
                                    </tr>
                                    {expandedStoreId === store.id && (
                                        <tr className="details-row">
                                            <td colSpan={3}>
                                                <div className="details-container">
                                                    {isLoadingDetails ? <p>로딩 중...</p> : detailedStores[store.id] ? (
                                                        <div>
                                                            <div className="audit-info">
                                                                <h4 className="audit-title">상세 정보</h4>
                                                                <div className="audit-body">
                                                                    <p>
                                                                        <strong>주소:</strong> {detailedStores[store.id].address}
                                                                    </p>
                                                                    <p>
                                                                        <strong>연락처:</strong> {detailedStores[store.id].contact}
                                                                    </p>
                                                                    <p>
                                                                        <strong>사업자등록번호:</strong> {detailedStores[store.id].businessRegNum}
                                                                    </p>
                                                                    <p><strong>지역
                                                                        코드:</strong> {detailedStores[store.id].region.code}
                                                                    </p>
                                                                    <p>
                                                                        <strong>생성일:</strong> {formatDisplayDateTime(detailedStores[store.id].audit.createdAt)}
                                                                    </p>
                                                                    <p>
                                                                        <strong>수정일:</strong> {formatDisplayDateTime(detailedStores[store.id].audit.updatedAt)}
                                                                    </p>
                                                                    <p>
                                                                        <strong>생성자:</strong> {detailedStores[store.id].audit.createdBy.name}({detailedStores[store.id].audit.createdBy.id})
                                                                    </p>
                                                                    <p>
                                                                        <strong>수정자:</strong> {detailedStores[store.id].audit.updatedBy.name}({detailedStores[store.id].audit.updatedBy.id})
                                                                    </p>
                                                                </div>
                                                            </div>

                                                            {isEditing && editingStore ? (
                                                                <div className="details-form-card">
                                                                    <div className="form-row">
                                                                        <div className="form-group"><label
                                                                            className="form-label">매장명</label><input
                                                                                type="text" name="name" className="form-input"
                                                                                value={editingStore.name}
                                                                                onChange={handleEditChange} /></div>
                                                                        <div className="form-group"><label
                                                                            className="form-label">주소</label><input
                                                                                type="text" name="address"
                                                                                className="form-input"
                                                                                value={editingStore.address}
                                                                                onChange={handleEditChange} /></div>
                                                                        <div className="form-group"><label
                                                                            className="form-label">연락처</label><input
                                                                                type="text" name="contact"
                                                                                className="form-input"
                                                                                value={editingStore.contact}
                                                                                onChange={handleEditChange} /></div>
                                                                    </div>
                                                                    <div className="button-group">
                                                                        <button className="btn btn-secondary"
                                                                            onClick={handleCancelEdit}>취소
                                                                        </button>
                                                                        <button className="btn btn-primary"
                                                                            onClick={() => handleSave(store.id)}>저장
                                                                        </button>
                                                                    </div>
                                                                </div>
                                                            ) : (
                                                                <div className="button-group">
                                                                    <button className="btn btn-danger"
                                                                        onClick={() => handleDeleteStore(store.id)}>삭제
                                                                    </button>
                                                                    <button className="btn btn-primary"
                                                                        onClick={() => handleEditClick(detailedStores[store.id])}>수정
                                                                    </button>
                                                                </div>
                                                            )}
                                                        </div>
                                                    ) : <p>상세 정보를 불러올 수 없습니다.</p>}
                                                </div>
                                            </td>
                                        </tr>
                                    )}
                                </Fragment>
                            ))}
                        </tbody>
                    </table>
                </div>
            </div>
        </div>
    );
};

export default AdminStorePage;