import { useState, useEffect, useCallback } from 'react';
import { useNavigate, useOutletContext } from 'react-router-dom';
import {
  Card, Button, Form, Input, Space, Typography, Spin, Alert,
  Steps, App, Grid, Divider, Result, Tag, theme,
} from 'antd';
import {
  CheckCircleOutlined, CloseCircleOutlined, LoadingOutlined,
  SettingOutlined, ApiOutlined, DatabaseOutlined, LockOutlined,
  BranchesOutlined, ReloadOutlined,
} from '@ant-design/icons';
import { api } from '@/lib/api';
import type { AppOutletContext } from '@/components/AppLayout';

const { Text, Paragraph, Title } = Typography;

interface SetupStatus {
  giteaOnline: boolean;
  installComplete: boolean;
  tokenConfigured: boolean;
  reposCreated: boolean;
  oauthConfigured: boolean;
  setupComplete: boolean;
}

interface TestConnectionResult {
  success: boolean;
  giteaVersion?: string;
  error?: string;
}

interface SetupStepResult {
  step: string;
  success: boolean;
  error?: string;
  data?: Record<string, unknown>;
}

interface SetupRunResult {
  success: boolean;
  steps: SetupStepResult[];
  error?: string;
}

const STEP_LABELS: Record<string, string> = {
  check_connection: 'Check Connection',
  create_token: 'Create API Token',
  create_comments_repo: 'Create Comments Repository',
  create_history_repo: 'Create History Repository',
  create_labels: 'Create Labels',
  create_oauth_app: 'Create OAuth Application',
  save_config: 'Save Configuration',
};

const STEP_ICONS: Record<string, React.ReactNode> = {
  check_connection: <ApiOutlined />,
  create_token: <LockOutlined />,
  create_comments_repo: <DatabaseOutlined />,
  create_history_repo: <DatabaseOutlined />,
  create_labels: <SettingOutlined />,
  create_oauth_app: <LockOutlined />,
  save_config: <SettingOutlined />,
};

