Add a contact form to a Nuxt site

Handle Nuxt form submissions with SiteBackend. Works with static generation (nuxt generate) - no server routes needed.

1 minUpdated

SiteBackend receives the form, so it works with nuxt generate and any static host.

components/ContactForm.vue
<script setup lang="ts">
const endpoint = useRuntimeConfig().public.sitebackendForm;
const status = ref<"idle" | "sending" | "sent" | "error">("idle");
const error = ref("");
 
async function onSubmit(event: Event) {
  status.value = "sending";
  const form = event.target as HTMLFormElement;
  const result = await $fetch<{ ok: boolean; error?: string }>(endpoint, {
    method: "POST",
    body: new FormData(form),
    headers: { Accept: "application/json" },
  }).catch((e) => e.data);
  if (result?.ok) status.value = "sent";
  else {
    error.value = result?.error ?? "Something went wrong";
    status.value = "error";
  }
}
</script>
 
<template>
  <p v-if="status === 'sent'">Thanks! We'll be in touch.</p>
  <form v-else :action="endpoint" method="POST" @submit.prevent="onSubmit">
    <input type="email" name="email" required />
    <textarea name="message" required />
    <button type="submit" :disabled="status === 'sending'">Send</button>
    <p v-if="status === 'error'" role="alert">{{ error }}</p>
  </form>
</template>
nuxt.config.ts
export default defineNuxtConfig({
  runtimeConfig: {
    public: { sitebackendForm: "" }, // set NUXT_PUBLIC_SITEBACKEND_FORM
  },
});

The form keeps its action, so it still works without JavaScript. If you use allowed origins, add http://localhost:3000 for local development.

Show testimonials too

SiteBackend can also collect testimonials from your customers and show them on your site. See add testimonials to a Nuxt site.