/* eslint-disable react/no-unstable-nested-components */
import { useLocaleContext } from '@arcblock/ux/lib/Locale/context';
import Toast from '@arcblock/ux/lib/Toast';
import {
  TxLink,
  api,
  formatError,
  formatTime,
  useMobile,
  hasDelegateTxHash,
  CreditGrantsList,
  CreditTransactionsList,
} from '@blocklet/payment-react';
import type { TProduct, TSubscriptionExpanded } from '@blocklet/payment-types';
import { ArrowBackOutlined } from '@mui/icons-material';
import { Alert, Box, Button, CircularProgress, Divider, Stack, Typography } from '@mui/material';
import { styled } from '@mui/system';
import { useRequest, useSetState } from 'ahooks';
import { Link } from 'react-router-dom';

import Copyable from '../../../../components/copyable';
import Currency from '../../../../components/currency';
import CustomerLink from '../../../../components/customer/link';
import EventList from '../../../../components/event/list';
import InfoRow from '../../../../components/info-row';
import InvoiceList from '../../../../components/invoice/list';
import MetadataEditor from '../../../../components/metadata/editor';
import MetadataList from '../../../../components/metadata/list';
import RefundList from '../../../../components/refund/list';
import SectionHeader from '../../../../components/section/header';
import SubscriptionActions from '../../../../components/subscription/actions';
import SubscriptionItemList from '../../../../components/subscription/items';
import SubscriptionMetrics from '../../../../components/subscription/metrics';
import DiscountInfo from '../../../../components/discount/discount-info';
import { goBackOrFallback } from '../../../../libs/util';
import InfoRowGroup from '../../../../components/info-row-group';
import VendorServiceList from '../../../../components/subscription/vendor-service-list';
import { useSessionContext } from '../../../../contexts/session';
import PaymentMethodInfo from '../../../../components/subscription/payment-method-info';

const fetchData = (id: string): Promise<TSubscriptionExpanded> => {
  return api.get(`/api/subscriptions/${id}`).then((res: any) => res.data);
};