export default function GiteaSetupPage() {
  const { setPageHeader } = useOutletContext<AppOutletContext>();
  const { message } = App.useApp();
  const navigate = useNavigate();
  const screens = Grid.useBreakpoint();
  const isMobile = !screens.md;
  const { token: themeToken } = theme.useToken();

  // State
  const [loading, setLoading] = useState(true);
  const [status, setStatus] = useState<SetupStatus | null>(null);
  const [currentStep, setCurrentStep] = useState(0);

  // Step 1: Auth
  const [username, setUsername] = useState('admin');
  const [password, setPassword] = useState('');
  const [testResult, setTestResult] = useState<TestConnectionResult | null>(null);
  const [testing, setTesting] = useState(false);

  // Step 2: Run
  const [running, setRunning] = useState(false);
  const [runResult, setRunResult] = useState<SetupRunResult | null>(null);

  useEffect(() => {
    setPageHeader({ title: 'Gitea Setup' });
    return () => setPageHeader(null);
  }, [setPageHeader]);

  const fetchStatus = useCallback(async () => {
    setLoading(true);
    try {
      const res = await api.get<SetupStatus>('/gitea/setup/status');
      setStatus(res.data);
    } catch {
      message.error('Failed to load Gitea setup status');
    } finally {
      setLoading(false);
    }
  }, [message]);

  useEffect(() => {
    fetchStatus();
  }, [fetchStatus]);

  const handleTestConnection = async () => {
    setTesting(true);
    setTestResult(null);
    try {
      const res = await api.post<TestConnectionResult>('/gitea/setup/test-connection', {
        username,
        password,
      });
      setTestResult(res.data);
      if (res.data.success) {
        message.success('Connected to Gitea successfully');
      }
    } catch (err: unknown) {
      const errorMsg = err instanceof Error ? err.message : 'Connection test failed';
      setTestResult({ success: false, error: errorMsg });
    } finally {
      setTesting(false);
    }
  };

  const handleRunSetup = async () => {
    setRunning(true);
    setRunResult(null);
    try {
      const res = await api.post<SetupRunResult>('/gitea/setup/run', {
        username,
        password,
      });
      setRunResult(res.data);
      if (res.data.success) {
        message.success('Gitea setup completed successfully');
      } else {
        message.error('Setup completed with errors');
      }
    } catch (err: unknown) {
      const errorMsg = err instanceof Error ? err.message : 'Setup failed';
      setRunResult({ success: false, steps: [], error: errorMsg });
      message.error('Setup failed');
    } finally {
      setRunning(false);
    }
  };

  const handleRerun = () => {
    setCurrentStep(0);
    setTestResult(null);
    setRunResult(null);
    setPassword('');
    fetchStatus();
  };

  if (loading) {
    return (
      <div style={{ textAlign: 'center', padding: 80 }}>
        <Spin size="large" />
      </div>
    );
  }

  // Already complete — show success overview
  if (status?.setupComplete && !runResult) {
    return (
      <Card>
        <Result
          status="success"
          title="Gitea Setup Complete"
          subTitle="All Gitea integrations have been configured successfully."
          extra={[
            <Button key="rerun" onClick={handleRerun} icon={<ReloadOutlined />}>
              Re-run Setup
            </Button>,
            <Button
              key="gitea"
              type="primary"
              icon={<BranchesOutlined />}
              onClick={() => navigate('/app/services/gitea')}
            >
              Open Gitea
            </Button>,
          ]}
        />
        <Divider />
        <Space direction="vertical" style={{ width: '100%' }} size="small">
          <StatusRow label="Gitea Online" ok={status.giteaOnline} />
          <StatusRow label="Initial Install Complete" ok={status.installComplete} />
          <StatusRow label="API Token Configured" ok={status.tokenConfigured} />
          <StatusRow label="Repositories Created" ok={status.reposCreated} />
          <StatusRow label="OAuth Configured" ok={status.oauthConfigured} />
        </Space>
      </Card>
    );
  }

  return (
    <Card>
      <Title level={4} style={{ marginTop: 0 }}>
        <SettingOutlined style={{ marginRight: 8 }} />
        Gitea Auto-Setup Wizard
      </Title>
      <Paragraph type="secondary">
        This wizard configures Gitea for documentation comments, page history tracking, and OAuth integration.
      </Paragraph>

      <Steps
        current={currentStep}
        style={{ marginBottom: 32 }}
        direction={isMobile ? 'vertical' : 'horizontal'}
        items={[
          { title: 'Status Check', icon: <ApiOutlined /> },
          { title: 'Authenticate', icon: <LockOutlined /> },
          { title: 'Run Setup', icon: <SettingOutlined /> },
          { title: 'Complete', icon: <CheckCircleOutlined /> },
        ]}
      />

      {/* Step 0: Status Check */}
      {currentStep === 0 && (
        <Space direction="vertical" style={{ width: '100%' }} size="middle">
          {!status?.giteaOnline && (
            <Alert
              type="warning"
              showIcon
              message="Gitea is not reachable"
              description="The admin API couldn't reach Gitea at its configured URL. If the container is already running, check API logs for the exact response (status code is logged at debug level). Otherwise start it with: docker compose up -d gitea"
            />
          )}

          {status?.giteaOnline && !status.installComplete && (
            <Alert
              type="info"
              showIcon
              message="Complete Gitea Initial Setup"
              description={
                <span>
                  Gitea needs its initial setup completed first. Visit{' '}
                  <a
                    href="/app/services/gitea"
                    onClick={(e) => { e.preventDefault(); navigate('/app/services/gitea'); }}
                  >
                    the Gitea page
                  </a>{' '}
                  and complete the installation wizard to create your admin account.
                </span>
              }
            />
          )}

          {status?.giteaOnline && status.installComplete && (
            <Alert
              type="success"
              showIcon
              message="Gitea is ready for setup"
              description="Gitea is running and the initial installation is complete. Proceed to authenticate."
            />
          )}

          <Space direction="vertical" style={{ width: '100%' }} size="small">
            <StatusRow label="Gitea Online" ok={status?.giteaOnline ?? false} />
            <StatusRow label="Initial Install Complete" ok={status?.installComplete ?? false} />
            <StatusRow label="API Token Configured" ok={status?.tokenConfigured ?? false} />
            <StatusRow label="Repositories Created" ok={status?.reposCreated ?? false} />
            <StatusRow label="OAuth Configured" ok={status?.oauthConfigured ?? false} />
          </Space>

          <Divider />

          <Space>
            <Button onClick={fetchStatus} icon={<ReloadOutlined />}>
              Refresh Status
            </Button>
            <Button
              type="primary"
              onClick={() => setCurrentStep(1)}
              disabled={!status?.giteaOnline || !status?.installComplete}
            >
              Next
            </Button>
          </Space>
        </Space>
      )}

      {/* Step 1: Authenticate */}
      {currentStep === 1 && (
        <Space direction="vertical" style={{ width: '100%' }} size="middle">
          <Alert
            type="info"
            showIcon
            message="Gitea Admin Credentials"
            description="Enter the admin username and password you created during Gitea's initial setup. These are used to create an API token for the integration."
          />

          <Form layout="vertical" style={{ maxWidth: 400 }}>
            <Form.Item label="Username">
              <Input
                value={username}
                onChange={(e) => setUsername(e.target.value)}
                placeholder="admin"
              />
            </Form.Item>
            <Form.Item label="Password">
              <Input.Password
                value={password}
                onChange={(e) => setPassword(e.target.value)}
                placeholder="Enter Gitea admin password"
                onPressEnter={handleTestConnection}
              />
            </Form.Item>
          </Form>

          <Space wrap>
            <Button
              onClick={handleTestConnection}
              loading={testing}
              icon={<ApiOutlined />}
              disabled={!username || !password}
            >
              Test Connection
            </Button>
          </Space>

          {testResult && (
            <Alert
              type={testResult.success ? 'success' : 'error'}
              showIcon
              message={
                testResult.success
                  ? `Connected successfully — Gitea ${testResult.giteaVersion || ''}`
                  : 'Connection failed'
              }
              description={testResult.error || undefined}
            />
          )}

          <Divider />

          <Space>
            <Button onClick={() => setCurrentStep(0)}>Back</Button>
            <Button
              type="primary"
              onClick={() => setCurrentStep(2)}
              disabled={!testResult?.success}
            >
              Next
            </Button>
          </Space>
        </Space>
      )}

      {/* Step 2: Run Setup */}
      {currentStep === 2 && (
        <Space direction="vertical" style={{ width: '100%' }} size="middle">
          <Alert
            type="info"
            showIcon
            message="Ready to Configure"
            description="This will create the API token, repositories, labels, and OAuth application in Gitea. Existing resources will be reused if found."
          />

          {!runResult && (
            <Button
              type="primary"
              size="large"
              onClick={handleRunSetup}
              loading={running}
              icon={<SettingOutlined />}
            >
              {running ? 'Running Setup...' : 'Run Setup'}
            </Button>
          )}

          {running && !runResult && (
            <div style={{ textAlign: 'center', padding: 24 }}>
              <Spin indicator={<LoadingOutlined style={{ fontSize: 32 }} spin />} />
              <Paragraph type="secondary" style={{ marginTop: 12 }}>
                Configuring Gitea resources...
              </Paragraph>
            </div>
          )}

          {runResult && (
            <Space direction="vertical" style={{ width: '100%' }} size="small">
              {runResult.steps.map((step) => (
                <div
                  key={step.step}
                  style={{
                    display: 'flex',
                    alignItems: 'center',
                    gap: 12,
                    padding: '8px 12px',
                    borderRadius: themeToken.borderRadius,
                    background: step.success
                      ? 'rgba(82, 196, 26, 0.06)'
                      : 'rgba(255, 77, 79, 0.06)',
                  }}
                >
                  {step.success ? (
                    <CheckCircleOutlined style={{ color: themeToken.colorSuccess, fontSize: 18 }} />
                  ) : (
                    <CloseCircleOutlined style={{ color: themeToken.colorError, fontSize: 18 }} />
                  )}
                  <span style={{ marginRight: 8 }}>{STEP_ICONS[step.step]}</span>
                  <Text style={{ flex: 1 }}>
                    {STEP_LABELS[step.step] || step.step}
                  </Text>
                  <Tag color={step.success ? 'success' : 'error'}>
                    {step.success ? 'OK' : 'Failed'}
                  </Tag>
                </div>
              ))}

              {runResult.error && (
                <Alert
                  type="error"
                  showIcon
                  message="Setup Error"
                  description={runResult.error}
                  style={{ marginTop: 8 }}
                />
              )}

              {runResult.success && (
                <Alert
                  type="success"
                  showIcon
                  message="All steps completed successfully"
                  style={{ marginTop: 8 }}
                />
              )}
            </Space>
          )}

          <Divider />

          <Space>
            <Button onClick={() => { setRunResult(null); setCurrentStep(1); }}>Back</Button>
            {runResult && (
              <Button
                type="primary"
                onClick={() => setCurrentStep(3)}
                disabled={!runResult.success}
              >
                Next
              </Button>
            )}
            {runResult && !runResult.success && (
              <Button onClick={() => setRunResult(null)} icon={<ReloadOutlined />}>
                Retry
              </Button>
            )}
          </Space>
        </Space>
      )}

      {/* Step 3: Complete */}
      {currentStep === 3 && (
        <Result
          status="success"
          title="Gitea Setup Complete"
          subTitle="All Gitea integrations have been configured. Documentation comments, page history, and OAuth are ready to use."
          extra={[
            <Button
              key="docs-comments"
              onClick={() => navigate('/app/docs/comments')}
              icon={<DatabaseOutlined />}
            >
              Documentation Comments
            </Button>,
            <Button
              key="docs"
              onClick={() => navigate('/app/docs')}
              icon={<SettingOutlined />}
            >
              Documentation
            </Button>,
            <Button
              key="gitea"
              type="primary"
              icon={<BranchesOutlined />}
              onClick={() => navigate('/app/services/gitea')}
            >
              Open Gitea
            </Button>,
          ]}
        />
      )}
    </Card>
  );
}

/** Small helper component for status rows */
function StatusRow({ label, ok }: { label: string; ok: boolean }) {
  return (
    <div style={{ display: 'flex', alignItems: 'center', gap: 8 }}>
      {ok ? (
        <CheckCircleOutlined style={{ color: '#52c41a' }} />
      ) : (
        <CloseCircleOutlined style={{ color: '#ff4d4f' }} />
      )}
      <Text>{label}</Text>
    </div>
  );
}
