import AddOutlined from "@mui/icons-material/AddOutlined";
import Alert from "@mui/material/Alert";
import Button from "@mui/material/Button";
import Dialog from "@mui/material/Dialog";
import DialogActions from "@mui/material/DialogActions";
import DialogContent from "@mui/material/DialogContent";
import DialogTitle from "@mui/material/DialogTitle";
import MenuItem from "@mui/material/MenuItem";
import TextField from "@mui/material/TextField";
import { useEffect, useMemo, useRef, useState } from "react";
import { AppIdentity } from "@/shared/ui/AppIdentity.jsx";
import {
    buildCoinSellerRechargeExchangeRatePayload,
    validateCoinSellerRechargeExchangeRatePayload,
} from "../format.js";

const EMPTY_CONFIG = { tiers: [], whitelist: [] };

export function FinanceCoinSellerExchangeRateDialog({ apps, initialAppCode, open, onClose, onLoad, onSave }) {
    const rowSequence = useRef(0);
    const [appCode, setAppCode] = useState("");
    const [config, setConfig] = useState(EMPTY_CONFIG);
    const [error, setError] = useState("");
    const [loading, setLoading] = useState(false);
    const [saving, setSaving] = useState(false);

    useEffect(() => {
        if (open) {
            setAppCode(initialAppCode || apps[0]?.appCode || "");
            setError("");
        }
    }, [apps, initialAppCode, open]);

    useEffect(() => {
        if (!open || !appCode) {
            return undefined;
        }
        let active = true;
        setLoading(true);
        setError("");
        onLoad(appCode)
            .then((data) => {
                if (!active) {
                    return;
                }
                setConfig({
                    tiers: (data?.tiers || []).map((item) => withRowID(item, rowSequence)),
                    whitelist: (data?.whitelist || []).map((item) => withRowID(item, rowSequence)),
                });
            })
            .catch((loadError) => {
                if (active) {
                    setConfig(EMPTY_CONFIG);
                    setError(loadError.message || "加载金币汇率配置失败");
                }
            })
            .finally(() => {
                if (active) {
                    setLoading(false);
                }
            });
        return () => {
            active = false;
        };
    }, [appCode, onLoad, open]);

    const payload = useMemo(() => buildCoinSellerRechargeExchangeRatePayload(config), [config]);

    const submit = async (event) => {
        event.preventDefault();
        const validationMessage = validateCoinSellerRechargeExchangeRatePayload(payload);
        if (validationMessage) {
            setError(validationMessage);
            return;
        }
        setSaving(true);
        setError("");
        try {
            await onSave(appCode, payload);
            onClose();
        } catch (saveError) {
            setError(saveError.message || "保存金币汇率配置失败");
        } finally {
            setSaving(false);
        }
    };

    const updateRow = (group, id, key, value) => {
        setConfig((current) => ({
            ...current,
            [group]: current[group].map((item) => (item.id === id ? { ...item, [key]: value } : item)),
        }));
        setError("");
    };

    const addRow = (group) => {
        const item =
            group === "tiers"
                ? { coinsPerUsd: "", maxUsdAmount: "", minUsdAmount: "" }
                : { coinsPerUsd: "", userId: "" };
        setConfig((current) => ({ ...current, [group]: [...current[group], withRowID(item, rowSequence)] }));
        setError("");
    };

    const removeRow = (group, id) => {
        setConfig((current) => ({ ...current, [group]: current[group].filter((item) => item.id !== id) }));
        setError("");
    };

    const disabled = loading || saving;

    return (
        <Dialog fullWidth maxWidth="md" open={open} onClose={disabled ? undefined : onClose}>
            <DialogTitle>币商充值金币汇率</DialogTitle>
            <DialogContent>
                <form className="finance-rate-config" id="coin-seller-exchange-rate-form" onSubmit={submit}>
                    {error ? <Alert severity="error">{error}</Alert> : null}
                    <TextField
                        disabled={disabled}
                        label="APP"
                        select
                        value={appCode}
                        onChange={(event) => setAppCode(event.target.value)}
                    >
                        {apps.map((app) => (
                            <MenuItem key={app.appCode} value={app.appCode}>
                                <AppIdentity app={app} size="small" />
                            </MenuItem>
                        ))}
                    </TextField>

                    <RateSection
                        actionLabel="添加区间"
                        columns={["最低 USD", "最高 USD", "1 USD 兑换金币"]}
                        disabled={disabled}
                        rows={config.tiers}
                        title="金额区间"
                        onAdd={() => addRow("tiers")}
                        onRemove={(id) => removeRow("tiers", id)}
                        renderRow={(item) => (
                            <>
                                <TextField
                                    disabled={disabled}
                                    slotProps={{ htmlInput: { "aria-label": "最低 USD", min: 0.01, step: "0.01" } }}
                                    type="number"
                                    value={item.minUsdAmount}
                                    onChange={(event) => updateRow("tiers", item.id, "minUsdAmount", event.target.value)}
                                />
                                <TextField
                                    disabled={disabled}
                                    slotProps={{ htmlInput: { "aria-label": "最高 USD", min: 0.01, step: "0.01" } }}
                                    type="number"
                                    value={item.maxUsdAmount}
                                    onChange={(event) => updateRow("tiers", item.id, "maxUsdAmount", event.target.value)}
                                />
                                <TextField
                                    disabled={disabled}
                                    slotProps={{ htmlInput: { "aria-label": "区间金币汇率", min: 1, step: "1" } }}
                                    type="number"
                                    value={item.coinsPerUsd}
                                    onChange={(event) => updateRow("tiers", item.id, "coinsPerUsd", event.target.value)}
                                />
                            </>
                        )}
                    />

                    <RateSection
                        actionLabel="添加白名单"
                        columns={["用户 ID", "1 USD 兑换金币"]}
                        disabled={disabled}
                        rows={config.whitelist}
                        title="用户 ID 白名单"
                        onAdd={() => addRow("whitelist")}
                        onRemove={(id) => removeRow("whitelist", id)}
                        renderRow={(item) => (
                            <>
                                <TextField
                                    disabled={disabled}
                                    slotProps={{ htmlInput: { "aria-label": "白名单用户 ID" } }}
                                    value={item.userId}
                                    onChange={(event) => updateRow("whitelist", item.id, "userId", event.target.value)}
                                />
                                <TextField
                                    disabled={disabled}
                                    slotProps={{ htmlInput: { "aria-label": "白名单金币汇率", min: 1, step: "1" } }}
                                    type="number"
                                    value={item.coinsPerUsd}
                                    onChange={(event) => updateRow("whitelist", item.id, "coinsPerUsd", event.target.value)}
                                />
                            </>
                        )}
                    />
                </form>
            </DialogContent>
            <DialogActions>
                <Button disabled={disabled} variant="outlined" onClick={onClose}>
                    取消
                </Button>
                <Button disabled={disabled || !appCode} form="coin-seller-exchange-rate-form" type="submit" variant="contained">
                    保存
                </Button>
            </DialogActions>
        </Dialog>
    );
}

