import React, { useState, useEffect } from "react";
import { api } from "../services/api";
import { useAuth } from "../hooks/useAuth";
import { usePageTitle } from "../hooks/usePageTitle";
import { toast } from "react-toastify";
import { ConfirmDialog } from "../components/ConfirmDialog";

const AWS_REGIONS = [
  "us-east-1", "us-east-2", "us-west-1", "us-west-2",
  "eu-west-1", "eu-west-2", "eu-west-3", "eu-central-1", "eu-north-1",
  "ap-southeast-1", "ap-southeast-2", "ap-northeast-1", "ap-northeast-2", "ap-south-1",
  "sa-east-1", "ca-central-1", "me-south-1", "af-south-1",
];

export function Settings() {
  const { user, refresh } = useAuth();
  usePageTitle("Settings");
  const [settings, setSettings] = useState<any>(null);
  const [loading, setLoading] = useState(true);

  const [username, setUsername] = useState("");
  const [currentPassword, setCurrentPassword] = useState("");
  const [newPassword, setNewPassword] = useState("");

  const [giteaUrl, setGiteaUrl] = useState("");
  const [giteaUsername, setGiteaUsername] = useState("");
  const [giteaPAT, setGiteaPAT] = useState("");

  const [awsKeyId, setAwsKeyId] = useState("");
  const [awsSecret, setAwsSecret] = useState("");
  const [awsRegion, setAwsRegion] = useState("us-east-1");

  const [webhookUrl, setWebhookUrl] = useState("");
  const [webhookSecret, setWebhookSecret] = useState("");
  const [confirmRotate, setConfirmRotate] = useState(false);
  const [saving, setSaving] = useState<string | null>(null);

  useEffect(() => {
    api.user.settings().then(res => {
      if (res.ok && res.data) {
        const d = res.data;
        setSettings(d);
        setUsername(d.username || "");
        setGiteaUrl(d.giteaInstanceUrl || "");
        setGiteaUsername(d.giteaUsername || "");
        setWebhookUrl(d.webhookUrl || "");
      }
    });
    api.user.getWebhookSecret().then(res => {
      if (res.ok && res.data) setWebhookSecret(res.data.token);
    });
    setLoading(false);
  }, []);

  const save = async (key: string, fn: () => Promise<any>) => {
    setSaving(key);
    const res = await fn();
    setSaving(null);
    if (res.ok) {
      toast.success(res.message || "Saved");
      refresh();
    } else {
      toast.error(res.message || "Failed to save");
    }
  };

  const handleRotateSecret = async () => {
    setConfirmRotate(false);
    setSaving("rotate");
    const res = await api.user.regenerateWebhookSecret();
    setSaving(null);
    if (res.ok && res.data) {
      setWebhookSecret(res.data.token);
      toast.success(res.message || "Secret regenerated");
    } else {
      toast.error(res.message || "Failed to regenerate");
    }
  };

  const copyToClipboard = (text: string, label: string) => {
    navigator.clipboard.writeText(text);
    toast.info(`${label} copied to clipboard`);
  };

  if (loading) return <div className="animate-pulse h-96 bg-gray-100 dark:bg-slate-800 rounded-xl" />;

  return (
    <div className="max-w-2xl space-y-8">
      <ConfirmDialog
        open={confirmRotate}
        title="Regenerate Webhook Secret"
        message="This will generate a new secret and update all registered Gitea webhooks. The old secret will become invalid immediately."
        confirmLabel="Regenerate"
        onConfirm={handleRotateSecret}
        onCancel={() => setConfirmRotate(false)}
        danger
      />

      <h1 className="text-2xl font-bold">Account Settings</h1>

      {/* Username */}
      <Section title="Username">
        <div className="flex gap-2">
          <input
            type="text"
            value={username}
            onChange={e => setUsername(e.target.value)}
            className={inputCls}
            placeholder="Username"
          />
          <button
            onClick={() => save("username", () => api.user.updateUsername(username))}
            disabled={saving === "username"}
            className={btnCls}
          >
            {saving === "username" ? "Saving..." : "Save"}
          </button>
        </div>
      </Section>

      {/* Password */}
      <Section title="Change Password">
        <div className="space-y-2">
          <input
            type="password"
            value={currentPassword}
            onChange={e => setCurrentPassword(e.target.value)}
            className={inputCls}
            placeholder="Current password"
          />
          <input
            type="password"
            value={newPassword}
            onChange={e => setNewPassword(e.target.value)}
            className={inputCls}
            placeholder="New password"
          />
          <button
            onClick={() => save("password", () => api.user.updatePassword(currentPassword, newPassword))}
            disabled={saving === "password"}
            className={btnCls}
          >
            {saving === "password" ? "Saving..." : "Update Password"}
          </button>
        </div>
      </Section>

      {/* Gitea */}
      <Section title="Gitea Connection">
        <p className="text-xs text-gray-500 dark:text-slate-400 mb-3">
          PP will post PR comments as your Gitea account (@{giteaUsername || "username"}). Make sure your PAT has 'issue' write permission.
        </p>
        <div className="space-y-2">
          <input
            type="url"
            value={giteaUrl}
            onChange={e => setGiteaUrl(e.target.value)}
            className={inputCls}
            placeholder="https://gitea.example.com"
          />
          <input
            type="text"
            value={giteaUsername}
            onChange={e => setGiteaUsername(e.target.value)}
            className={inputCls}
            placeholder="Gitea username"
          />
          <div className="relative">
            <input
              type="password"
              value={giteaPAT}
              onChange={e => setGiteaPAT(e.target.value)}
              className={inputCls}
              placeholder={settings?.giteaPatSet ? "••••••••  (set — enter new value to update)" : "Personal Access Token"}
            />
            <p className="text-xs text-gray-400 dark:text-slate-500 mt-1">
              Required PAT scopes: <code>repository</code> (read), <code>issue</code> (write), <code>admin:repo_hook</code>
            </p>
          </div>
          <button
            onClick={() => save("gitea", () => api.user.updateGitea({ giteaInstanceUrl: giteaUrl, giteaUsername, giteaPAT: giteaPAT || undefined }))}
            disabled={saving === "gitea"}
            className={btnCls}
          >
            {saving === "gitea" ? "Connecting..." : "Save & Validate"}
          </button>
        </div>
      </Section>

      {/* AWS */}
      <Section title="AWS Credentials">
        <div className="space-y-2">
          <input
            type="text"
            value={awsKeyId}
            onChange={e => setAwsKeyId(e.target.value)}
            className={inputCls}
            placeholder={settings?.awsAccessKeyId ? `${settings.awsAccessKeyId} (set)` : "AWS Access Key ID"}
          />
          <input
            type="password"
            value={awsSecret}
            onChange={e => setAwsSecret(e.target.value)}
            className={inputCls}
            placeholder="AWS Secret Access Key"
          />
          <select
            value={awsRegion}
            onChange={e => setAwsRegion(e.target.value)}
            className={inputCls}
          >
            {AWS_REGIONS.map(r => <option key={r} value={r}>{r}</option>)}
          </select>
          <div className="bg-gray-50 dark:bg-slate-700/50 rounded-lg p-3">
            <p className="text-xs font-medium mb-2">Required IAM Permissions:</p>
            <pre className="text-xs text-gray-600 dark:text-slate-300 overflow-auto">{IAM_POLICY}</pre>
            <button onClick={() => copyToClipboard(IAM_POLICY, "IAM policy")} className="text-xs text-blue-600 dark:text-blue-400 mt-1 hover:underline">
              Copy IAM policy
            </button>
          </div>
          <button
            onClick={() => save("aws", () => api.user.updateAws({ awsAccessKeyId: awsKeyId, awsSecretAccessKey: awsSecret, awsRegion }))}
            disabled={saving === "aws"}
            className={btnCls}
          >
            {saving === "aws" ? "Validating..." : "Save & Validate"}
          </button>
        </div>
      </Section>

      {/* Webhook */}
      <Section title="Webhook">
        <div className="space-y-3">
          <div>
            <label className="text-xs text-gray-500 dark:text-slate-400 block mb-1">Webhook URL (Target URL in Gitea)</label>
            <div className="flex gap-2">
              <input type="text" readOnly value={webhookUrl} className={`${inputCls} bg-gray-50 dark:bg-slate-700/50 font-mono text-xs`} />
              <button onClick={() => copyToClipboard(webhookUrl, "Webhook URL")} className={btnSecCls}>Copy</button>
            </div>
          </div>
          <div>
            <label className="text-xs text-gray-500 dark:text-slate-400 block mb-1">Webhook Secret</label>
            <div className="flex gap-2">
              <input type="text" readOnly value={webhookSecret} className={`${inputCls} bg-gray-50 dark:bg-slate-700/50 font-mono text-xs`} />
              <button onClick={() => copyToClipboard(webhookSecret, "Webhook secret")} className={btnSecCls}>Copy</button>
              <button onClick={() => setConfirmRotate(true)} disabled={saving === "rotate"} className="px-3 py-2 text-sm rounded-lg bg-yellow-100 dark:bg-yellow-900/30 text-yellow-700 dark:text-yellow-300 hover:bg-yellow-200 transition-colors">
                Rotate
              </button>
            </div>
          </div>
          <p className="text-xs text-gray-500 dark:text-slate-400">
            PP auto-registers per-repo webhooks when you enable a repo. These credentials are for reference only.
          </p>
        </div>
      </Section>
    </div>
  );
}

