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
Ajoutez l'id du formulaire
.env.production GATSBY_IKIFORM_FORM_ID=frm_xxxxxxxxxxxxxxxxGatsby 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.developmentpourgatsby develop.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 ajoutezsrc/pages/thanks.jspour 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.
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 serve | localhost. Correspond à http://localhost:8000 et http://localhost:9000 : Ikiform compare uniquement le nom d'hôte, jamais le port. |
| Votre domaine | example.com, qui couvre aussi www.example.com |
| Netlify | your-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 Pages | your-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.appoupages.devseul. Tous les sites de cet hébergeur correspondraient, y compris ceux des autres.
Checklist de test
- Lancez
gatsby buildet ouvrezpublic/contact/index.html. L'actiondu formulaire doit se terminer par l'id de votre formulaire, pas parundefined. - Lancez
gatsby serveaveclocalhostdans les domaines autorisés et envoyez. Le message de remerciement doit remplacer le formulaire. - Désactivez JavaScript, rechargez et envoyez. Vous devez voir la page de remerciement d'Ikiform en local, ou
/thanks/sur votre domainehttps:. - Si vous utilisez la fonction, envoyez vers
/api/contactsur un déploiement de prévisualisation et vérifiez que la soumission apparaît dans Ikiform.
Dépannage
| Ce que vous voyez | Pourquoi | Solution |
|---|---|---|
404 not_found, et l'action se termine par /f/undefined | La variable n'est pas préfixée par GATSBY_, ou n'était pas définie au moment du build | Nommez-la GATSBY_IKIFORM_FORM_ID et relancez le build. |
La fonction répond 403 forbidden | La clé secrète provient d'un autre espace de travail, est révoquée ou n'a pas submissions:write | Créez une clé secrète avec cette portée. |
/api/contact renvoie 404 après le déploiement | L'hébergeur ne sert que des fichiers statiques | Déployez chez un hébergeur compatible avec les Gatsby Functions, ou utilisez la version navigateur. |
Les soumissions arrivent dans le filtre spam avec origin_mismatch | La page qui a envoyé ne fait pas partie des domaines autorisés du formulaire | Ajoutez l'hôte du tableau ci-dessus. Avec Reject, les mêmes envois reçoivent plutôt 403 origin_not_allowed. |