Actions
Ajouté à la version :
astro@4.15
Astro Actions vous permet de définir et d’appeler des fonctions backend avec sûreté du typage. Les actions effectuent la récupération des données, l’analyse JSON et la validation des entrées pour vous. Cela peut réduire considérablement la quantité de code standard nécessaire par rapport à l’utilisation d’un point de terminaison d’API.
Utilisez des actions à la place de points de terminaison d’API pour une communication transparente entre votre code client et votre code serveur et pour :
- Valider automatiquement les entrées de données JSON et de formulaire à l’aide de la validation Zod.
- Générer des fonctions avec sûreté du typage pour appeler votre backend à partir du client et même à partir des actions de formulaire HTML. Pas besoin d’appels manuels à
fetch()
. - Standardiser les erreurs du backend avec l’objet
ActionError
.
Utilisation de base
Titre de la section Utilisation de baseLes actions sont définies dans un objet server
exporté depuis src/actions/index.ts
:
Vos actions sont disponibles en tant que fonctions à partir du module astro:actions
. Importez actions
et appelez-les côté client dans un composant de framework UI, une requête POST de formulaire ou en utilisant une balise <script>
dans un composant Astro.
Lorsque vous appelez une action, elle renvoie un objet avec soit data
contenant le résultat sérialisé JSON, soit error
contenant les erreurs renvoyées.
Écrivez votre première action
Titre de la section Écrivez votre première actionSuivez ces étapes pour définir une action et pour l’appeler dans une balise script
de votre page Astro.
-
Créez un fichier
src/actions/index.ts
et exportez un objetserver
. -
Importez l’utilitaire
defineAction()
depuisastro:actions
et l’objetz
depuisastro:schema
. -
Utilisez l’utilitaire
defineAction()
pour définir une actiongetGreeting
. La propriétéinput
sera utilisée pour valider les paramètres d’entrée avec un schéma Zod et la fonctionhandler()
inclut la logique backend à exécuter sur le serveur. -
Créez un composant Astro avec un bouton qui récupérera un message d’accueil à l’aide de votre action
getGreeting
lorsqu’il est cliqué. -
Pour utiliser votre action, importez
actions
depuisastro:actions
puis appelezactions.getGreeting()
dans le gestionnaire de clics. L’optionname
sera envoyée à la fonctionhandler()
de votre action sur le serveur et, s’il n’y a pas d’erreur, le résultat sera disponible sous la forme de la propriétédata
.
defineAction()
et ses propriétés.
Organiser les actions
Titre de la section Organiser les actionsToutes les actions de votre projet doivent être exportées depuis l’objet server
dans le fichier src/actions/index.ts
. Vous pouvez définir des actions en ligne ou déplacer les définitions d’actions vers des fichiers séparés et les importer. Vous pouvez même regrouper des fonctions liées dans des objets imbriqués.
Par exemple, pour regrouper toutes vos actions utilisateur, vous pouvez créer un fichier src/actions/user.ts
et imbriquer les définitions de getUser
et createUser
dans un seul objet user
.
Ensuite, vous pouvez importer cet objet user
dans votre fichier src/actions/index.ts
et l’ajouter en tant que propriété de niveau supérieur à l’objet server
aux côtés de toute autre action :
Désormais, toutes vos actions utilisateur peuvent être appelées à partir de l’objet actions.user
:
actions.user.getUser()
actions.user.createUser()
Gestion des données renvoyées
Titre de la section Gestion des données renvoyéesLes actions renvoient un objet contenant soit data
qui contient la valeur de retour de votre fonction handler()
avec sûreté du typage, soit error
qui contient les erreurs du backend. Ces dernières peuvent provenir d’erreurs de validation sur la propriété input
ou d’erreurs générées dans la fonction handler()
.
Vérification des erreurs
Titre de la section Vérification des erreursIl est préférable de vérifier si une erreur (error
) est présente avant d’utiliser la propriété data
. Cela vous permet à la fois de gérer les erreurs à l’avance et d’être certain que data
est définie sans vérification additionnelle pour undefined
.
Accéder directement aux données sans vérification d’erreur
Titre de la section Accéder directement aux données sans vérification d’erreurPour ignorer la gestion des erreurs, par exemple lors du prototypage ou de l’utilisation d’une bibliothèque qui détectera les erreurs à votre place, utilisez la propriété .orThrow()
sur votre appel d’action pour générer des erreurs au lieu de renvoyer une error
. Cela renverra directement les data
de l’action.
Cet exemple appelle une action likePost()
qui renvoie le nombre mis à jour de mentions « j’aime » sous forme de nombre à partir de l’action handler
:
Gestion des erreurs backend dans votre action
Titre de la section Gestion des erreurs backend dans votre actionVous pouvez utiliser la classe ActionError
fournie pour générer une erreur à partir de la fonction handler()
de votre action, comme, par exemple, « not found » lorsqu’une entrée de base de données est manquante ou « unauthorized » lorsqu’un utilisateur n’est pas connecté. Cela présente deux avantages principaux par rapport au renvoi de undefined
:
-
Vous pouvez définir un code d’état tel que
404 - Not found
ou401 - Unauthorized
. Cela améliore le débogage des erreurs à la fois en développement et en production en vous permettant de voir le code d’état de chaque demande. -
Dans le code de votre application, toutes les erreurs sont transmises à l’objet
error
sur un résultat d’action. Cela évite d’avoir à vérifier si les données sont indéfinies et vous permet d’afficher des commentaires ciblés à l’utilisateur en fonction de ce qui s’est mal passé.
Création d’une ActionError
Titre de la section Création d’une ActionErrorPour générer une erreur, importez la classe ActionError()
depuis le module astro:actions
. Transmettez-lui un code d’état lisible par l’homme (par exemple "NOT_FOUND"
ou "BAD_REQUEST"
), et un message
facultatif pour fournir des informations supplémentaires sur l’erreur.
Cet exemple génère une erreur d’une action likePost
lorsqu’un utilisateur n’est pas connecté, après avoir vérifié un hypothétique cookie de « session utilisateur » pour l’authentification :
Gestion d’une ActionError
Titre de la section Gestion d’une ActionErrorPour gérer cette erreur, vous pouvez appeler l’action depuis votre application et vérifier si une propriété error
est présente. Cette propriété sera de type ActionError
et contiendra votre code
et message
.
Dans l’exemple suivant, un composant LikeButton.tsx
appelle l’action likePost()
lorsqu’il est cliqué. Si une erreur d’authentification se produit, l’attribut error.code
est utilisé pour déterminer s’il faut afficher un lien de connexion :
Gestion des redirections client
Titre de la section Gestion des redirections clientLorsque vous appelez des actions à partir du client, vous pouvez intégrer une bibliothèque côté client comme react-router
, ou vous pouvez utiliser la fonction navigate()
d’Astro pour rediriger vers une nouvelle page lorsqu’une action réussit.
Cet exemple permet de retourner sur la page d’accueil après qu’une action de déconnexion (logout
) ait abouti avec succès :
Accepter les données d’un formulaire à partir d’une action
Titre de la section Accepter les données d’un formulaire à partir d’une actionLes actions acceptent les données JSON par défaut. Pour accepter les données d’un formulaire HTML, définissez accept: 'form'
dans votre appel defineAction()
:
Validation des données du formulaire
Titre de la section Validation des données du formulaireLes actions analyseront les données de formulaire soumises à un objet, en utilisant la valeur de l’attribut name
de chaque entrée comme propriétés d’objet. Par exemple, un formulaire contenant <input name="search">
sera analysé en un objet comme { search: 'user input' }
. Le schéma input
de votre action sera utilisé pour valider cet objet.
Pour recevoir l’objet FormData
brut dans votre gestionnaire d’action au lieu d’un objet analysé, omettez la propriété input
dans la définition de votre action.
L’exemple suivant montre un formulaire d’inscription à une newsletter validé qui accepte l’e-mail d’un utilisateur et nécessite une case à cocher pour accepter les « conditions d’utilisation ».
-
Créez un composant de formulaire HTML avec des attributs
name
uniques sur chaque entrée : -
Définir une action
newsletter
pour gérer le formulaire soumis. Validez le champemail
en utilisant le validateurz.string().email()
et la case à cocherterms
en utilisantz.boolean()
:Consultez la référence de l’APIinput
pour tous les validateurs de formulaire disponibles. -
Ajoutez un
<script>
au formulaire HTML pour soumettre la saisie de l’utilisateur. Cet exemple remplace le comportement de soumission par défaut du formulaire pour appeleractions.newsletter()
et redirige vers/confirmation
à l’aide de la fonctionnavigate()
:Consultez « Appeler des actions depuis une action de formulaire HTML » pour découvrir une autre façon de soumettre des données de formulaire.
Affichage des erreurs de saisie du formulaire
Titre de la section Affichage des erreurs de saisie du formulaireVous pouvez valider les entrées du formulaire avant la soumission à l’aide des attributs natifs de validation de formulaire HTML tels que required
, type="email"
et pattern
. Pour une validation plus complexe d’input
depuis le backend, vous pouvez utiliser la fonction utilitaire isInputError()
.
Pour récupérer les erreurs de saisie, utilisez l’utilitaire isInputError()
pour vérifier si une erreur a été provoquée par une entrée non valide. Les erreurs de saisie contiennent un objet fields
avec des messages pour chaque nom d’entrée qui n’a pas pu être validé. Vous pouvez utiliser ces messages pour demander à votre utilisateur de corriger sa soumission.
L’exemple suivant vérifie l’erreur avec isInputError()
, puis vérifie si l’erreur se trouve dans le champ e-mail, avant de créer finalement un message à partir des erreurs. Vous pouvez utiliser la manipulation DOM JavaScript ou votre infrastructure d’interface utilisateur préférée pour afficher ce message aux utilisateurs.
Appeler des actions depuis une action de formulaire HTML
Titre de la section Appeler des actions depuis une action de formulaire HTMLLes pages doivent être rendues à la demande lors de l’appel d’actions à l’aide d’une action de formulaire. Assurez-vous que le prérendu est désactivé sur la page avant d’utiliser cette API.
Vous pouvez activer les soumissions de formulaires zéro-JS avec des attributs standard sur n’importe quel élément <form>
. Les soumissions de formulaires sans JavaScript côté client peuvent être utiles à la fois comme solution de secours en cas d’échec du chargement de JavaScript ou si vous préférez gérer les formulaires entièrement à partir du serveur.
L’appel de Astro.getActionResult() sur le serveur renvoie le résultat de votre soumission de formulaire (data
ou error
), et peut être utilisé pour rediriger dynamiquement, gérer les erreurs de formulaire, mettre à jour l’interface utilisateur, etc.
Pour appeler une action à partir d’un formulaire HTML, ajoutez method="POST"
à votre <form>
, puis définissez l’attribut action
du formulaire à l’aide de votre action, par exemple action={actions.logout}
. Cela définira l’attribut action
pour utiliser une chaîne de requête gérée automatiquement par le serveur.
Par exemple, ce composant Astro appelle l’action logout
lorsque le bouton est cliqué et recharge la page actuelle :
Redirection en cas de réussite de l’action
Titre de la section Redirection en cas de réussite de l’actionPour accéder à une page différente lorsqu’une action réussit sans JavaScript côté client, vous pouvez ajouter un chemin dans l’attribut action
.
Par exemple, action={'/confirmation' + actions.newsletter}
naviguera vers /confirmation
lorsque l’action newsletter
réussit :
Redirection dynamique en cas de réussite de l’action
Titre de la section Redirection dynamique en cas de réussite de l’actionSi vous devez décider vers où rediriger de manière dynamique, vous pouvez utiliser le résultat d’une action sur le serveur. Un exemple courant est la création d’un enregistrement de produit et la redirection vers la page du nouveau produit, par exemple /products/[id]
.
Par exemple, supposons que vous ayez une action createProduct
qui renvoie l’identifiant du produit généré :
Vous pouvez récupérer le résultat de l’action de votre composant Astro en appelant Astro.getActionResult()
. Cela renvoie un objet contenant les propriétés data
ou error
lorsqu’une action est appelée, ou undefined
si l’action n’a pas été appelée pendant cette requête.
Utilisez la propriété data
pour construire une URL à utiliser avec Astro.redirect()
:
Gérer les erreurs d’action du formulaire
Titre de la section Gérer les erreurs d’action du formulaireAstro ne redirige pas vers votre route action
lorsqu’une action échoue. Au lieu de cela, la page actuelle est rechargée avec toutes les erreurs renvoyées par l’action. L’appel de Astro.getActionResult()
dans le composant Astro contenant votre formulaire vous donne accès à l’objet error
pour une gestion personnalisée des erreurs.
L’exemple suivant affiche un message d’échec général lorsqu’une action newsletter
échoue :
Pour plus de personnalisation, vous pouvez utiliser l’utilitaire isInputError()
pour vérifier si une erreur est provoquée par une entrée non valide.
L’exemple suivant affiche une bannière d’erreur sous le champ de saisie email
lorsqu’un e-mail invalide est soumis :
Astro conserve les données (data
) et erreurs (error
) de l’action avec un cookie à usage unique. Cela signifie que getActionResult()
renverra un résultat sur la première requête uniquement, et undefined
lors de la nouvelle consultation de la page.
Conserver les valeurs d’entrée en cas d’erreur
Titre de la section Conserver les valeurs d’entrée en cas d’erreurLes entrées seront effacées à chaque fois qu’un formulaire sera soumis. Pour conserver les valeurs d’entrée, vous pouvez activer les transitions de vue sur la page et appliquer la directive transition:persist
à chaque entrée :
Mettre à jour l’interface utilisateur avec un résultat d’action de formulaire
Titre de la section Mettre à jour l’interface utilisateur avec un résultat d’action de formulaireLe résultat renvoyé par Astro.getActionResult()
est à usage unique et sera réinitialisé à undefined
à chaque actualisation de la page. Ceci est idéal pour afficher les erreurs de saisie et afficher des notifications temporaires à l’utilisateur en cas de réussite.
Si vous avez besoin d’afficher un résultat lors des actualisations de page, envisagez de stocker le résultat dans une base de données ou dans un cookie.
Transmettez une action à Astro.getActionResult()
et utilisez la propriété data
renvoyée pour restituer n’importe quelle interface utilisateur temporaire que vous souhaitez afficher. Cet exemple utilise la propriété productName
renvoyée par une action addToCart
pour afficher un message de réussite :
Les données d’action sont transmises à l’aide d’un cookie persistant. Ce cookie n’est pas chiffré et sa taille est limitée à 4 Ko, bien que la limite exacte puisse varier d’un navigateur à l’autre.
En général, nous recommandons de renvoyer le minimum d’informations nécessaires à votre gestionnaire d’actions (handler
) pour éviter les vulnérabilités, et de conserver les autres informations sensibles dans une base de données.
Par exemple, vous pouvez renvoyer le nom d’un produit dans une action addToCart
, plutôt que de renvoyer l’intégralité de l’objet product
:
Appeler des actions à partir des composants Astro et des points de terminaison du serveur
Titre de la section Appeler des actions à partir des composants Astro et des points de terminaison du serveurVous pouvez appeler des actions directement à partir des scripts de composants Astro en utilisant le wrapper Astro.callAction()
(ou context.callAction()
lors de l’utilisation d’un point de terminaison de serveur). Il est courant de réutiliser la logique de vos actions dans un autre code serveur.
Transmettez l’action comme premier argument et tous les paramètres d’entrée comme deuxième argument. Cela renvoie les mêmes objets data
et error
que vous recevez lors de l’appel d’actions sur le client :