function Section({ title, children }: { title: string; children: React.ReactNode }) {
  return (
    <div className="bg-white dark:bg-slate-800 border border-gray-200 dark:border-slate-700 rounded-xl p-5">
      <h2 className="text-base font-semibold mb-4">{title}</h2>
      {children}
    </div>
  );
}

const inputCls = "w-full px-3 py-2 text-sm border border-gray-300 dark:border-slate-600 rounded-lg bg-white dark:bg-slate-700 focus:outline-none focus:ring-2 focus:ring-blue-500";
const btnCls = "px-4 py-2 text-sm rounded-lg bg-blue-600 hover:bg-blue-700 text-white font-medium transition-colors disabled:opacity-50";
const btnSecCls = "px-3 py-2 text-sm rounded-lg bg-gray-100 dark:bg-slate-700 hover:bg-gray-200 dark:hover:bg-slate-600 text-gray-700 dark:text-slate-300 transition-colors shrink-0";

const IAM_POLICY = `{
  "Version": "2012-10-17",
  "Statement": [{
    "Effect": "Allow",
    "Action": [
      "ec2:RunInstances",
      "ec2:TerminateInstances",
      "ec2:DescribeInstances",
      "ec2:CreateSecurityGroup",
      "ec2:DeleteSecurityGroup",
      "ec2:AuthorizeSecurityGroupIngress",
      "ec2:DescribeSecurityGroups",
      "ec2:CreateKeyPair",
      "ec2:DeleteKeyPair",
      "ec2:CreateTags",
      "sts:GetCallerIdentity"
    ],
    "Resource": "*"
  }]
}`;