function RateSection({ actionLabel, columns, disabled, onAdd, onRemove, renderRow, rows, title }) {
    return (
        <section className="finance-rate-config__section">
            <div className="finance-rate-config__heading">
                <h3>{title}</h3>
                <Button disabled={disabled} size="small" startIcon={<AddOutlined fontSize="small" />} onClick={onAdd}>
                    {actionLabel}
                </Button>
            </div>
            <div className="finance-rate-config__table">
                <div className={`finance-rate-config__row finance-rate-config__row--head finance-rate-config__row--${columns.length}`}>
                    {columns.map((column) => (
                        <span key={column}>{column}</span>
                    ))}
                    <span>操作</span>
                </div>
                {rows.length ? (
                    rows.map((item) => (
                        <div
                            className={`finance-rate-config__row finance-rate-config__row--${columns.length}`}
                            key={item.id}
                        >
                            {renderRow(item)}
                            <Button color="error" disabled={disabled} size="small" onClick={() => onRemove(item.id)}>
                                删除
                            </Button>
                        </div>
                    ))
                ) : (
                    <div className="finance-rate-config__empty">当前无数据</div>
                )}
            </div>
        </section>
    );
}

function withRowID(item, rowSequence) {
    rowSequence.current += 1;
    return { ...item, id: `rate-row-${rowSequence.current}` };
}
