// auth.jsx — Login component + useApi hook.

function useApi(fetcher, deps) {
  const [state, setState] = React.useState({ data: null, error: null, loading: true });
  const [tick, setTick] = React.useState(0);
  const depList = Array.isArray(deps) ? deps : [];

  React.useEffect(() => {
    let cancelled = false;
    setState((s) => ({ ...s, loading: true, error: null }));
    Promise.resolve()
      .then(() => fetcher())
      .then((res) => {
        if (cancelled) return;
        setState({ data: res && "data" in res ? res.data : res, error: null, loading: false, meta: res && res.meta });
      })
      .catch((err) => {
        if (cancelled) return;
        setState({ data: null, error: err, loading: false });
      });
    return () => { cancelled = true; };
  }, [...depList, tick]);

  return { ...state, reload: () => setTick((t) => t + 1) };
}
window.useApi = useApi;

// Subscribe to per-workspace real-time events via WebSocket. Calls
// `onEvent({event, callId, data, timestamp})` for every message after
// the initial 'realtime.hello'. Returns nothing — cleanup on unmount.
//
// Auto-reconnects with capped exponential backoff if the socket drops.
// Sends pings every 30s at the server side; client acks automatically.
function useWorkspaceEvents(workspaceId, onEvent) {
  const onEventRef = React.useRef(onEvent);
  React.useEffect(() => { onEventRef.current = onEvent; }, [onEvent]);

  React.useEffect(() => {
    if (!workspaceId) return;
    const token = API.getToken();
    if (!token) return;

    let socket = null;
    let cancelled = false;
    let backoffMs = 1000;

    function connect() {
      if (cancelled) return;
      // Browsers don't allow custom headers on WS handshake; pass JWT via
      // ?token= query param. The server accepts both Authorization header
      // and this query param (the auth plugin reads from request.headers
      // first; JWT tokens sent via query require minor server tweak).
      const wsBase = API.base.replace(/^http/, "ws");
      const url = `${wsBase}/workspaces/${workspaceId}/realtime?token=${encodeURIComponent(token)}`;
      socket = new WebSocket(url);

      socket.addEventListener("open", () => { backoffMs = 1000; });
      socket.addEventListener("message", (ev) => {
        try {
          const msg = JSON.parse(ev.data);
          if (msg.event !== "realtime.hello") onEventRef.current?.(msg);
        } catch {}
      });
      socket.addEventListener("close", () => {
        if (cancelled) return;
        const delay = Math.min(backoffMs, 30000);
        backoffMs = Math.min(backoffMs * 2, 30000);
        setTimeout(connect, delay);
      });
      socket.addEventListener("error", () => { try { socket.close(); } catch {} });
    }
    connect();

    return () => {
      cancelled = true;
      try { socket?.close(); } catch {}
    };
  }, [workspaceId]);
}
window.useWorkspaceEvents = useWorkspaceEvents;

function Login({ onSuccess, onGoSignup }) {
  const [email, setEmail] = React.useState("");
  const [password, setPassword] = React.useState("");
  const [error, setError] = React.useState(null);
  const [submitting, setSubmitting] = React.useState(false);

  async function submit(e) {
    e.preventDefault();
    if (submitting) return;
    setError(null);
    setSubmitting(true);
    try {
      const res = await API.auth.login(email, password);
      API.setToken(res.data.accessToken);
      onSuccess && onSuccess(res.data.user);
    } catch (err) {
      setError(err.message || "Login failed");
      setSubmitting(false);
    }
  }

  return (
    <div className="onboarding">
      <div className="onboarding-card">
        <div style={{display:"flex", alignItems:"center", justifyContent:"center", gap:10, marginBottom:28}}>
          <div style={{width:30, height:30, borderRadius:8, background:"linear-gradient(135deg,#0A84FF,#9333EA)", color:"white", fontSize:14, fontWeight:700, display:"grid", placeItems:"center"}}>C</div>
          <div style={{fontFamily:"var(--serif)", fontSize:20}}>Call tracking</div>
        </div>

        <form onSubmit={submit} className="col g16">
          <div style={{textAlign:"center"}}>
            <h1 className="serif" style={{fontSize:32, letterSpacing:"-0.015em", marginBottom:6, fontWeight:400}}>Welcome back</h1>
            <div style={{color:"var(--ink-3)", fontSize:14}}>Sign in to your workspace</div>
          </div>

          <div className="field">
            <label>Work email</label>
            <input
              className="input"
              type="email"
              placeholder="you@agency.com"
              value={email}
              onChange={(e) => setEmail(e.target.value)}
              autoFocus
              required
            />
          </div>
          <div className="field">
            <label>Password</label>
            <input
              className="input"
              type="password"
              value={password}
              onChange={(e) => setPassword(e.target.value)}
              required
            />
          </div>

          {error && (
            <div style={{fontSize:12.5, color:"#DC2626", background:"rgba(220,38,38,.08)", padding:"8px 10px", borderRadius:7, textAlign:"center"}}>
              {error}
            </div>
          )}

          <button className="btn btn-primary btn-lg" type="submit" disabled={submitting}>
            {submitting ? "Signing in…" : "Sign in"}
          </button>

          <div style={{fontSize:13, color:"var(--ink-3)", textAlign:"center"}}>
            New here?{" "}
            <a
              href="#"
              onClick={(e) => { e.preventDefault(); onGoSignup && onGoSignup(); }}
              style={{color:"var(--accent)", fontWeight:500, textDecoration:"none"}}
            >
              Create an account
            </a>
          </div>
        </form>
      </div>
    </div>
  );
}
window.Login = Login;
