ID du formulaire

Gatsby

Un formulaire Gatsby qui fonctionne déjà dans le HTML statique avant l'hydratation, amélioré ensuite avec fetch, plus une Gatsby Function pour les envois avec une clé secrète.

Gatsby génère chaque page en HTML au moment du build. Donnez au formulaire une vraie action et il envoie avant l'hydratation de React, ou si le bundle ne se charge pas ; une fois hydraté, le composant envoie avec fetch et affiche le résultat sur place.

Envoyer depuis le navigateur

  1. Ajoutez l'id du formulaire

    .env.production
    GATSBY_IKIFORM_FORM_ID=frm_xxxxxxxxxxxxxxxx

    Gatsby n'expose au code navigateur que les variables qui commencent par GATSBY_, et les intègre au moment du build. Ajoutez la même ligne à .env.development pour gatsby develop.

  2. Ajoutez le composant

    src/components/contact-form.js
    import * as React from "react";
    
    const endpoint = `https://ikiform.com/f/${process.env.GATSBY_IKIFORM_FORM_ID}`;
    
    export default function ContactForm() {
      const [status, setStatus] = React.useState("idle");
      const [message, setMessage] = React.useState("");
    
      async function onSubmit(event) {
        event.preventDefault();
        setStatus("sending");
        try {
          const response = await fetch(endpoint, {
            method: "POST",
            headers: { Accept: "application/json" },
            body: new FormData(event.currentTarget),
          });
          const result = await response.json();
          if (result.ok) return setStatus("sent");
          setMessage(result.error.message);
        } catch {
          setMessage("Couldn't reach the server. Try again.");
        }
        setStatus("error");
      }
    
      if (status === "sent") return <p>Thanks, we got it.</p>;
    
      return (
        <form action={endpoint} method="post" onSubmit={onSubmit}>
          <label>
            Email
            <input name="email" type="email" autoComplete="email" required />
          </label>
          <label>
            Message
            <textarea name="message" rows={5} />
          </label>
          <input type="hidden" name="_redirect" value="https://example.com/thanks/" />
          <input name="_gotcha" type="text" tabIndex={-1} autoComplete="off" hidden />
          {status === "error" ? <p role="alert">{message}</p> : null}
          <button disabled={status === "sending"}>Send</button>
        </form>
      );
    }

    Affichez-le depuis n'importe quelle page, par exemple src/pages/contact.js, et ajoutez src/pages/thanks.js pour la redirection sans JavaScript. Pour les erreurs de champ et la vérification humaine du SDK, complétez-le comme dans le guide React.

Envoyer depuis une Gatsby Function

Une Gatsby Function peut transmettre l'envoi avec une clé secrète, ce qui contourne les domaines autorisés et la vérification humaine. Elle ne tourne que chez les hébergeurs compatibles avec les Gatsby Functions, comme Netlify avec l'adaptateur Gatsby ; un hébergeur purement statique comme GitHub Pages ne peut pas l'exécuter. Stockez IKIFORM_FORM_ID et une clé secrète avec la portée submissions:write dans IKIFORM_SECRET_KEY, sans le préfixe GATSBY_, pour qu'elles n'atteignent jamais le navigateur.

src/api/contact.js
export default async function handler(req, res) {
  if (req.method !== "POST") return res.status(405).end();
  const response = await fetch(`https://ikiform.com/f/${process.env.IKIFORM_FORM_ID}`, {
    method: "POST",
    headers: {
      "Content-Type": "application/json",
      Accept: "application/json",
      Authorization: `Bearer ${process.env.IKIFORM_SECRET_KEY}`,
    },
    body: JSON.stringify(req.body),
  });
  res.status(response.status).json(await response.json());
}

Gatsby analyse les corps JSON et form-encoded dans req.body, donc la page peut envoyer vers /api/contact dans les deux formats. Tous les envois partagent alors l'adresse IP de votre fonction pour les limites de débit ; voir Depuis un serveur.

Domaines autorisés

Cela s'applique aux envois depuis le navigateur. Les envois depuis la Gatsby Function utilisent une clé secrète et contournent ce contrôle.

Où tourne le formulaireÀ ajouter aux domaines autorisés
gatsby develop et gatsby servelocalhost. Correspond à http://localhost:8000 et http://localhost:9000 : Ikiform compare uniquement le nom d'hôte, jamais le port.
Votre domaineexample.com, qui couvre aussi www.example.com
Netlifyyour-site.netlify.app. Les deploy previews (deploy-preview-12--your-site.netlify.app) et les branch deploys (branch--your-site.netlify.app) n'en sont pas des sous-domaines : ajoutez l'hôte de prévisualisation exact le temps de le tester.
Cloudflare Pagesyour-project.pages.dev. Les URL de prévisualisation comme abc123.your-project.pages.dev en sont des sous-domaines, donc elles correspondent déjà.
  • N'ajoutez jamais netlify.app ou pages.dev seul. Tous les sites de cet hébergeur correspondraient, y compris ceux des autres.

Checklist de test

  1. Lancez gatsby build et ouvrez public/contact/index.html. L'action du formulaire doit se terminer par l'id de votre formulaire, pas par undefined.
  2. Lancez gatsby serve avec localhost dans les domaines autorisés et envoyez. Le message de remerciement doit remplacer le formulaire.
  3. Désactivez JavaScript, rechargez et envoyez. Vous devez voir la page de remerciement d'Ikiform en local, ou /thanks/ sur votre domaine https:.
  4. Si vous utilisez la fonction, envoyez vers /api/contact sur un déploiement de prévisualisation et vérifiez que la soumission apparaît dans Ikiform.

Dépannage

Ce que vous voyezPourquoiSolution
404 not_found, et l'action se termine par /f/undefinedLa variable n'est pas préfixée par GATSBY_, ou n'était pas définie au moment du buildNommez-la GATSBY_IKIFORM_FORM_ID et relancez le build.
La fonction répond 403 forbiddenLa clé secrète provient d'un autre espace de travail, est révoquée ou n'a pas submissions:writeCréez une clé secrète avec cette portée.
/api/contact renvoie 404 après le déploiementL'hébergeur ne sert que des fichiers statiquesDéployez chez un hébergeur compatible avec les Gatsby Functions, ou utilisez la version navigateur.
Les soumissions arrivent dans le filtre spam avec origin_mismatchLa page qui a envoyé ne fait pas partie des domaines autorisés du formulaireAjoutez l'hôte du tableau ci-dessus. Avec Reject, les mêmes envois reçoivent plutôt 403 origin_not_allowed.