export default function SubscriptionDetail(props: { id: string }) {
  const { t } = useLocaleContext();
  const { session } = useSessionContext();
  const { isMobile } = useMobile();
  const [state, setState] = useSetState({
    adding: {
      price: false,
    },
    editing: {
      metadata: false,
      product: false,
    },
    loading: {
      metadata: false,
      price: false,
      product: false,
    },
  });

  const { loading, error, data, runAsync } = useRequest(() => fetchData(props.id));

  if (error) {
    return <Alert severity="error">{error.message}</Alert>;
  }

  if (loading || !data) {
    return <CircularProgress />;
  }

  const createUpdater = (key: string) => async (updates: TProduct) => {
    try {
      setState((prev) => ({ loading: { ...prev.loading, [key]: true } }));
      await api.put(`/api/subscriptions/${props.id}`, updates).then((res: any) => res.data);
      Toast.success(t('common.saved'));
      runAsync();
    } catch (err) {
      console.error(err);
      Toast.error(formatError(err));
    } finally {
      setState((prev) => ({ loading: { ...prev.loading, [key]: false } }));
    }
  };

  const onUpdateMetadata = createUpdater('metadata');
  const handleEditMetadata = () => {
    setState((prev) => ({ editing: { ...prev.editing, metadata: true } }));
  };

  const isCredit =
    data?.serviceType === 'credit' ||
    data?.paymentCurrency?.type === 'credit' ||
    data?.items?.some((item) => item?.price?.product?.type === 'credit' || item?.price?.metadata?.credit_config);

  return (
    <Root direction="column" spacing={2.5} sx={{ mb: 4 }}>
      <Box>
        <Stack
          className="page-header"
          direction="row"
          sx={{
            justifyContent: 'space-between',
            alignItems: 'center',
          }}>
          <Stack
            direction="row"
            onClick={() => goBackOrFallback('/admin/billing/subscriptions')}
            sx={{
              alignItems: 'center',
              fontWeight: 'normal',
              cursor: 'pointer',
            }}>
            <ArrowBackOutlined fontSize="small" sx={{ mr: 0.5, color: 'text.secondary' }} />
            <Typography variant="h6" sx={{ color: 'text.secondary', fontWeight: 'normal' }}>
              {t('admin.subscriptions')}
            </Typography>
          </Stack>
          <SubscriptionActions data={data} onChange={runAsync} variant="normal" />
        </Stack>
        <Box
          sx={{
            mt: 4,
            mb: 3,
            display: 'flex',

            gap: {
              xs: 2,
              sm: 2,
              md: 5,
            },

            flexWrap: 'wrap',

            flexDirection: {
              xs: 'column',
              sm: 'column',
              md: 'row',
            },

            alignItems: {
              xs: 'flex-start',
              sm: 'flex-start',
              md: 'center',
            },
          }}>
          <Stack
            direction="column"
            sx={{
              gap: 1,
            }}>
            <Stack
              direction="row"
              sx={{
                alignItems: 'center',
              }}>
              <Typography variant="h2" sx={{ fontWeight: 600 }}>
                {data.description}
              </Typography>
            </Stack>
            <Copyable text={props.id} />
          </Stack>
          <Stack
            className="section-body"
            sx={{
              justifyContent: 'flex-start',
              flexWrap: 'wrap',

              'hr.MuiDivider-root:last-child': {
                display: 'none',
              },

              flexDirection: {
                xs: 'column',
                sm: 'column',
                md: 'row',
              },

              alignItems: 'flex-start',

              gap: {
                xs: 1,
                sm: 1,
                md: 3,
              },
            }}>
            <SubscriptionMetrics subscription={data} mode="admin" />
          </Stack>
        </Box>
        <Divider />
      </Box>
      <Stack
        sx={{
          flexDirection: {
            xs: 'column',
            lg: 'row',
          },
          gap: {
            xs: 2.5,
            md: 4,
          },
          '.payment-link-column-1': {
            minWidth: {
              xs: '100%',
              lg: '600px',
            },
          },
          '.payment-link-column-2': {
            width: {
              xs: '100%',
              md: '100%',
              lg: '320px',
            },
            maxWidth: {
              xs: '100%',
              md: '33%',
            },
          },
        }}>
        <Box
          className="payment-link-column-1"
          sx={{
            flex: 1,
            gap: 2.5,
            display: 'flex',
            flexDirection: 'column',
          }}>
          <Box className="section" sx={{ containerType: 'inline-size' }}>
            <SectionHeader title={t('admin.details')} />
            <InfoRowGroup
              sx={{
                display: 'grid',
                gridTemplateColumns: {
                  xs: 'repeat(1, 1fr)',
                  xl: 'repeat(2, 1fr)',
                },
                '@container (min-width: 1000px)': {
                  gridTemplateColumns: 'repeat(2, 1fr)',
                },
                '.info-row-wrapper': {
                  gap: 1,
                  flexDirection: {
                    xs: 'column',
                    xl: 'row',
                  },
                  alignItems: {
                    xs: 'flex-start',
                    xl: 'center',
                  },
                  '@container (min-width: 1000px)': {
                    flexDirection: 'row',
                    alignItems: 'center',
                  },
                },
                '.currency-name': {
                  color: 'text.secondary',
                },
              }}>
              <InfoRow
                label={t('common.customer')}
                value={<CustomerLink customer={data.customer} size={isMobile ? 'default' : 'small'} />}
              />
              <InfoRow label={t('common.createdAt')} value={formatTime(data.created_at)} />
              <InfoRow
                label={t('admin.subscription.currentPeriod')}
                value={[formatTime(data.current_period_start * 1000), formatTime(data.current_period_end * 1000)].join(
                  ' ~ '
                )}
              />
              <InfoRow
                label={t('admin.subscription.trialingPeriod')}
                value={
                  data.trial_end && data.trial_start
                    ? [formatTime(data.trial_start * 1000), formatTime(data.trial_end * 1000)].join(' ~ ')
                    : ''
                }
              />
              {data.status === 'paused' && !!data.pause_collection?.resumes_at && (
                <InfoRow label={t('common.resumesAt')} value={formatTime(data.pause_collection.resumes_at * 1000)} />
              )}
              <InfoRow label={t('admin.subscription.collectionMethod')} value={data.collection_method} />
              <InfoRow
                label={t('admin.paymentCurrency.name')}
                value={
                  <Currency
                    logo={data.paymentCurrency.logo}
                    name={`${data.paymentCurrency.symbol} (${data.paymentMethod?.name})`}
                  />
                }
              />

              {(data as any).paymentMethodDetails && (
                <InfoRow
                  label={t('admin.subscription.payerAddress')}
                  value={
                    <PaymentMethodInfo
                      subscriptionId={data.id}
                      customer={data.customer}
                      paymentMethodDetails={(data as any).paymentMethodDetails}
                      editable={false}
                      paymentMethodType={data.paymentMethod?.type}
                    />
                  }
                />
              )}
              {data.payment_details && hasDelegateTxHash(data.payment_details, data.paymentMethod) && (
                <InfoRow
                  label={t('common.delegateTxHash')}
                  value={<TxLink details={data.payment_details} method={data.paymentMethod} />}
                />
              )}
              {data.paymentMethod?.type === 'arcblock' && data.payment_details?.arcblock?.staking?.tx_hash && (
                <InfoRow
                  label={t('common.stakeTxHash')}
                  value={
                    <TxLink
                      details={{ arcblock: { tx_hash: data.payment_details?.arcblock?.staking?.tx_hash, payer: '' } }}
                      method={data.paymentMethod}
                    />
                  }
                />
              )}
              {!!data.description && <InfoRow label={t('common.description')} value={data.description} />}
              {!!data.recovered_from && (
                <InfoRow
                  label={t('common.recoverFrom')}
                  value={
                    <Link to={`/admin/billing/${data.recovered_from}`} target="_blank">
                      {data.recovered_from}
                    </Link>
                  }
                />
              )}
            </InfoRowGroup>
          </Box>

          {/* IAP details — Google Play / App Store */}
          {(data.payment_details?.google_play || data.payment_details?.app_store) && (
            <>
              <Divider />
              <Box className="section" sx={{ containerType: 'inline-size' }}>
                <SectionHeader
                  title={
                    data.payment_details?.google_play
                      ? t('admin.subscription.iap.googlePlayTitle')
                      : t('admin.subscription.iap.appStoreTitle')
                  }
                />
                <InfoRowGroup
                  sx={{
                    '.info-row-value': { wordBreak: 'break-all' },
                  }}>
                  {(data as any).channel && (
                    <InfoRow label={t('admin.subscription.channel')} value={(data as any).channel} />
                  )}
                  {data.payment_details?.google_play && (
                    <>
                      <InfoRow
                        label={t('admin.subscription.iap.purchaseToken')}
                        value={data.payment_details.google_play.purchase_token}
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.orderId')}
                        value={data.payment_details.google_play.order_id || '—'}
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.productId')}
                        value={data.payment_details.google_play.product_id}
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.expiryTime')}
                        value={
                          data.payment_details.google_play.expiry_time_millis
                            ? formatTime(Number(data.payment_details.google_play.expiry_time_millis))
                            : '—'
                        }
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.environment')}
                        value={data.payment_details.google_play.environment || (data as any).environment || '—'}
                      />
                    </>
                  )}
                  {data.payment_details?.app_store && (
                    <>
                      <InfoRow
                        label={t('admin.subscription.iap.originalTransactionId')}
                        value={data.payment_details.app_store.original_transaction_id}
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.transactionId')}
                        value={data.payment_details.app_store.transaction_id || '—'}
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.productId')}
                        value={data.payment_details.app_store.product_id}
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.expiryTime')}
                        value={
                          data.payment_details.app_store.expires_at
                            ? formatTime(data.payment_details.app_store.expires_at * 1000)
                            : '—'
                        }
                      />
                      <InfoRow
                        label={t('admin.subscription.iap.environment')}
                        value={data.payment_details.app_store.environment || (data as any).environment || '—'}
                      />
                    </>
                  )}
                </InfoRowGroup>
              </Box>
            </>
          )}
          <Divider />
          {/* Discount Information */}
          {(data as any).discountStats && (
            <Box className="section">
              <Typography variant="h3" className="section-header" sx={{ mb: 1.5 }}>
                {t('admin.subscription.discount')}
              </Typography>
              <Box className="section-body">
                <DiscountInfo discountStats={(data as any).discountStats} />
              </Box>
            </Box>
          )}

          <Box className="section">
            <SectionHeader title={t('admin.product.pricing')} />
            <Box className="section-body">
              <SubscriptionItemList data={data.items} currency={data.paymentCurrency} mode="admin" />
            </Box>
          </Box>
          {(() => {
            const vendorServices = data.items?.map((item) => item.price?.product?.vendor_config || []).flat();
            if (!vendorServices || vendorServices.length === 0) return null;
            return (
              <>
                <Divider />
                <Box
                  className="section"
                  sx={{
                    '.section-header': {
                      fontSize: {
                        xs: '18px',
                        md: '1.09375rem',
                      },
                    },
                    '.vendor-service-item': {
                      maxWidth: '400px',
                    },
                  }}>
                  <VendorServiceList
                    vendorServices={vendorServices}
                    subscriptionId={data.id}
                    isOwner={session?.user?.did === data.customer?.did}
                    isCanceled={data.status === 'canceled'}
                  />
                </Box>
              </>
            );
          })()}
          <Divider sx={{ my: 1.5 }} />
          {isCredit ? (
            <>
              <Box className="section">
                <Typography variant="h3" className="section-header">
                  {t('admin.creditGrants.tab')}
                </Typography>
                <Box className="section-body">
                  <CreditGrantsList customer_id={data.customer_id} subscription_id={data.id} mode="dashboard" />
                </Box>
              </Box>
              <Box className="section">
                <Typography variant="h3" className="section-header">
                  {t('admin.creditTransactions.title')}
                </Typography>
                <Box className="section-body">
                  <CreditTransactionsList
                    customer_id={data.customer_id}
                    subscription_id={data.id}
                    includeGrants
                    mode="dashboard"
                  />
                </Box>
              </Box>
            </>
          ) : (
            <>
              <Box className="section">
                <SectionHeader title={t('admin.invoices')} />
                <Box className="section-body">
                  <InvoiceList
                    features={{ customer: true, toolbar: false }}
                    subscription_id={data.id}
                    include_staking
                  />
                </Box>
              </Box>
              <Divider />
              <Box className="section">
                <SectionHeader title={t('admin.refunds')} />
                <Box className="section-body">
                  <RefundList features={{ customer: true, toolbar: false }} subscription_id={data.id} />
                </Box>
              </Box>
            </>
          )}
          <Divider />
          <Box className="section">
            <SectionHeader title={t('admin.events.title')} />
            <Box className="section-body">
              <EventList features={{ toolbar: false }} object_id={data.id} />
            </Box>
          </Box>
        </Box>
        {isMobile && <Divider />}
        <Box className="payment-link-column-2" sx={{ gap: 2.5, display: 'flex', flexDirection: 'column' }}>
          <Box className="section">
            <SectionHeader title={t('common.metadata.label')}>
              <Button
                variant="text"
                color="inherit"
                size="small"
                sx={{ color: 'text.link' }}
                disabled={state.editing.metadata}
                onClick={handleEditMetadata}>
                {t('common.edit')}
              </Button>
            </SectionHeader>
            <Box className="section-body">
              <MetadataList data={data.metadata} handleEditMetadata={handleEditMetadata} />
              {state.editing.metadata && (
                <MetadataEditor
                  data={data}
                  loading={state.loading.metadata}
                  onSave={onUpdateMetadata}
                  onCancel={() => setState((prev) => ({ editing: { ...prev.editing, metadata: false } }))}
                />
              )}
            </Box>
          </Box>
        </Box>
      </Stack>
    </Root>
  );
}

const Root = styled(Stack)``;
