"use client";

import Link from "next/link";
import { useActionState, useEffect, useRef } from "react";

import { submitSupportRequest } from "@/app/actions";
import { initialFormState } from "@/lib/form-state";
import type { Locale } from "@/lib/locales";

import { Button } from "./Button";
import styles from "./Form.module.css";

export type SupportFormStrings = {
  name: string;
  company: string;
  module: string;
  modulePlaceholder: string;
  phone: string;
  description: string;
  optional: string;
  consent: string;
  privacyLabel: string;
  privacyHref: string;
  send: string;
  sending: string;
  successTitle: string;
  successBody: string;
  errorTitle: string;
  errorSummaryAria: string;
};

export type ModuleOption = { value: string; label: string };

/**
 * The support request. Same pipeline as the demo form with a different
 * subject prefix (Blueprint 07), so existing customers have a written route
 * that is not the phone.
 */
export function SupportForm({
  locale,
  modules,
  strings,
}: {
  locale: Locale;
  modules: ModuleOption[];
  strings: SupportFormStrings;
}) {
  const [state, action, pending] = useActionState(submitSupportRequest, initialFormState);
  const startedAtRef = useRef<HTMLInputElement | null>(null);
  const resultRef = useRef<HTMLDivElement | null>(null);

  /*
   * The fill-time reference is written straight into the input on mount. It
   * must not be part of the statically generated HTML: a build-time stamp
   * would make every submission look hours old and the check would never fire.
   */
  useEffect(() => {
    if (startedAtRef.current) {
      startedAtRef.current.value = String(Date.now());
    }
  }, []);

  useEffect(() => {
    if (state.status !== "idle") {
      resultRef.current?.focus();
    }
  }, [state.status]);

  if (state.status === "success") {
    return (
      <div className={styles.result} ref={resultRef} tabIndex={-1} role="status">
        <p className={styles.resultTitle}>{strings.successTitle}</p>
        <p className={styles.resultBody}>{strings.successBody}</p>
      </div>
    );
  }

  const errors = state.errors ?? {};
  const errorList = Object.values(errors);

  return (
    <form action={action} className={styles.form} noValidate>
      <input type="hidden" name="locale" value={locale} />
      <input type="hidden" name="startedAt" defaultValue="0" ref={startedAtRef} />

      {errorList.length > 0 ? (
        <div
          className={styles.summary}
          ref={resultRef}
          tabIndex={-1}
          role="alert"
          aria-label={strings.errorSummaryAria}
        >
          <p className={styles.resultTitle}>{strings.errorTitle}</p>
          <ul className={styles.summaryList}>
            {errorList.map((message) => (
              <li key={message}>{message}</li>
            ))}
          </ul>
        </div>
      ) : null}

      <div className={styles.fields}>
        <p className={styles.field}>
          <label className={styles.label} htmlFor="support-name">
            {strings.name}
          </label>
          <input
            id="support-name"
            name="name"
            type="text"
            autoComplete="name"
            required
            aria-invalid={errors.name ? true : undefined}
            aria-describedby={errors.name ? "support-name-error" : undefined}
            className={[styles.input, errors.name ? styles.invalid : null]
              .filter(Boolean)
              .join(" ")}
          />
          {errors.name ? (
            <span id="support-name-error" className={styles.error}>
              {errors.name}
            </span>
          ) : null}
        </p>

        <p className={styles.field}>
          <label className={styles.label} htmlFor="support-company">
            {strings.company} <span className={styles.optional}>({strings.optional})</span>
          </label>
          <input
            id="support-company"
            name="company"
            type="text"
            autoComplete="organization"
            className={styles.input}
          />
        </p>

        <p className={styles.field}>
          <label className={styles.label} htmlFor="support-module">
            {strings.module}
          </label>
          <select
            id="support-module"
            name="module"
            required
            defaultValue=""
            aria-invalid={errors.module ? true : undefined}
            aria-describedby={errors.module ? "support-module-error" : undefined}
            className={[styles.select, errors.module ? styles.invalid : null]
              .filter(Boolean)
              .join(" ")}
          >
            <option value="" disabled>
              {strings.modulePlaceholder}
            </option>
            {modules.map((module) => (
              <option key={module.value} value={module.value}>
                {module.label}
              </option>
            ))}
          </select>
          {errors.module ? (
            <span id="support-module-error" className={styles.error}>
              {errors.module}
            </span>
          ) : null}
        </p>

        <p className={styles.field}>
          <label className={styles.label} htmlFor="support-phone">
            {strings.phone}
          </label>
          <input
            id="support-phone"
            name="phone"
            type="tel"
            inputMode="tel"
            autoComplete="tel"
            required
            aria-invalid={errors.phone ? true : undefined}
            aria-describedby={errors.phone ? "support-phone-error" : undefined}
            className={[styles.input, errors.phone ? styles.invalid : null]
              .filter(Boolean)
              .join(" ")}
          />
          {errors.phone ? (
            <span id="support-phone-error" className={styles.error}>
              {errors.phone}
            </span>
          ) : null}
        </p>

        <p className={`${styles.field} ${styles.span2}`}>
          <label className={styles.label} htmlFor="support-description">
            {strings.description}
          </label>
          <textarea
            id="support-description"
            name="description"
            rows={4}
            required
            aria-invalid={errors.description ? true : undefined}
            aria-describedby={errors.description ? "support-description-error" : undefined}
            className={[styles.textarea, errors.description ? styles.invalid : null]
              .filter(Boolean)
              .join(" ")}
          />
          {errors.description ? (
            <span id="support-description-error" className={styles.error}>
              {errors.description}
            </span>
          ) : null}
        </p>
      </div>

      <p className={styles.honeypot} aria-hidden="true">
        <label htmlFor="support-website">Website</label>
        <input id="support-website" name="website" type="text" tabIndex={-1} autoComplete="off" />
      </p>

      <p className={styles.consent}>
        {strings.consent} <Link href={strings.privacyHref}>{strings.privacyLabel}</Link>
      </p>

      <div className={styles.actions}>
        <Button type="submit" disabled={pending} data-event="support_submit">
          {pending ? strings.sending : strings.send}
        </Button>
      </div>
    </form>
  );
}
