Aller au contenu principal

Validation des données entrantes

Que ce soit sur vos endpoints tRPC ou sur un endpoint à part dans Next.js pour recevoir des webhooks, la devise est de toujours valider les données entrantes.

Nous utilisons zod pour faire la validation au moment du runtime (quand les types ne peuvent être garantis sur les données entrantes). Cela nous permet une certaine flexibilité puisqu'il peut servir à la validation d'entrée d'un endpoint mais aussi pour formater une structure métier (dans le cas où vous voulez que ça émette une erreur si la structure récupérée depuis une base de données est mal formatée par exemple).

  • Une pratique peut être de définir vos structures métiers avec zod puisque les types peuvent être "inférés" ;
  • zod est nativement supporté par tRPC, donc vous n'avez qu'à mettre votre structure input au niveau du endpoint ;
  • zod peut s'utiliser côté frontend avec react-hook-form afin de faire des validations sans même contacter le serveur. Ce qui est pratique dans notre cas c'est que la même structure de validation est utilisée dans les 2 mondes (avec ces textes d'erreurs qui peuvent être personnalisés).
entities/agent.tsx | Déclaration d'une structure d'entité
import z from 'zod';

import { UserSchema } from './user';

export const AgentSchema = z
.object({
id: z.string().uuid(),
userId: z.string().uuid(),
authorityId: z.string().uuid(),
firstname: UserSchema.shape.firstname,
lastname: UserSchema.shape.lastname,
email: UserSchema.shape.email,
profilePicture: UserSchema.shape.profilePicture,
isMainAgent: z.boolean(),
createdAt: z.date(),
updatedAt: z.date(),
deletedAt: z.date().nullable(),
})
.strict();
export type AgentSchemaType = z.infer<typeof AgentSchema>;
actions/agent.tsx | Validation d'une mutation avec les propriétés d'entités existantes
import { AgentSchema } from '@mediature/main/src/models/entities/agent';
import { AuthoritySchema } from '@mediature/main/src/models/entities/authority';
import { UserSchema } from '@mediature/main/src/models/entities/user';
import z from 'zod';

export const AddAgentSchema = z
.object({
userId: UserSchema.shape.id,
authorityId: AgentSchema.shape.authorityId,
grantMainAgent: z.boolean(),
})
.strict();
export type AddAgentSchemaType = z.infer<typeof AddAgentSchema>;