Le formulaire envoie, Resend ne trouve pas l’audience

Le message « Aucune audience trouvée » sur Resend apparaît quand la clé API utilisée a la permission Sending only : elle peut envoyer des emails, mais pas lister ni gérer les audiences. La correction passe par une clé Full access, en gardant en tête que le plan gratuit ne permet qu’une seule audience.

Rien de cassé côté code en général : c’est un problème de permissions et de plan, pas de bug. Le formulaire fonctionne, l’email de confirmation part parfois même, mais la route serveur qui doit rattacher le contact à une audience tombe dans le vide. Deux minutes de dashboard suffisent à régler 90 % des cas.

Ce qui bloque concrètement

1. Vérifier la permission de la clé API dans le dashboard

Ouvre Resend, va dans API Keys, et regarde la colonne de permission de la clé utilisée par ta route serveur. Deux valeurs possibles : Full access ou Sending access.

Une clé API est un jeton d’authentification qui autorise une application à appeler les endpoints d’un service sans exposer d’identifiants classiques. Sur Resend, une clé Sending access peut appeler emails.send et rien d’autre : elle ne voit ni les domaines, ni les audiences, ni les autres clés Resend Changelog, New API Key Permissions. Une clé Full access, elle, peut créer, lire, modifier et supprimer n’importe quelle ressource du compte Resend Docs, Add a domain.

C’est exactement ce qu’on a rencontré chez Peechy sur peechy.fr en juin 2026 : le formulaire d’inscription du pied de page et celui de la popup envoyaient les emails vers une audience Resend via une route serveur, mais la clé configurée était en Sending only. Résultat : les emails partaient (la permission le permet), mais l’appel qui allait chercher l’audience pour y attacher le contact renvoyait « Aucune audience trouvée », puisque cette lecture est réservée aux clés Full access.

2. Créer une clé Full access dédiée à la gestion des audiences

Ne réutilise pas la clé de production existante si elle est en Sending only pour d’autres raisons (bonne pratique de sécurité). Crée une clé séparée, nommée clairement (par exemple audiences-server), avec la permission Full access.

Attention : le paramètre de restriction par domaine (domainId) ne s’applique que sur une clé en sending_access ; une clé full_access reste valable pour tout le compte, ce qui augmente sa surface d’exposition en cas de fuite Resend Docs, Add a domain. Stocke-la dans une variable d’environnement dédiée, jamais dans le code source, et limite son usage à la seule route serveur qui en a besoin.

3. Composer avec la limite d’une audience sur le plan gratuit

Le plan gratuit d’emailing marketing de Resend est plafonné à 1 000 contacts avec des envois illimités, mais il ne propose qu’une seule audience à gérer, ce qui empêche de séparer une liste « prospects » d’une liste « clients actifs » sans passer sur un plan payant démarrant autour de 40 $/mois pour 5 000 contacts (source secondaire à recouper : Flexprice, guide pricing Resend).

Sur un projet en plan gratuit, la solution la plus simple n’est pas de contourner la limite, mais d’accepter une seule audience et de segmenter par tags sur les contacts eux-mêmes plutôt que par audience séparée. Ça évite l’erreur de vouloir créer une deuxième audience qui échouera silencieusement tant que le plan reste gratuit.

4. Auto-détecter l’audience côté serveur plutôt que coder un ID en dur

Coder l’identifiant d’audience directement dans le code casse le jour où l’audience est recréée ou renommée. Le pattern recommandé, illustré dans les exemples officiels Resend, consiste à interroger l’API pour retrouver l’audience existante plutôt que de la deviner :

import { Resend } from 'resend';

const resend = new Resend(process.env.RESEND_API_KEY);

async function getAudienceId() {
  if (process.env.RESEND_AUDIENCE_ID) {
    return process.env.RESEND_AUDIENCE_ID;
  }
  const { data } = await resend.audiences.list();
  const audiences = data?.data ?? [];
  if (audiences.length === 0) {
    throw new Error('Aucune audience trouvée : vérifie la permission de la clé API');
  }
  return audiences[0].id;
}

Ce fallback (variable d’environnement en priorité, sinon appel à audiences.list()) reprend directement le pattern documenté dans les exemples officiels Resend en Python GitHub Resend, resend-examples. Le message d’erreur explicite (« vérifie la permission de la clé API ») fait gagner un temps précieux au prochain qui touchera ce code, y compris toi dans six mois.

5. Mettre en place un vrai double opt-in

Le double opt-in désigne le mécanisme qui exige une confirmation explicite du contact, par clic sur un lien reçu par email, avant de l’ajouter définitivement à une liste de diffusion active. Resend ne le fournit pas nativement : le repo officiel resend-double-opt-in-example montre comment le reconstituer en Next.js, en ajoutant d’abord le contact avec le statut unsubscribed: true, puis en le faisant basculer à false seulement après clic sur un lien de confirmation signé GitHub Resend, resend-double-opt-in-example.

C’est le point que beaucoup de sites sautent, souvent parce que le premier blocage (l’erreur d’audience) a déjà pris tout le temps prévu pour l’intégration. Sans ce mécanisme, tu risques d’inscrire des adresses invalides ou non consenties, ce qui pose un vrai problème RGPD sur la base légale de collecte : voir notre guide sur la conformité RGPD d’un site web pour le cadre exact.

Tableau récapitulatif

CauseSolution
Clé API en Sending onlyCréer une clé Full access dédiée à la lecture des audiences
Plan gratuit limité à une audienceSegmenter par tags sur les contacts plutôt que par audience séparée
ID d’audience codé en durAuto-détecter via resend.audiences.list() avec fallback sur variable d’environnement
Pas de confirmation d’inscriptionImplémenter le flux unsubscribed + lien signé du repo officiel Resend
Confusion Audiences / SegmentsVérifier dans le dashboard quelle terminologie s’applique à ton compte

Ce diagnostic vaut aussi si tu es venu ici après avoir cherché pourquoi un formulaire de contact n’envoie rien : le symptôme (rien ne se passe côté destinataire) est souvent le même, la cause diffère seulement sur l’endpoint qui échoue.

FAQ

Pourquoi Resend accepte l'envoi d'email mais pas la lecture de l'audience ?

Parce que ce sont deux permissions distinctes sur la clé API. sending_access autorise uniquement emails.send ; toute lecture ou gestion de ressource (audiences, domaines, autres clés) exige full_access Resend Docs, Create API key.

Une clé Full access est-elle plus risquée en cas de fuite ?

Oui. Une clé Full access compromise permet de supprimer des domaines, créer de nouvelles clés ou verrouiller le compte, alors qu’une clé Sending access compromise ne permet que d’envoyer des emails. Limite son usage strictement à la route serveur qui en a besoin, et ne la stocke jamais côté client.

Peut-on créer une deuxième audience sur le plan gratuit Resend ?

Non, le plan gratuit Resend limite la gestion des audiences à une seule, avec un plafond de 1 000 contacts. Pour séparer plusieurs listes, il faut passer sur un plan payant Resend Docs, Pricing.

Faut-il utiliser Audiences ou Segments chez Resend en 2026 ?

Les Audiences restent fonctionnelles mais Resend les fait progressivement évoluer vers les Segments, une notion plus fine de filtrage des contacts. Pour un projet neuf, vérifie dans le dashboard quelle terminologie s’applique à ton compte avant de coder contre l’un ou l’autre.

Le double opt-in est-il obligatoire légalement en France ?

La collecte du consentement doit être explicite et vérifiable, ce qui rend le double opt-in fortement recommandé en pratique, même si le texte ne l’impose pas mot pour mot. Voir notre article sur la conformité RGPD d’un site web pour le détail des obligations.

Quand passer la main à un pro

Si le diagnostic ci-dessus ne débloque rien après avoir vérifié la permission de la clé, régénéré une clé Full access propre et testé l’appel audiences.list() en isolation, le problème vient probablement d’ailleurs : un webhook mal configuré, une route serveur qui timeout avant même d’appeler Resend, ou un compte Resend suspendu pour dépassement de quota. À ce stade, un développeur qui connaît la configuration de l’API Resend de bout en bout ira plus vite qu’un nouvel essai-erreur en production.

Ce problème, Peechy s'en occupe

Plutôt que de tout gérer seul, confiez votre site à une agence qui s'occupe de tout, hébergement, sécurité, maintenance et corrections. Encore plus simple en abonnement : on règle les soucis avant même que vous les remarquiez.

Confier mon site à Peechy