[{"data":1,"prerenderedAt":8447},["ShallowReactive",2],{"search-api":-1,"listing-tag-code-review-page-1":3},[4,6027],{"_path":5,"_dir":6,"_draft":7,"_partial":7,"_locale":8,"title":9,"description":10,"id":11,"date":12,"listed":13,"nocomments":7,"hidden":13,"categories":14,"tags":15,"cover":21,"readingTime":22,"body":27,"_type":6021,"_id":6022,"_source":6023,"_file":6024,"_stem":6025,"_extension":6026},"/fr/intelligence-artificielle/5-patterns-dangereux-claude","intelligence-artificielle",false,"","5 anti-patterns que Claude reproduit en silence dans vos codebases","Cinq patterns dangereux que Claude écrit depuis 2 ans dans des milliers de repos. La liste, les exemples, et les contre-patterns craft à appliquer.",63,"2026-05-07",true,[6],[16,17,18,19,20],"claude-code","anti-patterns","software-craftsmanship","code-review","ia","covers/articles/5-patterns-dangereux-claude.jpg",{"text":23,"minutes":24,"time":25,"words":26},"15 min read",14.52,871200,2904,{"type":28,"children":29,"toc":6009},"root",[30,42,47,51,58,74,79,93,121,124,130,135,140,2234,2283,2295,2298,2304,2317,2330,2868,2920,3419,3424,3427,3433,3454,3929,3934,3946,4545,4558,4563,4566,4572,4577,4863,4876,4897,5333,5353,5356,5362,5399,5411,5432,5445,5448,5454,5459,5633,5638,5641,5654,5657,5663,5668,5785,5797,5800,5806,5811,5816,5821,5834,5837,5849,5852,5858,5873,5893,5936,5949,5975,5988,5991,6003],{"type":31,"tag":32,"props":33,"children":34},"element","p",{},[35],{"type":31,"tag":36,"props":37,"children":38},"strong",{},[39],{"type":40,"value":41},"text","En construisant crmcoaching avec Claude (et au fil de mes accompagnements), j'ai vu Claude reproduire les mêmes 5 patterns à chaque nouvelle fonctionnalité. Copiés-collés sans relecture, ils pourrissent la maintenabilité à bas bruit. Aucun ne fait planter la prod tout de suite. Tous coûtent cher à 12 mois.",{"type":31,"tag":32,"props":43,"children":44},{},[45],{"type":40,"value":46},"Voici les 5 anti-patterns que je vois revenir, pourquoi Claude les écrit, et les contre-patterns craft que j'impose pour les neutraliser. Vous pouvez ouvrir votre repo principal et chercher ces signatures dès lundi matin.",{"type":31,"tag":48,"props":49,"children":50},"hr",{},[],{"type":31,"tag":52,"props":53,"children":55},"h2",{"id":54},"pourquoi-claude-reproduit-certains-patterns-en-silence",[56],{"type":40,"value":57},"Pourquoi Claude reproduit certains patterns en silence",{"type":31,"tag":32,"props":59,"children":60},{},[61,63,72],{"type":40,"value":62},"Le constat de base est documenté. Le ",{"type":31,"tag":64,"props":65,"children":69},"a",{"href":66,"rel":67},"https://www.gitclear.com/ai_assistant_code_quality_2024_research",[68],"nofollow",[70],{"type":40,"value":71},"GitClear AI Copilot Code Quality Report 2024",{"type":40,"value":73}," montre que sur 153 millions de lignes de code analysées, le code \"copié\" (par opposition à refactoré) a augmenté de 8 fois depuis l'arrivée massive des assistants IA dans les workflows de développement. Le code \"moved or refactored\" a baissé de 39%. Les équipes consomment de la suggestion brute et la collent dans leur repo, parfois sans modification.",{"type":31,"tag":32,"props":75,"children":76},{},[77],{"type":40,"value":78},"Ce n'est pas un problème de modèle, c'est un problème de training data. Claude apprend à partir de milliards de lignes de code public. Sur GitHub, le code public est massivement écrit par des juniors, des bibliothèques en alpha, des exemples de tutoriels, des copier-collers de Stack Overflow. Quand vous promptez Claude pour une God Function, il vous en livre une, parce que c'est la moyenne statistique de ce qu'il a vu. Et cette moyenne, comme je l'analyse dans le retour d'expérience sur la code review IA, est très en dessous du standard craft attendu en production sérieuse.",{"type":31,"tag":80,"props":81,"children":82},"blockquote",{},[83],{"type":31,"tag":32,"props":84,"children":85},{},[86,91],{"type":31,"tag":36,"props":87,"children":88},{},[89],{"type":40,"value":90},"Ce que j'ai observé sur crmcoaching",{"type":40,"value":92}," : au fil du développement du CRM, j'ai mesuré le ratio de fonctions de plus de 60 lignes dans les commits que j'acceptais tels quels versus ceux que je repassais en review avant de les intégrer. Sans grille de review active : 22% des fonctions Claude dépassaient ce seuil. Avec re-prompt explicite et review systématique : 4%. La codebase ne s'effondre pas tout de suite, mais le coût de modification grimpe linéairement avec la longueur moyenne des fonctions. À 6 mois, c'était le sujet n°1 de mes sessions de refactoring.",{"type":31,"tag":32,"props":94,"children":95},{},[96,98,104,106,111,113,119],{"type":40,"value":97},"Robert C. Martin l'avait écrit dans ",{"type":31,"tag":99,"props":100,"children":101},"em",{},[102],{"type":40,"value":103},"Clean Code",{"type":40,"value":105}," en 2008 : ",{"type":31,"tag":99,"props":107,"children":108},{},[109],{"type":40,"value":110},"\"The first rule of functions is that they should be small. The second rule of functions is that they should be smaller than that.\"",{"type":40,"value":112}," Cette règle, exposée en français dans ",{"type":31,"tag":64,"props":114,"children":116},{"href":115},"/fr/dette-technique/clean-code-software-craftsmanship-principes-java",[117],{"type":40,"value":118},"les principes Clean Code et software craftsmanship",{"type":40,"value":120},", Claude ne l'applique pas par défaut. C'est à vous de la lui imposer par le prompt et la review.",{"type":31,"tag":48,"props":122,"children":123},{},[],{"type":31,"tag":52,"props":125,"children":127},{"id":126},"pattern-1-la-god-function",[128],{"type":40,"value":129},"Pattern #1 : la God Function",{"type":31,"tag":32,"props":131,"children":132},{},[133],{"type":40,"value":134},"C'est le pattern le plus visible. Claude livre une fonction de 60 à 120 lignes qui fait tout : validation, transformation, accès DB, logging, envoi d'événement. Tout dans le même bloc, parce que c'est ce qui ressort statistiquement le plus dans le training data.",{"type":31,"tag":32,"props":136,"children":137},{},[138],{"type":40,"value":139},"Voici un exemple réel que j'ai vu apparaître dans crmcoaching sur la conversion d'un lead en client :",{"type":31,"tag":141,"props":142,"children":146},"pre",{"className":143,"code":144,"language":145,"meta":8,"style":8},"language-typescript shiki shiki-themes catppuccin-frappe github-dark","// apps/api/src/application/use-cases/convert-lead-to-client.use-case.ts\n// Généré par Claude sans prompt de découpe (tel quel)\n\n@Injectable()\nexport class ConvertLeadToClientUseCase {\n  constructor(\n    private readonly prisma: PrismaClient,\n    private readonly brevoService: BrevoService,\n    private readonly auditService: AuditService,\n    private readonly eventEmitter: EventEmitter2,\n  ) {}\n\n  async execute(leadId: string, coachId: string): Promise\u003CClientDto> {\n    // 1. Validation (15 lignes)\n    if (!leadId) throw new BadRequestException('leadId requis');\n    const lead = await this.prisma.lead.findUnique({ where: { id: leadId } });\n    if (!lead) throw new NotFoundException(`Lead ${leadId} introuvable`);\n    if (lead.coachId !== coachId) throw new ForbiddenException('Lead hors scope');\n    if (lead.status === 'CONVERTED') throw new ConflictException('Lead déjà converti');\n    const existingClient = await this.prisma.client.findFirst({\n      where: { email: lead.email, coachId },\n    });\n    if (existingClient) throw new ConflictException('Client existant avec cet email');\n    // ... 8 autres lignes de validation métier\n\n    // 2. Création du client (15 lignes)\n    const client = await this.prisma.client.create({\n      data: {\n        email: lead.email,\n        firstName: lead.firstName,\n        lastName: lead.lastName,\n        phone: lead.phone,\n        coachId,\n        status: 'ACTIVE',\n        createdBy: coachId,\n        convertedFromLeadId: leadId,\n      },\n    });\n    await this.prisma.lead.update({\n      where: { id: leadId },\n      data: { status: 'CONVERTED', convertedAt: new Date(), convertedToClientId: client.id },\n    });\n\n    // 3. Notification Brevo (12 lignes)\n    await this.brevoService.sendTransactionalEmail({\n      to: [{ email: client.email, name: `${client.firstName} ${client.lastName}` }],\n      templateId: 42,\n      params: { firstName: client.firstName, coachName: lead.coachId },\n    });\n    await this.brevoService.addContactToList(client.email, 'clients-actifs');\n\n    // 4. Audit (6 lignes)\n    await this.auditService.log({\n      action: 'LEAD_CONVERTED',\n      entityType: 'client',\n      entityId: client.id,\n      userId: coachId,\n      meta: { fromLeadId: leadId },\n    });\n\n    // 5. Événement domaine (4 lignes)\n    this.eventEmitter.emit('client.created', { clientId: client.id, coachId });\n\n    return ClientDto.fromPrisma(client);\n  }\n}\n","typescript",[147],{"type":31,"tag":148,"props":149,"children":150},"code",{"__ignoreMap":8},[151,163,172,181,203,230,244,280,310,340,370,384,392,478,487,547,662,732,794,860,920,973,990,1032,1041,1049,1058,1116,1133,1162,1192,1222,1252,1265,1287,1308,1330,1339,1355,1401,1433,1519,1535,1543,1552,1590,1710,1733,1800,1816,1875,1883,1892,1930,1952,1974,2004,2025,2059,2075,2083,2092,2177,2184,2216,2225],{"type":31,"tag":152,"props":153,"children":156},"span",{"class":154,"line":155},"line",1,[157],{"type":31,"tag":152,"props":158,"children":160},{"style":159},"--shiki-default:#737994;--shiki-default-font-style:italic;--shiki-dark:#6A737D;--shiki-dark-font-style:inherit",[161],{"type":40,"value":162},"// apps/api/src/application/use-cases/convert-lead-to-client.use-case.ts\n",{"type":31,"tag":152,"props":164,"children":166},{"class":154,"line":165},2,[167],{"type":31,"tag":152,"props":168,"children":169},{"style":159},[170],{"type":40,"value":171},"// Généré par Claude sans prompt de découpe (tel quel)\n",{"type":31,"tag":152,"props":173,"children":175},{"class":154,"line":174},3,[176],{"type":31,"tag":152,"props":177,"children":178},{"emptyLinePlaceholder":13},[179],{"type":40,"value":180},"\n",{"type":31,"tag":152,"props":182,"children":184},{"class":154,"line":183},4,[185,191,197],{"type":31,"tag":152,"props":186,"children":188},{"style":187},"--shiki-default:#8CAAEE;--shiki-default-font-style:italic;--shiki-dark:#E1E4E8;--shiki-dark-font-style:inherit",[189],{"type":40,"value":190},"@",{"type":31,"tag":152,"props":192,"children":194},{"style":193},"--shiki-default:#8CAAEE;--shiki-default-font-style:italic;--shiki-dark:#B392F0;--shiki-dark-font-style:inherit",[195],{"type":40,"value":196},"Injectable",{"type":31,"tag":152,"props":198,"children":200},{"style":199},"--shiki-default:#EF9F76;--shiki-dark:#E1E4E8",[201],{"type":40,"value":202},"()\n",{"type":31,"tag":152,"props":204,"children":206},{"class":154,"line":205},5,[207,213,218,224],{"type":31,"tag":152,"props":208,"children":210},{"style":209},"--shiki-default:#CA9EE6;--shiki-dark:#F97583",[211],{"type":40,"value":212},"export",{"type":31,"tag":152,"props":214,"children":215},{"style":209},[216],{"type":40,"value":217}," class",{"type":31,"tag":152,"props":219,"children":221},{"style":220},"--shiki-default:#E5C890;--shiki-default-font-style:italic;--shiki-dark:#B392F0;--shiki-dark-font-style:inherit",[222],{"type":40,"value":223}," ConvertLeadToClientUseCase",{"type":31,"tag":152,"props":225,"children":227},{"style":226},"--shiki-default:#949CBB;--shiki-dark:#E1E4E8",[228],{"type":40,"value":229}," {\n",{"type":31,"tag":152,"props":231,"children":233},{"class":154,"line":232},6,[234,239],{"type":31,"tag":152,"props":235,"children":236},{"style":209},[237],{"type":40,"value":238},"  constructor",{"type":31,"tag":152,"props":240,"children":241},{"style":226},[242],{"type":40,"value":243},"(\n",{"type":31,"tag":152,"props":245,"children":247},{"class":154,"line":246},7,[248,253,258,264,270,275],{"type":31,"tag":152,"props":249,"children":250},{"style":209},[251],{"type":40,"value":252},"    private",{"type":31,"tag":152,"props":254,"children":255},{"style":209},[256],{"type":40,"value":257}," readonly",{"type":31,"tag":152,"props":259,"children":261},{"style":260},"--shiki-default:#EA999C;--shiki-default-font-style:italic;--shiki-dark:#FFAB70;--shiki-dark-font-style:inherit",[262],{"type":40,"value":263}," prisma",{"type":31,"tag":152,"props":265,"children":267},{"style":266},"--shiki-default:#81C8BE;--shiki-dark:#F97583",[268],{"type":40,"value":269},":",{"type":31,"tag":152,"props":271,"children":272},{"style":220},[273],{"type":40,"value":274}," PrismaClient",{"type":31,"tag":152,"props":276,"children":277},{"style":226},[278],{"type":40,"value":279},",\n",{"type":31,"tag":152,"props":281,"children":283},{"class":154,"line":282},8,[284,288,292,297,301,306],{"type":31,"tag":152,"props":285,"children":286},{"style":209},[287],{"type":40,"value":252},{"type":31,"tag":152,"props":289,"children":290},{"style":209},[291],{"type":40,"value":257},{"type":31,"tag":152,"props":293,"children":294},{"style":260},[295],{"type":40,"value":296}," brevoService",{"type":31,"tag":152,"props":298,"children":299},{"style":266},[300],{"type":40,"value":269},{"type":31,"tag":152,"props":302,"children":303},{"style":220},[304],{"type":40,"value":305}," BrevoService",{"type":31,"tag":152,"props":307,"children":308},{"style":226},[309],{"type":40,"value":279},{"type":31,"tag":152,"props":311,"children":313},{"class":154,"line":312},9,[314,318,322,327,331,336],{"type":31,"tag":152,"props":315,"children":316},{"style":209},[317],{"type":40,"value":252},{"type":31,"tag":152,"props":319,"children":320},{"style":209},[321],{"type":40,"value":257},{"type":31,"tag":152,"props":323,"children":324},{"style":260},[325],{"type":40,"value":326}," auditService",{"type":31,"tag":152,"props":328,"children":329},{"style":266},[330],{"type":40,"value":269},{"type":31,"tag":152,"props":332,"children":333},{"style":220},[334],{"type":40,"value":335}," AuditService",{"type":31,"tag":152,"props":337,"children":338},{"style":226},[339],{"type":40,"value":279},{"type":31,"tag":152,"props":341,"children":343},{"class":154,"line":342},10,[344,348,352,357,361,366],{"type":31,"tag":152,"props":345,"children":346},{"style":209},[347],{"type":40,"value":252},{"type":31,"tag":152,"props":349,"children":350},{"style":209},[351],{"type":40,"value":257},{"type":31,"tag":152,"props":353,"children":354},{"style":260},[355],{"type":40,"value":356}," eventEmitter",{"type":31,"tag":152,"props":358,"children":359},{"style":266},[360],{"type":40,"value":269},{"type":31,"tag":152,"props":362,"children":363},{"style":220},[364],{"type":40,"value":365}," EventEmitter2",{"type":31,"tag":152,"props":367,"children":368},{"style":226},[369],{"type":40,"value":279},{"type":31,"tag":152,"props":371,"children":373},{"class":154,"line":372},11,[374,379],{"type":31,"tag":152,"props":375,"children":376},{"style":226},[377],{"type":40,"value":378},"  )",{"type":31,"tag":152,"props":380,"children":381},{"style":226},[382],{"type":40,"value":383}," {}\n",{"type":31,"tag":152,"props":385,"children":387},{"class":154,"line":386},12,[388],{"type":31,"tag":152,"props":389,"children":390},{"emptyLinePlaceholder":13},[391],{"type":40,"value":180},{"type":31,"tag":152,"props":393,"children":395},{"class":154,"line":394},13,[396,401,406,411,416,420,426,431,436,440,444,449,453,458,464,469,474],{"type":31,"tag":152,"props":397,"children":398},{"style":209},[399],{"type":40,"value":400},"  async",{"type":31,"tag":152,"props":402,"children":403},{"style":193},[404],{"type":40,"value":405}," execute",{"type":31,"tag":152,"props":407,"children":408},{"style":226},[409],{"type":40,"value":410},"(",{"type":31,"tag":152,"props":412,"children":413},{"style":260},[414],{"type":40,"value":415},"leadId",{"type":31,"tag":152,"props":417,"children":418},{"style":266},[419],{"type":40,"value":269},{"type":31,"tag":152,"props":421,"children":423},{"style":422},"--shiki-default:#CA9EE6;--shiki-dark:#79B8FF",[424],{"type":40,"value":425}," string",{"type":31,"tag":152,"props":427,"children":428},{"style":226},[429],{"type":40,"value":430},",",{"type":31,"tag":152,"props":432,"children":433},{"style":260},[434],{"type":40,"value":435}," coachId",{"type":31,"tag":152,"props":437,"children":438},{"style":266},[439],{"type":40,"value":269},{"type":31,"tag":152,"props":441,"children":442},{"style":422},[443],{"type":40,"value":425},{"type":31,"tag":152,"props":445,"children":446},{"style":226},[447],{"type":40,"value":448},")",{"type":31,"tag":152,"props":450,"children":451},{"style":266},[452],{"type":40,"value":269},{"type":31,"tag":152,"props":454,"children":455},{"style":220},[456],{"type":40,"value":457}," Promise",{"type":31,"tag":152,"props":459,"children":461},{"style":460},"--shiki-default:#99D1DB;--shiki-dark:#E1E4E8",[462],{"type":40,"value":463},"\u003C",{"type":31,"tag":152,"props":465,"children":466},{"style":220},[467],{"type":40,"value":468},"ClientDto",{"type":31,"tag":152,"props":470,"children":471},{"style":460},[472],{"type":40,"value":473},">",{"type":31,"tag":152,"props":475,"children":476},{"style":226},[477],{"type":40,"value":229},{"type":31,"tag":152,"props":479,"children":481},{"class":154,"line":480},14,[482],{"type":31,"tag":152,"props":483,"children":484},{"style":159},[485],{"type":40,"value":486},"    // 1. Validation (15 lignes)\n",{"type":31,"tag":152,"props":488,"children":490},{"class":154,"line":489},15,[491,496,502,507,512,517,523,528,532,538,542],{"type":31,"tag":152,"props":492,"children":493},{"style":209},[494],{"type":40,"value":495},"    if",{"type":31,"tag":152,"props":497,"children":499},{"style":498},"--shiki-default:#C6D0F5;--shiki-dark:#E1E4E8",[500],{"type":40,"value":501}," (",{"type":31,"tag":152,"props":503,"children":504},{"style":266},[505],{"type":40,"value":506},"!",{"type":31,"tag":152,"props":508,"children":509},{"style":498},[510],{"type":40,"value":511},"leadId) ",{"type":31,"tag":152,"props":513,"children":514},{"style":209},[515],{"type":40,"value":516},"throw",{"type":31,"tag":152,"props":518,"children":520},{"style":519},"--shiki-default:#CA9EE6;--shiki-default-font-weight:bold;--shiki-dark:#F97583;--shiki-dark-font-weight:inherit",[521],{"type":40,"value":522}," new",{"type":31,"tag":152,"props":524,"children":525},{"style":193},[526],{"type":40,"value":527}," BadRequestException",{"type":31,"tag":152,"props":529,"children":530},{"style":498},[531],{"type":40,"value":410},{"type":31,"tag":152,"props":533,"children":535},{"style":534},"--shiki-default:#A6D189;--shiki-dark:#9ECBFF",[536],{"type":40,"value":537},"'leadId requis'",{"type":31,"tag":152,"props":539,"children":540},{"style":498},[541],{"type":40,"value":448},{"type":31,"tag":152,"props":543,"children":544},{"style":226},[545],{"type":40,"value":546},";\n",{"type":31,"tag":152,"props":548,"children":550},{"class":154,"line":549},16,[551,556,562,567,572,578,584,589,593,598,602,607,611,616,621,625,630,635,639,644,649,654,658],{"type":31,"tag":152,"props":552,"children":553},{"style":209},[554],{"type":40,"value":555},"    const",{"type":31,"tag":152,"props":557,"children":559},{"style":558},"--shiki-default:#C6D0F5;--shiki-dark:#79B8FF",[560],{"type":40,"value":561}," lead",{"type":31,"tag":152,"props":563,"children":564},{"style":266},[565],{"type":40,"value":566}," =",{"type":31,"tag":152,"props":568,"children":569},{"style":209},[570],{"type":40,"value":571}," await",{"type":31,"tag":152,"props":573,"children":575},{"style":574},"--shiki-default:#E78284;--shiki-dark:#79B8FF",[576],{"type":40,"value":577}," this",{"type":31,"tag":152,"props":579,"children":581},{"style":580},"--shiki-default:#81C8BE;--shiki-dark:#E1E4E8",[582],{"type":40,"value":583},".",{"type":31,"tag":152,"props":585,"children":586},{"style":498},[587],{"type":40,"value":588},"prisma",{"type":31,"tag":152,"props":590,"children":591},{"style":580},[592],{"type":40,"value":583},{"type":31,"tag":152,"props":594,"children":595},{"style":498},[596],{"type":40,"value":597},"lead",{"type":31,"tag":152,"props":599,"children":600},{"style":580},[601],{"type":40,"value":583},{"type":31,"tag":152,"props":603,"children":604},{"style":193},[605],{"type":40,"value":606},"findUnique",{"type":31,"tag":152,"props":608,"children":609},{"style":498},[610],{"type":40,"value":410},{"type":31,"tag":152,"props":612,"children":613},{"style":226},[614],{"type":40,"value":615},"{",{"type":31,"tag":152,"props":617,"children":618},{"style":498},[619],{"type":40,"value":620}," where",{"type":31,"tag":152,"props":622,"children":623},{"style":580},[624],{"type":40,"value":269},{"type":31,"tag":152,"props":626,"children":627},{"style":226},[628],{"type":40,"value":629}," {",{"type":31,"tag":152,"props":631,"children":632},{"style":498},[633],{"type":40,"value":634}," id",{"type":31,"tag":152,"props":636,"children":637},{"style":580},[638],{"type":40,"value":269},{"type":31,"tag":152,"props":640,"children":641},{"style":498},[642],{"type":40,"value":643}," leadId ",{"type":31,"tag":152,"props":645,"children":646},{"style":226},[647],{"type":40,"value":648},"}",{"type":31,"tag":152,"props":650,"children":651},{"style":226},[652],{"type":40,"value":653}," }",{"type":31,"tag":152,"props":655,"children":656},{"style":498},[657],{"type":40,"value":448},{"type":31,"tag":152,"props":659,"children":660},{"style":226},[661],{"type":40,"value":546},{"type":31,"tag":152,"props":663,"children":665},{"class":154,"line":664},17,[666,670,674,678,683,687,691,696,700,705,711,715,719,724,728],{"type":31,"tag":152,"props":667,"children":668},{"style":209},[669],{"type":40,"value":495},{"type":31,"tag":152,"props":671,"children":672},{"style":498},[673],{"type":40,"value":501},{"type":31,"tag":152,"props":675,"children":676},{"style":266},[677],{"type":40,"value":506},{"type":31,"tag":152,"props":679,"children":680},{"style":498},[681],{"type":40,"value":682},"lead) ",{"type":31,"tag":152,"props":684,"children":685},{"style":209},[686],{"type":40,"value":516},{"type":31,"tag":152,"props":688,"children":689},{"style":519},[690],{"type":40,"value":522},{"type":31,"tag":152,"props":692,"children":693},{"style":193},[694],{"type":40,"value":695}," NotFoundException",{"type":31,"tag":152,"props":697,"children":698},{"style":498},[699],{"type":40,"value":410},{"type":31,"tag":152,"props":701,"children":702},{"style":534},[703],{"type":40,"value":704},"`Lead ",{"type":31,"tag":152,"props":706,"children":708},{"style":707},"--shiki-default:#949CBB;--shiki-dark:#9ECBFF",[709],{"type":40,"value":710},"${",{"type":31,"tag":152,"props":712,"children":713},{"style":498},[714],{"type":40,"value":415},{"type":31,"tag":152,"props":716,"children":717},{"style":707},[718],{"type":40,"value":648},{"type":31,"tag":152,"props":720,"children":721},{"style":534},[722],{"type":40,"value":723}," introuvable`",{"type":31,"tag":152,"props":725,"children":726},{"style":498},[727],{"type":40,"value":448},{"type":31,"tag":152,"props":729,"children":730},{"style":226},[731],{"type":40,"value":546},{"type":31,"tag":152,"props":733,"children":735},{"class":154,"line":734},18,[736,740,745,749,754,759,764,768,772,777,781,786,790],{"type":31,"tag":152,"props":737,"children":738},{"style":209},[739],{"type":40,"value":495},{"type":31,"tag":152,"props":741,"children":742},{"style":498},[743],{"type":40,"value":744}," (lead",{"type":31,"tag":152,"props":746,"children":747},{"style":580},[748],{"type":40,"value":583},{"type":31,"tag":152,"props":750,"children":751},{"style":498},[752],{"type":40,"value":753},"coachId ",{"type":31,"tag":152,"props":755,"children":756},{"style":266},[757],{"type":40,"value":758},"!==",{"type":31,"tag":152,"props":760,"children":761},{"style":498},[762],{"type":40,"value":763}," coachId) ",{"type":31,"tag":152,"props":765,"children":766},{"style":209},[767],{"type":40,"value":516},{"type":31,"tag":152,"props":769,"children":770},{"style":519},[771],{"type":40,"value":522},{"type":31,"tag":152,"props":773,"children":774},{"style":193},[775],{"type":40,"value":776}," ForbiddenException",{"type":31,"tag":152,"props":778,"children":779},{"style":498},[780],{"type":40,"value":410},{"type":31,"tag":152,"props":782,"children":783},{"style":534},[784],{"type":40,"value":785},"'Lead hors scope'",{"type":31,"tag":152,"props":787,"children":788},{"style":498},[789],{"type":40,"value":448},{"type":31,"tag":152,"props":791,"children":792},{"style":226},[793],{"type":40,"value":546},{"type":31,"tag":152,"props":795,"children":797},{"class":154,"line":796},19,[798,802,806,810,815,820,825,830,834,838,843,847,852,856],{"type":31,"tag":152,"props":799,"children":800},{"style":209},[801],{"type":40,"value":495},{"type":31,"tag":152,"props":803,"children":804},{"style":498},[805],{"type":40,"value":744},{"type":31,"tag":152,"props":807,"children":808},{"style":580},[809],{"type":40,"value":583},{"type":31,"tag":152,"props":811,"children":812},{"style":498},[813],{"type":40,"value":814},"status ",{"type":31,"tag":152,"props":816,"children":817},{"style":266},[818],{"type":40,"value":819},"===",{"type":31,"tag":152,"props":821,"children":822},{"style":534},[823],{"type":40,"value":824}," 'CONVERTED'",{"type":31,"tag":152,"props":826,"children":827},{"style":498},[828],{"type":40,"value":829},") ",{"type":31,"tag":152,"props":831,"children":832},{"style":209},[833],{"type":40,"value":516},{"type":31,"tag":152,"props":835,"children":836},{"style":519},[837],{"type":40,"value":522},{"type":31,"tag":152,"props":839,"children":840},{"style":193},[841],{"type":40,"value":842}," ConflictException",{"type":31,"tag":152,"props":844,"children":845},{"style":498},[846],{"type":40,"value":410},{"type":31,"tag":152,"props":848,"children":849},{"style":534},[850],{"type":40,"value":851},"'Lead déjà converti'",{"type":31,"tag":152,"props":853,"children":854},{"style":498},[855],{"type":40,"value":448},{"type":31,"tag":152,"props":857,"children":858},{"style":226},[859],{"type":40,"value":546},{"type":31,"tag":152,"props":861,"children":863},{"class":154,"line":862},20,[864,868,873,877,881,885,889,893,897,902,906,911,915],{"type":31,"tag":152,"props":865,"children":866},{"style":209},[867],{"type":40,"value":555},{"type":31,"tag":152,"props":869,"children":870},{"style":558},[871],{"type":40,"value":872}," existingClient",{"type":31,"tag":152,"props":874,"children":875},{"style":266},[876],{"type":40,"value":566},{"type":31,"tag":152,"props":878,"children":879},{"style":209},[880],{"type":40,"value":571},{"type":31,"tag":152,"props":882,"children":883},{"style":574},[884],{"type":40,"value":577},{"type":31,"tag":152,"props":886,"children":887},{"style":580},[888],{"type":40,"value":583},{"type":31,"tag":152,"props":890,"children":891},{"style":498},[892],{"type":40,"value":588},{"type":31,"tag":152,"props":894,"children":895},{"style":580},[896],{"type":40,"value":583},{"type":31,"tag":152,"props":898,"children":899},{"style":498},[900],{"type":40,"value":901},"client",{"type":31,"tag":152,"props":903,"children":904},{"style":580},[905],{"type":40,"value":583},{"type":31,"tag":152,"props":907,"children":908},{"style":193},[909],{"type":40,"value":910},"findFirst",{"type":31,"tag":152,"props":912,"children":913},{"style":498},[914],{"type":40,"value":410},{"type":31,"tag":152,"props":916,"children":917},{"style":226},[918],{"type":40,"value":919},"{\n",{"type":31,"tag":152,"props":921,"children":923},{"class":154,"line":922},21,[924,929,933,937,942,946,950,954,959,963,968],{"type":31,"tag":152,"props":925,"children":926},{"style":498},[927],{"type":40,"value":928},"      where",{"type":31,"tag":152,"props":930,"children":931},{"style":580},[932],{"type":40,"value":269},{"type":31,"tag":152,"props":934,"children":935},{"style":226},[936],{"type":40,"value":629},{"type":31,"tag":152,"props":938,"children":939},{"style":498},[940],{"type":40,"value":941}," email",{"type":31,"tag":152,"props":943,"children":944},{"style":580},[945],{"type":40,"value":269},{"type":31,"tag":152,"props":947,"children":948},{"style":498},[949],{"type":40,"value":561},{"type":31,"tag":152,"props":951,"children":952},{"style":580},[953],{"type":40,"value":583},{"type":31,"tag":152,"props":955,"children":956},{"style":498},[957],{"type":40,"value":958},"email",{"type":31,"tag":152,"props":960,"children":961},{"style":226},[962],{"type":40,"value":430},{"type":31,"tag":152,"props":964,"children":965},{"style":498},[966],{"type":40,"value":967}," coachId ",{"type":31,"tag":152,"props":969,"children":970},{"style":226},[971],{"type":40,"value":972},"},\n",{"type":31,"tag":152,"props":974,"children":976},{"class":154,"line":975},22,[977,982,986],{"type":31,"tag":152,"props":978,"children":979},{"style":226},[980],{"type":40,"value":981},"    }",{"type":31,"tag":152,"props":983,"children":984},{"style":498},[985],{"type":40,"value":448},{"type":31,"tag":152,"props":987,"children":988},{"style":226},[989],{"type":40,"value":546},{"type":31,"tag":152,"props":991,"children":993},{"class":154,"line":992},23,[994,998,1003,1007,1011,1015,1019,1024,1028],{"type":31,"tag":152,"props":995,"children":996},{"style":209},[997],{"type":40,"value":495},{"type":31,"tag":152,"props":999,"children":1000},{"style":498},[1001],{"type":40,"value":1002}," (existingClient) ",{"type":31,"tag":152,"props":1004,"children":1005},{"style":209},[1006],{"type":40,"value":516},{"type":31,"tag":152,"props":1008,"children":1009},{"style":519},[1010],{"type":40,"value":522},{"type":31,"tag":152,"props":1012,"children":1013},{"style":193},[1014],{"type":40,"value":842},{"type":31,"tag":152,"props":1016,"children":1017},{"style":498},[1018],{"type":40,"value":410},{"type":31,"tag":152,"props":1020,"children":1021},{"style":534},[1022],{"type":40,"value":1023},"'Client existant avec cet email'",{"type":31,"tag":152,"props":1025,"children":1026},{"style":498},[1027],{"type":40,"value":448},{"type":31,"tag":152,"props":1029,"children":1030},{"style":226},[1031],{"type":40,"value":546},{"type":31,"tag":152,"props":1033,"children":1035},{"class":154,"line":1034},24,[1036],{"type":31,"tag":152,"props":1037,"children":1038},{"style":159},[1039],{"type":40,"value":1040},"    // ... 8 autres lignes de validation métier\n",{"type":31,"tag":152,"props":1042,"children":1044},{"class":154,"line":1043},25,[1045],{"type":31,"tag":152,"props":1046,"children":1047},{"emptyLinePlaceholder":13},[1048],{"type":40,"value":180},{"type":31,"tag":152,"props":1050,"children":1052},{"class":154,"line":1051},26,[1053],{"type":31,"tag":152,"props":1054,"children":1055},{"style":159},[1056],{"type":40,"value":1057},"    // 2. Création du client (15 lignes)\n",{"type":31,"tag":152,"props":1059,"children":1061},{"class":154,"line":1060},27,[1062,1066,1071,1075,1079,1083,1087,1091,1095,1099,1103,1108,1112],{"type":31,"tag":152,"props":1063,"children":1064},{"style":209},[1065],{"type":40,"value":555},{"type":31,"tag":152,"props":1067,"children":1068},{"style":558},[1069],{"type":40,"value":1070}," client",{"type":31,"tag":152,"props":1072,"children":1073},{"style":266},[1074],{"type":40,"value":566},{"type":31,"tag":152,"props":1076,"children":1077},{"style":209},[1078],{"type":40,"value":571},{"type":31,"tag":152,"props":1080,"children":1081},{"style":574},[1082],{"type":40,"value":577},{"type":31,"tag":152,"props":1084,"children":1085},{"style":580},[1086],{"type":40,"value":583},{"type":31,"tag":152,"props":1088,"children":1089},{"style":498},[1090],{"type":40,"value":588},{"type":31,"tag":152,"props":1092,"children":1093},{"style":580},[1094],{"type":40,"value":583},{"type":31,"tag":152,"props":1096,"children":1097},{"style":498},[1098],{"type":40,"value":901},{"type":31,"tag":152,"props":1100,"children":1101},{"style":580},[1102],{"type":40,"value":583},{"type":31,"tag":152,"props":1104,"children":1105},{"style":193},[1106],{"type":40,"value":1107},"create",{"type":31,"tag":152,"props":1109,"children":1110},{"style":498},[1111],{"type":40,"value":410},{"type":31,"tag":152,"props":1113,"children":1114},{"style":226},[1115],{"type":40,"value":919},{"type":31,"tag":152,"props":1117,"children":1119},{"class":154,"line":1118},28,[1120,1125,1129],{"type":31,"tag":152,"props":1121,"children":1122},{"style":498},[1123],{"type":40,"value":1124},"      data",{"type":31,"tag":152,"props":1126,"children":1127},{"style":580},[1128],{"type":40,"value":269},{"type":31,"tag":152,"props":1130,"children":1131},{"style":226},[1132],{"type":40,"value":229},{"type":31,"tag":152,"props":1134,"children":1136},{"class":154,"line":1135},29,[1137,1142,1146,1150,1154,1158],{"type":31,"tag":152,"props":1138,"children":1139},{"style":498},[1140],{"type":40,"value":1141},"        email",{"type":31,"tag":152,"props":1143,"children":1144},{"style":580},[1145],{"type":40,"value":269},{"type":31,"tag":152,"props":1147,"children":1148},{"style":498},[1149],{"type":40,"value":561},{"type":31,"tag":152,"props":1151,"children":1152},{"style":580},[1153],{"type":40,"value":583},{"type":31,"tag":152,"props":1155,"children":1156},{"style":498},[1157],{"type":40,"value":958},{"type":31,"tag":152,"props":1159,"children":1160},{"style":226},[1161],{"type":40,"value":279},{"type":31,"tag":152,"props":1163,"children":1165},{"class":154,"line":1164},30,[1166,1171,1175,1179,1183,1188],{"type":31,"tag":152,"props":1167,"children":1168},{"style":498},[1169],{"type":40,"value":1170},"        firstName",{"type":31,"tag":152,"props":1172,"children":1173},{"style":580},[1174],{"type":40,"value":269},{"type":31,"tag":152,"props":1176,"children":1177},{"style":498},[1178],{"type":40,"value":561},{"type":31,"tag":152,"props":1180,"children":1181},{"style":580},[1182],{"type":40,"value":583},{"type":31,"tag":152,"props":1184,"children":1185},{"style":498},[1186],{"type":40,"value":1187},"firstName",{"type":31,"tag":152,"props":1189,"children":1190},{"style":226},[1191],{"type":40,"value":279},{"type":31,"tag":152,"props":1193,"children":1195},{"class":154,"line":1194},31,[1196,1201,1205,1209,1213,1218],{"type":31,"tag":152,"props":1197,"children":1198},{"style":498},[1199],{"type":40,"value":1200},"        lastName",{"type":31,"tag":152,"props":1202,"children":1203},{"style":580},[1204],{"type":40,"value":269},{"type":31,"tag":152,"props":1206,"children":1207},{"style":498},[1208],{"type":40,"value":561},{"type":31,"tag":152,"props":1210,"children":1211},{"style":580},[1212],{"type":40,"value":583},{"type":31,"tag":152,"props":1214,"children":1215},{"style":498},[1216],{"type":40,"value":1217},"lastName",{"type":31,"tag":152,"props":1219,"children":1220},{"style":226},[1221],{"type":40,"value":279},{"type":31,"tag":152,"props":1223,"children":1225},{"class":154,"line":1224},32,[1226,1231,1235,1239,1243,1248],{"type":31,"tag":152,"props":1227,"children":1228},{"style":498},[1229],{"type":40,"value":1230},"        phone",{"type":31,"tag":152,"props":1232,"children":1233},{"style":580},[1234],{"type":40,"value":269},{"type":31,"tag":152,"props":1236,"children":1237},{"style":498},[1238],{"type":40,"value":561},{"type":31,"tag":152,"props":1240,"children":1241},{"style":580},[1242],{"type":40,"value":583},{"type":31,"tag":152,"props":1244,"children":1245},{"style":498},[1246],{"type":40,"value":1247},"phone",{"type":31,"tag":152,"props":1249,"children":1250},{"style":226},[1251],{"type":40,"value":279},{"type":31,"tag":152,"props":1253,"children":1255},{"class":154,"line":1254},33,[1256,1261],{"type":31,"tag":152,"props":1257,"children":1258},{"style":498},[1259],{"type":40,"value":1260},"        coachId",{"type":31,"tag":152,"props":1262,"children":1263},{"style":226},[1264],{"type":40,"value":279},{"type":31,"tag":152,"props":1266,"children":1268},{"class":154,"line":1267},34,[1269,1274,1278,1283],{"type":31,"tag":152,"props":1270,"children":1271},{"style":498},[1272],{"type":40,"value":1273},"        status",{"type":31,"tag":152,"props":1275,"children":1276},{"style":580},[1277],{"type":40,"value":269},{"type":31,"tag":152,"props":1279,"children":1280},{"style":534},[1281],{"type":40,"value":1282}," 'ACTIVE'",{"type":31,"tag":152,"props":1284,"children":1285},{"style":226},[1286],{"type":40,"value":279},{"type":31,"tag":152,"props":1288,"children":1290},{"class":154,"line":1289},35,[1291,1296,1300,1304],{"type":31,"tag":152,"props":1292,"children":1293},{"style":498},[1294],{"type":40,"value":1295},"        createdBy",{"type":31,"tag":152,"props":1297,"children":1298},{"style":580},[1299],{"type":40,"value":269},{"type":31,"tag":152,"props":1301,"children":1302},{"style":498},[1303],{"type":40,"value":435},{"type":31,"tag":152,"props":1305,"children":1306},{"style":226},[1307],{"type":40,"value":279},{"type":31,"tag":152,"props":1309,"children":1311},{"class":154,"line":1310},36,[1312,1317,1321,1326],{"type":31,"tag":152,"props":1313,"children":1314},{"style":498},[1315],{"type":40,"value":1316},"        convertedFromLeadId",{"type":31,"tag":152,"props":1318,"children":1319},{"style":580},[1320],{"type":40,"value":269},{"type":31,"tag":152,"props":1322,"children":1323},{"style":498},[1324],{"type":40,"value":1325}," leadId",{"type":31,"tag":152,"props":1327,"children":1328},{"style":226},[1329],{"type":40,"value":279},{"type":31,"tag":152,"props":1331,"children":1333},{"class":154,"line":1332},37,[1334],{"type":31,"tag":152,"props":1335,"children":1336},{"style":226},[1337],{"type":40,"value":1338},"      },\n",{"type":31,"tag":152,"props":1340,"children":1342},{"class":154,"line":1341},38,[1343,1347,1351],{"type":31,"tag":152,"props":1344,"children":1345},{"style":226},[1346],{"type":40,"value":981},{"type":31,"tag":152,"props":1348,"children":1349},{"style":498},[1350],{"type":40,"value":448},{"type":31,"tag":152,"props":1352,"children":1353},{"style":226},[1354],{"type":40,"value":546},{"type":31,"tag":152,"props":1356,"children":1358},{"class":154,"line":1357},39,[1359,1364,1368,1372,1376,1380,1384,1388,1393,1397],{"type":31,"tag":152,"props":1360,"children":1361},{"style":209},[1362],{"type":40,"value":1363},"    await",{"type":31,"tag":152,"props":1365,"children":1366},{"style":574},[1367],{"type":40,"value":577},{"type":31,"tag":152,"props":1369,"children":1370},{"style":580},[1371],{"type":40,"value":583},{"type":31,"tag":152,"props":1373,"children":1374},{"style":498},[1375],{"type":40,"value":588},{"type":31,"tag":152,"props":1377,"children":1378},{"style":580},[1379],{"type":40,"value":583},{"type":31,"tag":152,"props":1381,"children":1382},{"style":498},[1383],{"type":40,"value":597},{"type":31,"tag":152,"props":1385,"children":1386},{"style":580},[1387],{"type":40,"value":583},{"type":31,"tag":152,"props":1389,"children":1390},{"style":193},[1391],{"type":40,"value":1392},"update",{"type":31,"tag":152,"props":1394,"children":1395},{"style":498},[1396],{"type":40,"value":410},{"type":31,"tag":152,"props":1398,"children":1399},{"style":226},[1400],{"type":40,"value":919},{"type":31,"tag":152,"props":1402,"children":1404},{"class":154,"line":1403},40,[1405,1409,1413,1417,1421,1425,1429],{"type":31,"tag":152,"props":1406,"children":1407},{"style":498},[1408],{"type":40,"value":928},{"type":31,"tag":152,"props":1410,"children":1411},{"style":580},[1412],{"type":40,"value":269},{"type":31,"tag":152,"props":1414,"children":1415},{"style":226},[1416],{"type":40,"value":629},{"type":31,"tag":152,"props":1418,"children":1419},{"style":498},[1420],{"type":40,"value":634},{"type":31,"tag":152,"props":1422,"children":1423},{"style":580},[1424],{"type":40,"value":269},{"type":31,"tag":152,"props":1426,"children":1427},{"style":498},[1428],{"type":40,"value":643},{"type":31,"tag":152,"props":1430,"children":1431},{"style":226},[1432],{"type":40,"value":972},{"type":31,"tag":152,"props":1434,"children":1436},{"class":154,"line":1435},41,[1437,1441,1445,1449,1454,1458,1462,1466,1471,1475,1479,1484,1489,1493,1498,1502,1506,1510,1515],{"type":31,"tag":152,"props":1438,"children":1439},{"style":498},[1440],{"type":40,"value":1124},{"type":31,"tag":152,"props":1442,"children":1443},{"style":580},[1444],{"type":40,"value":269},{"type":31,"tag":152,"props":1446,"children":1447},{"style":226},[1448],{"type":40,"value":629},{"type":31,"tag":152,"props":1450,"children":1451},{"style":498},[1452],{"type":40,"value":1453}," status",{"type":31,"tag":152,"props":1455,"children":1456},{"style":580},[1457],{"type":40,"value":269},{"type":31,"tag":152,"props":1459,"children":1460},{"style":534},[1461],{"type":40,"value":824},{"type":31,"tag":152,"props":1463,"children":1464},{"style":226},[1465],{"type":40,"value":430},{"type":31,"tag":152,"props":1467,"children":1468},{"style":498},[1469],{"type":40,"value":1470}," convertedAt",{"type":31,"tag":152,"props":1472,"children":1473},{"style":580},[1474],{"type":40,"value":269},{"type":31,"tag":152,"props":1476,"children":1477},{"style":519},[1478],{"type":40,"value":522},{"type":31,"tag":152,"props":1480,"children":1481},{"style":193},[1482],{"type":40,"value":1483}," Date",{"type":31,"tag":152,"props":1485,"children":1486},{"style":498},[1487],{"type":40,"value":1488},"()",{"type":31,"tag":152,"props":1490,"children":1491},{"style":226},[1492],{"type":40,"value":430},{"type":31,"tag":152,"props":1494,"children":1495},{"style":498},[1496],{"type":40,"value":1497}," convertedToClientId",{"type":31,"tag":152,"props":1499,"children":1500},{"style":580},[1501],{"type":40,"value":269},{"type":31,"tag":152,"props":1503,"children":1504},{"style":498},[1505],{"type":40,"value":1070},{"type":31,"tag":152,"props":1507,"children":1508},{"style":580},[1509],{"type":40,"value":583},{"type":31,"tag":152,"props":1511,"children":1512},{"style":498},[1513],{"type":40,"value":1514},"id ",{"type":31,"tag":152,"props":1516,"children":1517},{"style":226},[1518],{"type":40,"value":972},{"type":31,"tag":152,"props":1520,"children":1522},{"class":154,"line":1521},42,[1523,1527,1531],{"type":31,"tag":152,"props":1524,"children":1525},{"style":226},[1526],{"type":40,"value":981},{"type":31,"tag":152,"props":1528,"children":1529},{"style":498},[1530],{"type":40,"value":448},{"type":31,"tag":152,"props":1532,"children":1533},{"style":226},[1534],{"type":40,"value":546},{"type":31,"tag":152,"props":1536,"children":1538},{"class":154,"line":1537},43,[1539],{"type":31,"tag":152,"props":1540,"children":1541},{"emptyLinePlaceholder":13},[1542],{"type":40,"value":180},{"type":31,"tag":152,"props":1544,"children":1546},{"class":154,"line":1545},44,[1547],{"type":31,"tag":152,"props":1548,"children":1549},{"style":159},[1550],{"type":40,"value":1551},"    // 3. Notification Brevo (12 lignes)\n",{"type":31,"tag":152,"props":1553,"children":1555},{"class":154,"line":1554},45,[1556,1560,1564,1568,1573,1577,1582,1586],{"type":31,"tag":152,"props":1557,"children":1558},{"style":209},[1559],{"type":40,"value":1363},{"type":31,"tag":152,"props":1561,"children":1562},{"style":574},[1563],{"type":40,"value":577},{"type":31,"tag":152,"props":1565,"children":1566},{"style":580},[1567],{"type":40,"value":583},{"type":31,"tag":152,"props":1569,"children":1570},{"style":498},[1571],{"type":40,"value":1572},"brevoService",{"type":31,"tag":152,"props":1574,"children":1575},{"style":580},[1576],{"type":40,"value":583},{"type":31,"tag":152,"props":1578,"children":1579},{"style":193},[1580],{"type":40,"value":1581},"sendTransactionalEmail",{"type":31,"tag":152,"props":1583,"children":1584},{"style":498},[1585],{"type":40,"value":410},{"type":31,"tag":152,"props":1587,"children":1588},{"style":226},[1589],{"type":40,"value":919},{"type":31,"tag":152,"props":1591,"children":1593},{"class":154,"line":1592},46,[1594,1599,1603,1608,1612,1616,1620,1624,1628,1632,1636,1641,1645,1650,1654,1658,1663,1667,1671,1676,1680,1684,1688,1692,1697,1701,1706],{"type":31,"tag":152,"props":1595,"children":1596},{"style":498},[1597],{"type":40,"value":1598},"      to",{"type":31,"tag":152,"props":1600,"children":1601},{"style":580},[1602],{"type":40,"value":269},{"type":31,"tag":152,"props":1604,"children":1605},{"style":498},[1606],{"type":40,"value":1607}," [",{"type":31,"tag":152,"props":1609,"children":1610},{"style":226},[1611],{"type":40,"value":615},{"type":31,"tag":152,"props":1613,"children":1614},{"style":498},[1615],{"type":40,"value":941},{"type":31,"tag":152,"props":1617,"children":1618},{"style":580},[1619],{"type":40,"value":269},{"type":31,"tag":152,"props":1621,"children":1622},{"style":498},[1623],{"type":40,"value":1070},{"type":31,"tag":152,"props":1625,"children":1626},{"style":580},[1627],{"type":40,"value":583},{"type":31,"tag":152,"props":1629,"children":1630},{"style":498},[1631],{"type":40,"value":958},{"type":31,"tag":152,"props":1633,"children":1634},{"style":226},[1635],{"type":40,"value":430},{"type":31,"tag":152,"props":1637,"children":1638},{"style":498},[1639],{"type":40,"value":1640}," name",{"type":31,"tag":152,"props":1642,"children":1643},{"style":580},[1644],{"type":40,"value":269},{"type":31,"tag":152,"props":1646,"children":1647},{"style":534},[1648],{"type":40,"value":1649}," `",{"type":31,"tag":152,"props":1651,"children":1652},{"style":707},[1653],{"type":40,"value":710},{"type":31,"tag":152,"props":1655,"children":1656},{"style":498},[1657],{"type":40,"value":901},{"type":31,"tag":152,"props":1659,"children":1661},{"style":1660},"--shiki-default:#81C8BE;--shiki-dark:#9ECBFF",[1662],{"type":40,"value":583},{"type":31,"tag":152,"props":1664,"children":1665},{"style":498},[1666],{"type":40,"value":1187},{"type":31,"tag":152,"props":1668,"children":1669},{"style":707},[1670],{"type":40,"value":648},{"type":31,"tag":152,"props":1672,"children":1673},{"style":707},[1674],{"type":40,"value":1675}," ${",{"type":31,"tag":152,"props":1677,"children":1678},{"style":498},[1679],{"type":40,"value":901},{"type":31,"tag":152,"props":1681,"children":1682},{"style":1660},[1683],{"type":40,"value":583},{"type":31,"tag":152,"props":1685,"children":1686},{"style":498},[1687],{"type":40,"value":1217},{"type":31,"tag":152,"props":1689,"children":1690},{"style":707},[1691],{"type":40,"value":648},{"type":31,"tag":152,"props":1693,"children":1694},{"style":534},[1695],{"type":40,"value":1696},"`",{"type":31,"tag":152,"props":1698,"children":1699},{"style":226},[1700],{"type":40,"value":653},{"type":31,"tag":152,"props":1702,"children":1703},{"style":498},[1704],{"type":40,"value":1705},"]",{"type":31,"tag":152,"props":1707,"children":1708},{"style":226},[1709],{"type":40,"value":279},{"type":31,"tag":152,"props":1711,"children":1713},{"class":154,"line":1712},47,[1714,1719,1723,1729],{"type":31,"tag":152,"props":1715,"children":1716},{"style":498},[1717],{"type":40,"value":1718},"      templateId",{"type":31,"tag":152,"props":1720,"children":1721},{"style":580},[1722],{"type":40,"value":269},{"type":31,"tag":152,"props":1724,"children":1726},{"style":1725},"--shiki-default:#EF9F76;--shiki-dark:#79B8FF",[1727],{"type":40,"value":1728}," 42",{"type":31,"tag":152,"props":1730,"children":1731},{"style":226},[1732],{"type":40,"value":279},{"type":31,"tag":152,"props":1734,"children":1736},{"class":154,"line":1735},48,[1737,1742,1746,1750,1755,1759,1763,1767,1771,1775,1780,1784,1788,1792,1796],{"type":31,"tag":152,"props":1738,"children":1739},{"style":498},[1740],{"type":40,"value":1741},"      params",{"type":31,"tag":152,"props":1743,"children":1744},{"style":580},[1745],{"type":40,"value":269},{"type":31,"tag":152,"props":1747,"children":1748},{"style":226},[1749],{"type":40,"value":629},{"type":31,"tag":152,"props":1751,"children":1752},{"style":498},[1753],{"type":40,"value":1754}," firstName",{"type":31,"tag":152,"props":1756,"children":1757},{"style":580},[1758],{"type":40,"value":269},{"type":31,"tag":152,"props":1760,"children":1761},{"style":498},[1762],{"type":40,"value":1070},{"type":31,"tag":152,"props":1764,"children":1765},{"style":580},[1766],{"type":40,"value":583},{"type":31,"tag":152,"props":1768,"children":1769},{"style":498},[1770],{"type":40,"value":1187},{"type":31,"tag":152,"props":1772,"children":1773},{"style":226},[1774],{"type":40,"value":430},{"type":31,"tag":152,"props":1776,"children":1777},{"style":498},[1778],{"type":40,"value":1779}," coachName",{"type":31,"tag":152,"props":1781,"children":1782},{"style":580},[1783],{"type":40,"value":269},{"type":31,"tag":152,"props":1785,"children":1786},{"style":498},[1787],{"type":40,"value":561},{"type":31,"tag":152,"props":1789,"children":1790},{"style":580},[1791],{"type":40,"value":583},{"type":31,"tag":152,"props":1793,"children":1794},{"style":498},[1795],{"type":40,"value":753},{"type":31,"tag":152,"props":1797,"children":1798},{"style":226},[1799],{"type":40,"value":972},{"type":31,"tag":152,"props":1801,"children":1803},{"class":154,"line":1802},49,[1804,1808,1812],{"type":31,"tag":152,"props":1805,"children":1806},{"style":226},[1807],{"type":40,"value":981},{"type":31,"tag":152,"props":1809,"children":1810},{"style":498},[1811],{"type":40,"value":448},{"type":31,"tag":152,"props":1813,"children":1814},{"style":226},[1815],{"type":40,"value":546},{"type":31,"tag":152,"props":1817,"children":1819},{"class":154,"line":1818},50,[1820,1824,1828,1832,1836,1840,1845,1850,1854,1858,1862,1867,1871],{"type":31,"tag":152,"props":1821,"children":1822},{"style":209},[1823],{"type":40,"value":1363},{"type":31,"tag":152,"props":1825,"children":1826},{"style":574},[1827],{"type":40,"value":577},{"type":31,"tag":152,"props":1829,"children":1830},{"style":580},[1831],{"type":40,"value":583},{"type":31,"tag":152,"props":1833,"children":1834},{"style":498},[1835],{"type":40,"value":1572},{"type":31,"tag":152,"props":1837,"children":1838},{"style":580},[1839],{"type":40,"value":583},{"type":31,"tag":152,"props":1841,"children":1842},{"style":193},[1843],{"type":40,"value":1844},"addContactToList",{"type":31,"tag":152,"props":1846,"children":1847},{"style":498},[1848],{"type":40,"value":1849},"(client",{"type":31,"tag":152,"props":1851,"children":1852},{"style":580},[1853],{"type":40,"value":583},{"type":31,"tag":152,"props":1855,"children":1856},{"style":498},[1857],{"type":40,"value":958},{"type":31,"tag":152,"props":1859,"children":1860},{"style":226},[1861],{"type":40,"value":430},{"type":31,"tag":152,"props":1863,"children":1864},{"style":534},[1865],{"type":40,"value":1866}," 'clients-actifs'",{"type":31,"tag":152,"props":1868,"children":1869},{"style":498},[1870],{"type":40,"value":448},{"type":31,"tag":152,"props":1872,"children":1873},{"style":226},[1874],{"type":40,"value":546},{"type":31,"tag":152,"props":1876,"children":1878},{"class":154,"line":1877},51,[1879],{"type":31,"tag":152,"props":1880,"children":1881},{"emptyLinePlaceholder":13},[1882],{"type":40,"value":180},{"type":31,"tag":152,"props":1884,"children":1886},{"class":154,"line":1885},52,[1887],{"type":31,"tag":152,"props":1888,"children":1889},{"style":159},[1890],{"type":40,"value":1891},"    // 4. Audit (6 lignes)\n",{"type":31,"tag":152,"props":1893,"children":1895},{"class":154,"line":1894},53,[1896,1900,1904,1908,1913,1917,1922,1926],{"type":31,"tag":152,"props":1897,"children":1898},{"style":209},[1899],{"type":40,"value":1363},{"type":31,"tag":152,"props":1901,"children":1902},{"style":574},[1903],{"type":40,"value":577},{"type":31,"tag":152,"props":1905,"children":1906},{"style":580},[1907],{"type":40,"value":583},{"type":31,"tag":152,"props":1909,"children":1910},{"style":498},[1911],{"type":40,"value":1912},"auditService",{"type":31,"tag":152,"props":1914,"children":1915},{"style":580},[1916],{"type":40,"value":583},{"type":31,"tag":152,"props":1918,"children":1919},{"style":193},[1920],{"type":40,"value":1921},"log",{"type":31,"tag":152,"props":1923,"children":1924},{"style":498},[1925],{"type":40,"value":410},{"type":31,"tag":152,"props":1927,"children":1928},{"style":226},[1929],{"type":40,"value":919},{"type":31,"tag":152,"props":1931,"children":1933},{"class":154,"line":1932},54,[1934,1939,1943,1948],{"type":31,"tag":152,"props":1935,"children":1936},{"style":498},[1937],{"type":40,"value":1938},"      action",{"type":31,"tag":152,"props":1940,"children":1941},{"style":580},[1942],{"type":40,"value":269},{"type":31,"tag":152,"props":1944,"children":1945},{"style":534},[1946],{"type":40,"value":1947}," 'LEAD_CONVERTED'",{"type":31,"tag":152,"props":1949,"children":1950},{"style":226},[1951],{"type":40,"value":279},{"type":31,"tag":152,"props":1953,"children":1955},{"class":154,"line":1954},55,[1956,1961,1965,1970],{"type":31,"tag":152,"props":1957,"children":1958},{"style":498},[1959],{"type":40,"value":1960},"      entityType",{"type":31,"tag":152,"props":1962,"children":1963},{"style":580},[1964],{"type":40,"value":269},{"type":31,"tag":152,"props":1966,"children":1967},{"style":534},[1968],{"type":40,"value":1969}," 'client'",{"type":31,"tag":152,"props":1971,"children":1972},{"style":226},[1973],{"type":40,"value":279},{"type":31,"tag":152,"props":1975,"children":1977},{"class":154,"line":1976},56,[1978,1983,1987,1991,1995,2000],{"type":31,"tag":152,"props":1979,"children":1980},{"style":498},[1981],{"type":40,"value":1982},"      entityId",{"type":31,"tag":152,"props":1984,"children":1985},{"style":580},[1986],{"type":40,"value":269},{"type":31,"tag":152,"props":1988,"children":1989},{"style":498},[1990],{"type":40,"value":1070},{"type":31,"tag":152,"props":1992,"children":1993},{"style":580},[1994],{"type":40,"value":583},{"type":31,"tag":152,"props":1996,"children":1997},{"style":498},[1998],{"type":40,"value":1999},"id",{"type":31,"tag":152,"props":2001,"children":2002},{"style":226},[2003],{"type":40,"value":279},{"type":31,"tag":152,"props":2005,"children":2007},{"class":154,"line":2006},57,[2008,2013,2017,2021],{"type":31,"tag":152,"props":2009,"children":2010},{"style":498},[2011],{"type":40,"value":2012},"      userId",{"type":31,"tag":152,"props":2014,"children":2015},{"style":580},[2016],{"type":40,"value":269},{"type":31,"tag":152,"props":2018,"children":2019},{"style":498},[2020],{"type":40,"value":435},{"type":31,"tag":152,"props":2022,"children":2023},{"style":226},[2024],{"type":40,"value":279},{"type":31,"tag":152,"props":2026,"children":2028},{"class":154,"line":2027},58,[2029,2034,2038,2042,2047,2051,2055],{"type":31,"tag":152,"props":2030,"children":2031},{"style":498},[2032],{"type":40,"value":2033},"      meta",{"type":31,"tag":152,"props":2035,"children":2036},{"style":580},[2037],{"type":40,"value":269},{"type":31,"tag":152,"props":2039,"children":2040},{"style":226},[2041],{"type":40,"value":629},{"type":31,"tag":152,"props":2043,"children":2044},{"style":498},[2045],{"type":40,"value":2046}," fromLeadId",{"type":31,"tag":152,"props":2048,"children":2049},{"style":580},[2050],{"type":40,"value":269},{"type":31,"tag":152,"props":2052,"children":2053},{"style":498},[2054],{"type":40,"value":643},{"type":31,"tag":152,"props":2056,"children":2057},{"style":226},[2058],{"type":40,"value":972},{"type":31,"tag":152,"props":2060,"children":2062},{"class":154,"line":2061},59,[2063,2067,2071],{"type":31,"tag":152,"props":2064,"children":2065},{"style":226},[2066],{"type":40,"value":981},{"type":31,"tag":152,"props":2068,"children":2069},{"style":498},[2070],{"type":40,"value":448},{"type":31,"tag":152,"props":2072,"children":2073},{"style":226},[2074],{"type":40,"value":546},{"type":31,"tag":152,"props":2076,"children":2078},{"class":154,"line":2077},60,[2079],{"type":31,"tag":152,"props":2080,"children":2081},{"emptyLinePlaceholder":13},[2082],{"type":40,"value":180},{"type":31,"tag":152,"props":2084,"children":2086},{"class":154,"line":2085},61,[2087],{"type":31,"tag":152,"props":2088,"children":2089},{"style":159},[2090],{"type":40,"value":2091},"    // 5. Événement domaine (4 lignes)\n",{"type":31,"tag":152,"props":2093,"children":2095},{"class":154,"line":2094},62,[2096,2101,2105,2110,2114,2119,2123,2128,2132,2136,2141,2145,2149,2153,2157,2161,2165,2169,2173],{"type":31,"tag":152,"props":2097,"children":2098},{"style":574},[2099],{"type":40,"value":2100},"    this",{"type":31,"tag":152,"props":2102,"children":2103},{"style":580},[2104],{"type":40,"value":583},{"type":31,"tag":152,"props":2106,"children":2107},{"style":498},[2108],{"type":40,"value":2109},"eventEmitter",{"type":31,"tag":152,"props":2111,"children":2112},{"style":580},[2113],{"type":40,"value":583},{"type":31,"tag":152,"props":2115,"children":2116},{"style":193},[2117],{"type":40,"value":2118},"emit",{"type":31,"tag":152,"props":2120,"children":2121},{"style":498},[2122],{"type":40,"value":410},{"type":31,"tag":152,"props":2124,"children":2125},{"style":534},[2126],{"type":40,"value":2127},"'client.created'",{"type":31,"tag":152,"props":2129,"children":2130},{"style":226},[2131],{"type":40,"value":430},{"type":31,"tag":152,"props":2133,"children":2134},{"style":226},[2135],{"type":40,"value":629},{"type":31,"tag":152,"props":2137,"children":2138},{"style":498},[2139],{"type":40,"value":2140}," clientId",{"type":31,"tag":152,"props":2142,"children":2143},{"style":580},[2144],{"type":40,"value":269},{"type":31,"tag":152,"props":2146,"children":2147},{"style":498},[2148],{"type":40,"value":1070},{"type":31,"tag":152,"props":2150,"children":2151},{"style":580},[2152],{"type":40,"value":583},{"type":31,"tag":152,"props":2154,"children":2155},{"style":498},[2156],{"type":40,"value":1999},{"type":31,"tag":152,"props":2158,"children":2159},{"style":226},[2160],{"type":40,"value":430},{"type":31,"tag":152,"props":2162,"children":2163},{"style":498},[2164],{"type":40,"value":967},{"type":31,"tag":152,"props":2166,"children":2167},{"style":226},[2168],{"type":40,"value":648},{"type":31,"tag":152,"props":2170,"children":2171},{"style":498},[2172],{"type":40,"value":448},{"type":31,"tag":152,"props":2174,"children":2175},{"style":226},[2176],{"type":40,"value":546},{"type":31,"tag":152,"props":2178,"children":2179},{"class":154,"line":11},[2180],{"type":31,"tag":152,"props":2181,"children":2182},{"emptyLinePlaceholder":13},[2183],{"type":40,"value":180},{"type":31,"tag":152,"props":2185,"children":2187},{"class":154,"line":2186},64,[2188,2193,2198,2202,2207,2212],{"type":31,"tag":152,"props":2189,"children":2190},{"style":209},[2191],{"type":40,"value":2192},"    return",{"type":31,"tag":152,"props":2194,"children":2195},{"style":498},[2196],{"type":40,"value":2197}," ClientDto",{"type":31,"tag":152,"props":2199,"children":2200},{"style":580},[2201],{"type":40,"value":583},{"type":31,"tag":152,"props":2203,"children":2204},{"style":193},[2205],{"type":40,"value":2206},"fromPrisma",{"type":31,"tag":152,"props":2208,"children":2209},{"style":498},[2210],{"type":40,"value":2211},"(client)",{"type":31,"tag":152,"props":2213,"children":2214},{"style":226},[2215],{"type":40,"value":546},{"type":31,"tag":152,"props":2217,"children":2219},{"class":154,"line":2218},65,[2220],{"type":31,"tag":152,"props":2221,"children":2222},{"style":226},[2223],{"type":40,"value":2224},"  }\n",{"type":31,"tag":152,"props":2226,"children":2228},{"class":154,"line":2227},66,[2229],{"type":31,"tag":152,"props":2230,"children":2231},{"style":226},[2232],{"type":40,"value":2233},"}\n",{"type":31,"tag":32,"props":2235,"children":2236},{},[2237,2239,2245,2247,2253,2254,2260,2261,2267,2268,2274,2275,2281],{"type":40,"value":2238},"Le contre-pattern craft, c'est l'application du Single Responsibility Principle. Cette fonction devient un orchestrateur de 10 lignes qui appelle des helpers nommés : ",{"type":31,"tag":148,"props":2240,"children":2242},{"className":2241},[],[2243],{"type":40,"value":2244},"assertLeadIsConvertible",{"type":40,"value":2246},", ",{"type":31,"tag":148,"props":2248,"children":2250},{"className":2249},[],[2251],{"type":40,"value":2252},"createClientFromLead",{"type":40,"value":2246},{"type":31,"tag":148,"props":2255,"children":2257},{"className":2256},[],[2258],{"type":40,"value":2259},"markLeadAsConverted",{"type":40,"value":2246},{"type":31,"tag":148,"props":2262,"children":2264},{"className":2263},[],[2265],{"type":40,"value":2266},"notifyClientOnboarding",{"type":40,"value":2246},{"type":31,"tag":148,"props":2269,"children":2271},{"className":2270},[],[2272],{"type":40,"value":2273},"logConversionAudit",{"type":40,"value":2246},{"type":31,"tag":148,"props":2276,"children":2278},{"className":2277},[],[2279],{"type":40,"value":2280},"emitClientCreated",{"type":40,"value":2282},". Chacun est testable isolément. Chacun est lisible en 30 secondes.",{"type":31,"tag":32,"props":2284,"children":2285},{},[2286,2288,2293],{"type":40,"value":2287},"Le prompt que j'utilise : ",{"type":31,"tag":99,"props":2289,"children":2290},{},[2291],{"type":40,"value":2292},"\"Découpe ce use case en responsabilités nommées. Chaque helper doit tenir en moins de 20 lignes et avoir un seul motif de changement.\"",{"type":40,"value":2294}," Claude exécute proprement. Le problème est qu'il ne le fait jamais spontanément.",{"type":31,"tag":48,"props":2296,"children":2297},{},[],{"type":31,"tag":52,"props":2299,"children":2301},{"id":2300},"pattern-2-couplage-métierorm",[2302],{"type":40,"value":2303},"Pattern #2 : couplage métier/ORM",{"type":31,"tag":32,"props":2305,"children":2306},{},[2307,2309,2315],{"type":40,"value":2308},"Celui-là est plus insidieux. Claude injecte directement le ",{"type":31,"tag":148,"props":2310,"children":2312},{"className":2311},[],[2313],{"type":40,"value":2314},"PrismaClient",{"type":40,"value":2316}," dans les use cases métier. Le résultat : vos règles de gestion ne peuvent plus tourner sans une base Postgres, vos tests ne peuvent plus être unitaires, et changer de stratégie de persistence devient une refonte de plusieurs mois.",{"type":31,"tag":32,"props":2318,"children":2319},{},[2320,2322,2328],{"type":40,"value":2321},"Concrètement, j'ai vu ça dans crmcoaching sur le bounded context ",{"type":31,"tag":148,"props":2323,"children":2325},{"className":2324},[],[2326],{"type":40,"value":2327},"slot-hold",{"type":40,"value":2329}," :",{"type":31,"tag":141,"props":2331,"children":2333},{"className":143,"code":2332,"language":145,"meta":8,"style":8},"// apps/api/src/application/use-cases/check-slot-availability.use-case.ts\n// Couplage direct Prisma dans le use case (anti-pattern)\n\n@Injectable()\nexport class CheckSlotAvailabilityUseCase {\n  constructor(\n    private readonly prisma: PrismaClient, // couplage direct infra\n  ) {}\n\n  async execute(slotId: string, coachId: string): Promise\u003Cboolean> {\n    const holds = await this.prisma.slotHold.count({\n      where: { slotId, status: 'ACTIVE', expiresAt: { gt: new Date() } },\n    });\n    const slot = await this.prisma.slot.findUnique({ where: { id: slotId } });\n    return slot != null && slot.coachId === coachId && holds === 0;\n  }\n}\n",[2334],{"type":31,"tag":148,"props":2335,"children":2336},{"__ignoreMap":8},[2337,2345,2353,2360,2375,2395,2406,2438,2449,2456,2529,2587,2671,2686,2784,2854,2861],{"type":31,"tag":152,"props":2338,"children":2339},{"class":154,"line":155},[2340],{"type":31,"tag":152,"props":2341,"children":2342},{"style":159},[2343],{"type":40,"value":2344},"// apps/api/src/application/use-cases/check-slot-availability.use-case.ts\n",{"type":31,"tag":152,"props":2346,"children":2347},{"class":154,"line":165},[2348],{"type":31,"tag":152,"props":2349,"children":2350},{"style":159},[2351],{"type":40,"value":2352},"// Couplage direct Prisma dans le use case (anti-pattern)\n",{"type":31,"tag":152,"props":2354,"children":2355},{"class":154,"line":174},[2356],{"type":31,"tag":152,"props":2357,"children":2358},{"emptyLinePlaceholder":13},[2359],{"type":40,"value":180},{"type":31,"tag":152,"props":2361,"children":2362},{"class":154,"line":183},[2363,2367,2371],{"type":31,"tag":152,"props":2364,"children":2365},{"style":187},[2366],{"type":40,"value":190},{"type":31,"tag":152,"props":2368,"children":2369},{"style":193},[2370],{"type":40,"value":196},{"type":31,"tag":152,"props":2372,"children":2373},{"style":199},[2374],{"type":40,"value":202},{"type":31,"tag":152,"props":2376,"children":2377},{"class":154,"line":205},[2378,2382,2386,2391],{"type":31,"tag":152,"props":2379,"children":2380},{"style":209},[2381],{"type":40,"value":212},{"type":31,"tag":152,"props":2383,"children":2384},{"style":209},[2385],{"type":40,"value":217},{"type":31,"tag":152,"props":2387,"children":2388},{"style":220},[2389],{"type":40,"value":2390}," CheckSlotAvailabilityUseCase",{"type":31,"tag":152,"props":2392,"children":2393},{"style":226},[2394],{"type":40,"value":229},{"type":31,"tag":152,"props":2396,"children":2397},{"class":154,"line":232},[2398,2402],{"type":31,"tag":152,"props":2399,"children":2400},{"style":209},[2401],{"type":40,"value":238},{"type":31,"tag":152,"props":2403,"children":2404},{"style":226},[2405],{"type":40,"value":243},{"type":31,"tag":152,"props":2407,"children":2408},{"class":154,"line":246},[2409,2413,2417,2421,2425,2429,2433],{"type":31,"tag":152,"props":2410,"children":2411},{"style":209},[2412],{"type":40,"value":252},{"type":31,"tag":152,"props":2414,"children":2415},{"style":209},[2416],{"type":40,"value":257},{"type":31,"tag":152,"props":2418,"children":2419},{"style":260},[2420],{"type":40,"value":263},{"type":31,"tag":152,"props":2422,"children":2423},{"style":266},[2424],{"type":40,"value":269},{"type":31,"tag":152,"props":2426,"children":2427},{"style":220},[2428],{"type":40,"value":274},{"type":31,"tag":152,"props":2430,"children":2431},{"style":226},[2432],{"type":40,"value":430},{"type":31,"tag":152,"props":2434,"children":2435},{"style":159},[2436],{"type":40,"value":2437}," // couplage direct infra\n",{"type":31,"tag":152,"props":2439,"children":2440},{"class":154,"line":282},[2441,2445],{"type":31,"tag":152,"props":2442,"children":2443},{"style":226},[2444],{"type":40,"value":378},{"type":31,"tag":152,"props":2446,"children":2447},{"style":226},[2448],{"type":40,"value":383},{"type":31,"tag":152,"props":2450,"children":2451},{"class":154,"line":312},[2452],{"type":31,"tag":152,"props":2453,"children":2454},{"emptyLinePlaceholder":13},[2455],{"type":40,"value":180},{"type":31,"tag":152,"props":2457,"children":2458},{"class":154,"line":342},[2459,2463,2467,2471,2476,2480,2484,2488,2492,2496,2500,2504,2508,2512,2516,2521,2525],{"type":31,"tag":152,"props":2460,"children":2461},{"style":209},[2462],{"type":40,"value":400},{"type":31,"tag":152,"props":2464,"children":2465},{"style":193},[2466],{"type":40,"value":405},{"type":31,"tag":152,"props":2468,"children":2469},{"style":226},[2470],{"type":40,"value":410},{"type":31,"tag":152,"props":2472,"children":2473},{"style":260},[2474],{"type":40,"value":2475},"slotId",{"type":31,"tag":152,"props":2477,"children":2478},{"style":266},[2479],{"type":40,"value":269},{"type":31,"tag":152,"props":2481,"children":2482},{"style":422},[2483],{"type":40,"value":425},{"type":31,"tag":152,"props":2485,"children":2486},{"style":226},[2487],{"type":40,"value":430},{"type":31,"tag":152,"props":2489,"children":2490},{"style":260},[2491],{"type":40,"value":435},{"type":31,"tag":152,"props":2493,"children":2494},{"style":266},[2495],{"type":40,"value":269},{"type":31,"tag":152,"props":2497,"children":2498},{"style":422},[2499],{"type":40,"value":425},{"type":31,"tag":152,"props":2501,"children":2502},{"style":226},[2503],{"type":40,"value":448},{"type":31,"tag":152,"props":2505,"children":2506},{"style":266},[2507],{"type":40,"value":269},{"type":31,"tag":152,"props":2509,"children":2510},{"style":220},[2511],{"type":40,"value":457},{"type":31,"tag":152,"props":2513,"children":2514},{"style":460},[2515],{"type":40,"value":463},{"type":31,"tag":152,"props":2517,"children":2518},{"style":422},[2519],{"type":40,"value":2520},"boolean",{"type":31,"tag":152,"props":2522,"children":2523},{"style":460},[2524],{"type":40,"value":473},{"type":31,"tag":152,"props":2526,"children":2527},{"style":226},[2528],{"type":40,"value":229},{"type":31,"tag":152,"props":2530,"children":2531},{"class":154,"line":372},[2532,2536,2541,2545,2549,2553,2557,2561,2565,2570,2574,2579,2583],{"type":31,"tag":152,"props":2533,"children":2534},{"style":209},[2535],{"type":40,"value":555},{"type":31,"tag":152,"props":2537,"children":2538},{"style":558},[2539],{"type":40,"value":2540}," holds",{"type":31,"tag":152,"props":2542,"children":2543},{"style":266},[2544],{"type":40,"value":566},{"type":31,"tag":152,"props":2546,"children":2547},{"style":209},[2548],{"type":40,"value":571},{"type":31,"tag":152,"props":2550,"children":2551},{"style":574},[2552],{"type":40,"value":577},{"type":31,"tag":152,"props":2554,"children":2555},{"style":580},[2556],{"type":40,"value":583},{"type":31,"tag":152,"props":2558,"children":2559},{"style":498},[2560],{"type":40,"value":588},{"type":31,"tag":152,"props":2562,"children":2563},{"style":580},[2564],{"type":40,"value":583},{"type":31,"tag":152,"props":2566,"children":2567},{"style":498},[2568],{"type":40,"value":2569},"slotHold",{"type":31,"tag":152,"props":2571,"children":2572},{"style":580},[2573],{"type":40,"value":583},{"type":31,"tag":152,"props":2575,"children":2576},{"style":193},[2577],{"type":40,"value":2578},"count",{"type":31,"tag":152,"props":2580,"children":2581},{"style":498},[2582],{"type":40,"value":410},{"type":31,"tag":152,"props":2584,"children":2585},{"style":226},[2586],{"type":40,"value":919},{"type":31,"tag":152,"props":2588,"children":2589},{"class":154,"line":386},[2590,2594,2598,2602,2607,2611,2615,2619,2623,2627,2632,2636,2640,2645,2649,2653,2657,2662,2666],{"type":31,"tag":152,"props":2591,"children":2592},{"style":498},[2593],{"type":40,"value":928},{"type":31,"tag":152,"props":2595,"children":2596},{"style":580},[2597],{"type":40,"value":269},{"type":31,"tag":152,"props":2599,"children":2600},{"style":226},[2601],{"type":40,"value":629},{"type":31,"tag":152,"props":2603,"children":2604},{"style":498},[2605],{"type":40,"value":2606}," slotId",{"type":31,"tag":152,"props":2608,"children":2609},{"style":226},[2610],{"type":40,"value":430},{"type":31,"tag":152,"props":2612,"children":2613},{"style":498},[2614],{"type":40,"value":1453},{"type":31,"tag":152,"props":2616,"children":2617},{"style":580},[2618],{"type":40,"value":269},{"type":31,"tag":152,"props":2620,"children":2621},{"style":534},[2622],{"type":40,"value":1282},{"type":31,"tag":152,"props":2624,"children":2625},{"style":226},[2626],{"type":40,"value":430},{"type":31,"tag":152,"props":2628,"children":2629},{"style":498},[2630],{"type":40,"value":2631}," expiresAt",{"type":31,"tag":152,"props":2633,"children":2634},{"style":580},[2635],{"type":40,"value":269},{"type":31,"tag":152,"props":2637,"children":2638},{"style":226},[2639],{"type":40,"value":629},{"type":31,"tag":152,"props":2641,"children":2642},{"style":498},[2643],{"type":40,"value":2644}," gt",{"type":31,"tag":152,"props":2646,"children":2647},{"style":580},[2648],{"type":40,"value":269},{"type":31,"tag":152,"props":2650,"children":2651},{"style":519},[2652],{"type":40,"value":522},{"type":31,"tag":152,"props":2654,"children":2655},{"style":193},[2656],{"type":40,"value":1483},{"type":31,"tag":152,"props":2658,"children":2659},{"style":498},[2660],{"type":40,"value":2661},"() ",{"type":31,"tag":152,"props":2663,"children":2664},{"style":226},[2665],{"type":40,"value":648},{"type":31,"tag":152,"props":2667,"children":2668},{"style":226},[2669],{"type":40,"value":2670}," },\n",{"type":31,"tag":152,"props":2672,"children":2673},{"class":154,"line":394},[2674,2678,2682],{"type":31,"tag":152,"props":2675,"children":2676},{"style":226},[2677],{"type":40,"value":981},{"type":31,"tag":152,"props":2679,"children":2680},{"style":498},[2681],{"type":40,"value":448},{"type":31,"tag":152,"props":2683,"children":2684},{"style":226},[2685],{"type":40,"value":546},{"type":31,"tag":152,"props":2687,"children":2688},{"class":154,"line":480},[2689,2693,2698,2702,2706,2710,2714,2718,2722,2727,2731,2735,2739,2743,2747,2751,2755,2759,2763,2768,2772,2776,2780],{"type":31,"tag":152,"props":2690,"children":2691},{"style":209},[2692],{"type":40,"value":555},{"type":31,"tag":152,"props":2694,"children":2695},{"style":558},[2696],{"type":40,"value":2697}," slot",{"type":31,"tag":152,"props":2699,"children":2700},{"style":266},[2701],{"type":40,"value":566},{"type":31,"tag":152,"props":2703,"children":2704},{"style":209},[2705],{"type":40,"value":571},{"type":31,"tag":152,"props":2707,"children":2708},{"style":574},[2709],{"type":40,"value":577},{"type":31,"tag":152,"props":2711,"children":2712},{"style":580},[2713],{"type":40,"value":583},{"type":31,"tag":152,"props":2715,"children":2716},{"style":498},[2717],{"type":40,"value":588},{"type":31,"tag":152,"props":2719,"children":2720},{"style":580},[2721],{"type":40,"value":583},{"type":31,"tag":152,"props":2723,"children":2724},{"style":498},[2725],{"type":40,"value":2726},"slot",{"type":31,"tag":152,"props":2728,"children":2729},{"style":580},[2730],{"type":40,"value":583},{"type":31,"tag":152,"props":2732,"children":2733},{"style":193},[2734],{"type":40,"value":606},{"type":31,"tag":152,"props":2736,"children":2737},{"style":498},[2738],{"type":40,"value":410},{"type":31,"tag":152,"props":2740,"children":2741},{"style":226},[2742],{"type":40,"value":615},{"type":31,"tag":152,"props":2744,"children":2745},{"style":498},[2746],{"type":40,"value":620},{"type":31,"tag":152,"props":2748,"children":2749},{"style":580},[2750],{"type":40,"value":269},{"type":31,"tag":152,"props":2752,"children":2753},{"style":226},[2754],{"type":40,"value":629},{"type":31,"tag":152,"props":2756,"children":2757},{"style":498},[2758],{"type":40,"value":634},{"type":31,"tag":152,"props":2760,"children":2761},{"style":580},[2762],{"type":40,"value":269},{"type":31,"tag":152,"props":2764,"children":2765},{"style":498},[2766],{"type":40,"value":2767}," slotId ",{"type":31,"tag":152,"props":2769,"children":2770},{"style":226},[2771],{"type":40,"value":648},{"type":31,"tag":152,"props":2773,"children":2774},{"style":226},[2775],{"type":40,"value":653},{"type":31,"tag":152,"props":2777,"children":2778},{"style":498},[2779],{"type":40,"value":448},{"type":31,"tag":152,"props":2781,"children":2782},{"style":226},[2783],{"type":40,"value":546},{"type":31,"tag":152,"props":2785,"children":2786},{"class":154,"line":489},[2787,2791,2796,2801,2806,2811,2815,2819,2823,2827,2831,2836,2841,2845,2850],{"type":31,"tag":152,"props":2788,"children":2789},{"style":209},[2790],{"type":40,"value":2192},{"type":31,"tag":152,"props":2792,"children":2793},{"style":498},[2794],{"type":40,"value":2795}," slot ",{"type":31,"tag":152,"props":2797,"children":2798},{"style":266},[2799],{"type":40,"value":2800},"!=",{"type":31,"tag":152,"props":2802,"children":2803},{"style":422},[2804],{"type":40,"value":2805}," null",{"type":31,"tag":152,"props":2807,"children":2808},{"style":266},[2809],{"type":40,"value":2810}," &&",{"type":31,"tag":152,"props":2812,"children":2813},{"style":498},[2814],{"type":40,"value":2697},{"type":31,"tag":152,"props":2816,"children":2817},{"style":580},[2818],{"type":40,"value":583},{"type":31,"tag":152,"props":2820,"children":2821},{"style":498},[2822],{"type":40,"value":753},{"type":31,"tag":152,"props":2824,"children":2825},{"style":266},[2826],{"type":40,"value":819},{"type":31,"tag":152,"props":2828,"children":2829},{"style":498},[2830],{"type":40,"value":967},{"type":31,"tag":152,"props":2832,"children":2833},{"style":266},[2834],{"type":40,"value":2835},"&&",{"type":31,"tag":152,"props":2837,"children":2838},{"style":498},[2839],{"type":40,"value":2840}," holds ",{"type":31,"tag":152,"props":2842,"children":2843},{"style":266},[2844],{"type":40,"value":819},{"type":31,"tag":152,"props":2846,"children":2847},{"style":1725},[2848],{"type":40,"value":2849}," 0",{"type":31,"tag":152,"props":2851,"children":2852},{"style":226},[2853],{"type":40,"value":546},{"type":31,"tag":152,"props":2855,"children":2856},{"class":154,"line":549},[2857],{"type":31,"tag":152,"props":2858,"children":2859},{"style":226},[2860],{"type":40,"value":2224},{"type":31,"tag":152,"props":2862,"children":2863},{"class":154,"line":664},[2864],{"type":31,"tag":152,"props":2865,"children":2866},{"style":226},[2867],{"type":40,"value":2233},{"type":31,"tag":32,"props":2869,"children":2870},{},[2871,2873,2879,2881,2887,2889,2895,2897,2903,2904,2910,2912,2918],{"type":40,"value":2872},"Le contre-pattern, c'est l'",{"type":31,"tag":64,"props":2874,"children":2876},{"href":2875},"/fr/architecture-craft/architecture-hexagonale-java-exemples-bonnes-pratiques",[2877],{"type":40,"value":2878},"architecture hexagonale d'Alistair Cockburn",{"type":40,"value":2880}," (2005). La règle métier ne connaît pas Prisma. Elle prend un port ",{"type":31,"tag":148,"props":2882,"children":2884},{"className":2883},[],[2885],{"type":40,"value":2886},"ISlotHoldRepository",{"type":40,"value":2888}," qui expose ",{"type":31,"tag":148,"props":2890,"children":2892},{"className":2891},[],[2893],{"type":40,"value":2894},"countActiveHolds(slotId)",{"type":40,"value":2896}," et un port ",{"type":31,"tag":148,"props":2898,"children":2900},{"className":2899},[],[2901],{"type":40,"value":2902},"ISlotRepository",{"type":40,"value":2888},{"type":31,"tag":148,"props":2905,"children":2907},{"className":2906},[],[2908],{"type":40,"value":2909},"findById(slotId)",{"type":40,"value":2911},". L'implémentation Prisma vit dans ",{"type":31,"tag":148,"props":2913,"children":2915},{"className":2914},[],[2916],{"type":40,"value":2917},"infrastructure/",{"type":40,"value":2919},". Les tests unitaires utilisent un fake repository en mémoire.",{"type":31,"tag":141,"props":2921,"children":2923},{"className":143,"code":2922,"language":145,"meta":8,"style":8},"// apps/api/src/domain/ports/slot-hold.repository.port.ts\nexport interface ISlotHoldRepository {\n  countActiveHolds(slotId: string): Promise\u003Cnumber>;\n}\n\n// apps/api/src/application/use-cases/check-slot-availability.use-case.ts\n@Injectable()\nexport class CheckSlotAvailabilityUseCase {\n  constructor(\n    private readonly slotRepo: ISlotRepository,\n    private readonly slotHoldRepo: ISlotHoldRepository,\n  ) {}\n\n  async execute(slotId: string, coachId: string): Promise\u003Cboolean> {\n    const slot = await this.slotRepo.findById(slotId);\n    if (slot == null || slot.coachId !== coachId) return false;\n    const activeHolds = await this.slotHoldRepo.countActiveHolds(slotId);\n    return activeHolds === 0;\n  }\n}\n",[2924],{"type":31,"tag":148,"props":2925,"children":2926},{"__ignoreMap":8},[2927,2935,2956,3009,3016,3023,3030,3045,3064,3075,3104,3132,3143,3150,3221,3271,3331,3381,3405,3412],{"type":31,"tag":152,"props":2928,"children":2929},{"class":154,"line":155},[2930],{"type":31,"tag":152,"props":2931,"children":2932},{"style":159},[2933],{"type":40,"value":2934},"// apps/api/src/domain/ports/slot-hold.repository.port.ts\n",{"type":31,"tag":152,"props":2936,"children":2937},{"class":154,"line":165},[2938,2942,2947,2952],{"type":31,"tag":152,"props":2939,"children":2940},{"style":209},[2941],{"type":40,"value":212},{"type":31,"tag":152,"props":2943,"children":2944},{"style":209},[2945],{"type":40,"value":2946}," interface",{"type":31,"tag":152,"props":2948,"children":2949},{"style":220},[2950],{"type":40,"value":2951}," ISlotHoldRepository",{"type":31,"tag":152,"props":2953,"children":2954},{"style":226},[2955],{"type":40,"value":229},{"type":31,"tag":152,"props":2957,"children":2958},{"class":154,"line":174},[2959,2964,2968,2972,2976,2980,2984,2988,2992,2996,3001,3005],{"type":31,"tag":152,"props":2960,"children":2961},{"style":193},[2962],{"type":40,"value":2963},"  countActiveHolds",{"type":31,"tag":152,"props":2965,"children":2966},{"style":226},[2967],{"type":40,"value":410},{"type":31,"tag":152,"props":2969,"children":2970},{"style":260},[2971],{"type":40,"value":2475},{"type":31,"tag":152,"props":2973,"children":2974},{"style":266},[2975],{"type":40,"value":269},{"type":31,"tag":152,"props":2977,"children":2978},{"style":422},[2979],{"type":40,"value":425},{"type":31,"tag":152,"props":2981,"children":2982},{"style":226},[2983],{"type":40,"value":448},{"type":31,"tag":152,"props":2985,"children":2986},{"style":266},[2987],{"type":40,"value":269},{"type":31,"tag":152,"props":2989,"children":2990},{"style":220},[2991],{"type":40,"value":457},{"type":31,"tag":152,"props":2993,"children":2994},{"style":460},[2995],{"type":40,"value":463},{"type":31,"tag":152,"props":2997,"children":2998},{"style":422},[2999],{"type":40,"value":3000},"number",{"type":31,"tag":152,"props":3002,"children":3003},{"style":460},[3004],{"type":40,"value":473},{"type":31,"tag":152,"props":3006,"children":3007},{"style":226},[3008],{"type":40,"value":546},{"type":31,"tag":152,"props":3010,"children":3011},{"class":154,"line":183},[3012],{"type":31,"tag":152,"props":3013,"children":3014},{"style":226},[3015],{"type":40,"value":2233},{"type":31,"tag":152,"props":3017,"children":3018},{"class":154,"line":205},[3019],{"type":31,"tag":152,"props":3020,"children":3021},{"emptyLinePlaceholder":13},[3022],{"type":40,"value":180},{"type":31,"tag":152,"props":3024,"children":3025},{"class":154,"line":232},[3026],{"type":31,"tag":152,"props":3027,"children":3028},{"style":159},[3029],{"type":40,"value":2344},{"type":31,"tag":152,"props":3031,"children":3032},{"class":154,"line":246},[3033,3037,3041],{"type":31,"tag":152,"props":3034,"children":3035},{"style":187},[3036],{"type":40,"value":190},{"type":31,"tag":152,"props":3038,"children":3039},{"style":193},[3040],{"type":40,"value":196},{"type":31,"tag":152,"props":3042,"children":3043},{"style":199},[3044],{"type":40,"value":202},{"type":31,"tag":152,"props":3046,"children":3047},{"class":154,"line":282},[3048,3052,3056,3060],{"type":31,"tag":152,"props":3049,"children":3050},{"style":209},[3051],{"type":40,"value":212},{"type":31,"tag":152,"props":3053,"children":3054},{"style":209},[3055],{"type":40,"value":217},{"type":31,"tag":152,"props":3057,"children":3058},{"style":220},[3059],{"type":40,"value":2390},{"type":31,"tag":152,"props":3061,"children":3062},{"style":226},[3063],{"type":40,"value":229},{"type":31,"tag":152,"props":3065,"children":3066},{"class":154,"line":312},[3067,3071],{"type":31,"tag":152,"props":3068,"children":3069},{"style":209},[3070],{"type":40,"value":238},{"type":31,"tag":152,"props":3072,"children":3073},{"style":226},[3074],{"type":40,"value":243},{"type":31,"tag":152,"props":3076,"children":3077},{"class":154,"line":342},[3078,3082,3086,3091,3095,3100],{"type":31,"tag":152,"props":3079,"children":3080},{"style":209},[3081],{"type":40,"value":252},{"type":31,"tag":152,"props":3083,"children":3084},{"style":209},[3085],{"type":40,"value":257},{"type":31,"tag":152,"props":3087,"children":3088},{"style":260},[3089],{"type":40,"value":3090}," slotRepo",{"type":31,"tag":152,"props":3092,"children":3093},{"style":266},[3094],{"type":40,"value":269},{"type":31,"tag":152,"props":3096,"children":3097},{"style":220},[3098],{"type":40,"value":3099}," ISlotRepository",{"type":31,"tag":152,"props":3101,"children":3102},{"style":226},[3103],{"type":40,"value":279},{"type":31,"tag":152,"props":3105,"children":3106},{"class":154,"line":372},[3107,3111,3115,3120,3124,3128],{"type":31,"tag":152,"props":3108,"children":3109},{"style":209},[3110],{"type":40,"value":252},{"type":31,"tag":152,"props":3112,"children":3113},{"style":209},[3114],{"type":40,"value":257},{"type":31,"tag":152,"props":3116,"children":3117},{"style":260},[3118],{"type":40,"value":3119}," slotHoldRepo",{"type":31,"tag":152,"props":3121,"children":3122},{"style":266},[3123],{"type":40,"value":269},{"type":31,"tag":152,"props":3125,"children":3126},{"style":220},[3127],{"type":40,"value":2951},{"type":31,"tag":152,"props":3129,"children":3130},{"style":226},[3131],{"type":40,"value":279},{"type":31,"tag":152,"props":3133,"children":3134},{"class":154,"line":386},[3135,3139],{"type":31,"tag":152,"props":3136,"children":3137},{"style":226},[3138],{"type":40,"value":378},{"type":31,"tag":152,"props":3140,"children":3141},{"style":226},[3142],{"type":40,"value":383},{"type":31,"tag":152,"props":3144,"children":3145},{"class":154,"line":394},[3146],{"type":31,"tag":152,"props":3147,"children":3148},{"emptyLinePlaceholder":13},[3149],{"type":40,"value":180},{"type":31,"tag":152,"props":3151,"children":3152},{"class":154,"line":480},[3153,3157,3161,3165,3169,3173,3177,3181,3185,3189,3193,3197,3201,3205,3209,3213,3217],{"type":31,"tag":152,"props":3154,"children":3155},{"style":209},[3156],{"type":40,"value":400},{"type":31,"tag":152,"props":3158,"children":3159},{"style":193},[3160],{"type":40,"value":405},{"type":31,"tag":152,"props":3162,"children":3163},{"style":226},[3164],{"type":40,"value":410},{"type":31,"tag":152,"props":3166,"children":3167},{"style":260},[3168],{"type":40,"value":2475},{"type":31,"tag":152,"props":3170,"children":3171},{"style":266},[3172],{"type":40,"value":269},{"type":31,"tag":152,"props":3174,"children":3175},{"style":422},[3176],{"type":40,"value":425},{"type":31,"tag":152,"props":3178,"children":3179},{"style":226},[3180],{"type":40,"value":430},{"type":31,"tag":152,"props":3182,"children":3183},{"style":260},[3184],{"type":40,"value":435},{"type":31,"tag":152,"props":3186,"children":3187},{"style":266},[3188],{"type":40,"value":269},{"type":31,"tag":152,"props":3190,"children":3191},{"style":422},[3192],{"type":40,"value":425},{"type":31,"tag":152,"props":3194,"children":3195},{"style":226},[3196],{"type":40,"value":448},{"type":31,"tag":152,"props":3198,"children":3199},{"style":266},[3200],{"type":40,"value":269},{"type":31,"tag":152,"props":3202,"children":3203},{"style":220},[3204],{"type":40,"value":457},{"type":31,"tag":152,"props":3206,"children":3207},{"style":460},[3208],{"type":40,"value":463},{"type":31,"tag":152,"props":3210,"children":3211},{"style":422},[3212],{"type":40,"value":2520},{"type":31,"tag":152,"props":3214,"children":3215},{"style":460},[3216],{"type":40,"value":473},{"type":31,"tag":152,"props":3218,"children":3219},{"style":226},[3220],{"type":40,"value":229},{"type":31,"tag":152,"props":3222,"children":3223},{"class":154,"line":489},[3224,3228,3232,3236,3240,3244,3248,3253,3257,3262,3267],{"type":31,"tag":152,"props":3225,"children":3226},{"style":209},[3227],{"type":40,"value":555},{"type":31,"tag":152,"props":3229,"children":3230},{"style":558},[3231],{"type":40,"value":2697},{"type":31,"tag":152,"props":3233,"children":3234},{"style":266},[3235],{"type":40,"value":566},{"type":31,"tag":152,"props":3237,"children":3238},{"style":209},[3239],{"type":40,"value":571},{"type":31,"tag":152,"props":3241,"children":3242},{"style":574},[3243],{"type":40,"value":577},{"type":31,"tag":152,"props":3245,"children":3246},{"style":580},[3247],{"type":40,"value":583},{"type":31,"tag":152,"props":3249,"children":3250},{"style":498},[3251],{"type":40,"value":3252},"slotRepo",{"type":31,"tag":152,"props":3254,"children":3255},{"style":580},[3256],{"type":40,"value":583},{"type":31,"tag":152,"props":3258,"children":3259},{"style":193},[3260],{"type":40,"value":3261},"findById",{"type":31,"tag":152,"props":3263,"children":3264},{"style":498},[3265],{"type":40,"value":3266},"(slotId)",{"type":31,"tag":152,"props":3268,"children":3269},{"style":226},[3270],{"type":40,"value":546},{"type":31,"tag":152,"props":3272,"children":3273},{"class":154,"line":549},[3274,3278,3283,3288,3292,3297,3301,3305,3309,3313,3317,3322,3327],{"type":31,"tag":152,"props":3275,"children":3276},{"style":209},[3277],{"type":40,"value":495},{"type":31,"tag":152,"props":3279,"children":3280},{"style":498},[3281],{"type":40,"value":3282}," (slot ",{"type":31,"tag":152,"props":3284,"children":3285},{"style":266},[3286],{"type":40,"value":3287},"==",{"type":31,"tag":152,"props":3289,"children":3290},{"style":422},[3291],{"type":40,"value":2805},{"type":31,"tag":152,"props":3293,"children":3294},{"style":266},[3295],{"type":40,"value":3296}," ||",{"type":31,"tag":152,"props":3298,"children":3299},{"style":498},[3300],{"type":40,"value":2697},{"type":31,"tag":152,"props":3302,"children":3303},{"style":580},[3304],{"type":40,"value":583},{"type":31,"tag":152,"props":3306,"children":3307},{"style":498},[3308],{"type":40,"value":753},{"type":31,"tag":152,"props":3310,"children":3311},{"style":266},[3312],{"type":40,"value":758},{"type":31,"tag":152,"props":3314,"children":3315},{"style":498},[3316],{"type":40,"value":763},{"type":31,"tag":152,"props":3318,"children":3319},{"style":209},[3320],{"type":40,"value":3321},"return",{"type":31,"tag":152,"props":3323,"children":3324},{"style":1725},[3325],{"type":40,"value":3326}," false",{"type":31,"tag":152,"props":3328,"children":3329},{"style":226},[3330],{"type":40,"value":546},{"type":31,"tag":152,"props":3332,"children":3333},{"class":154,"line":664},[3334,3338,3343,3347,3351,3355,3359,3364,3368,3373,3377],{"type":31,"tag":152,"props":3335,"children":3336},{"style":209},[3337],{"type":40,"value":555},{"type":31,"tag":152,"props":3339,"children":3340},{"style":558},[3341],{"type":40,"value":3342}," activeHolds",{"type":31,"tag":152,"props":3344,"children":3345},{"style":266},[3346],{"type":40,"value":566},{"type":31,"tag":152,"props":3348,"children":3349},{"style":209},[3350],{"type":40,"value":571},{"type":31,"tag":152,"props":3352,"children":3353},{"style":574},[3354],{"type":40,"value":577},{"type":31,"tag":152,"props":3356,"children":3357},{"style":580},[3358],{"type":40,"value":583},{"type":31,"tag":152,"props":3360,"children":3361},{"style":498},[3362],{"type":40,"value":3363},"slotHoldRepo",{"type":31,"tag":152,"props":3365,"children":3366},{"style":580},[3367],{"type":40,"value":583},{"type":31,"tag":152,"props":3369,"children":3370},{"style":193},[3371],{"type":40,"value":3372},"countActiveHolds",{"type":31,"tag":152,"props":3374,"children":3375},{"style":498},[3376],{"type":40,"value":3266},{"type":31,"tag":152,"props":3378,"children":3379},{"style":226},[3380],{"type":40,"value":546},{"type":31,"tag":152,"props":3382,"children":3383},{"class":154,"line":734},[3384,3388,3393,3397,3401],{"type":31,"tag":152,"props":3385,"children":3386},{"style":209},[3387],{"type":40,"value":2192},{"type":31,"tag":152,"props":3389,"children":3390},{"style":498},[3391],{"type":40,"value":3392}," activeHolds ",{"type":31,"tag":152,"props":3394,"children":3395},{"style":266},[3396],{"type":40,"value":819},{"type":31,"tag":152,"props":3398,"children":3399},{"style":1725},[3400],{"type":40,"value":2849},{"type":31,"tag":152,"props":3402,"children":3403},{"style":226},[3404],{"type":40,"value":546},{"type":31,"tag":152,"props":3406,"children":3407},{"class":154,"line":796},[3408],{"type":31,"tag":152,"props":3409,"children":3410},{"style":226},[3411],{"type":40,"value":2224},{"type":31,"tag":152,"props":3413,"children":3414},{"class":154,"line":862},[3415],{"type":31,"tag":152,"props":3416,"children":3417},{"style":226},[3418],{"type":40,"value":2233},{"type":31,"tag":32,"props":3420,"children":3421},{},[3422],{"type":40,"value":3423},"Sur crmcoaching, j'ai 47 use cases qui ne dépendent d'aucun module externe. Je peux faire tourner toute la logique métier en CI sans démarrer Postgres. Le jour où je voudrai migrer vers Drizzle, ce sera 2 jours de travail au lieu de plusieurs mois.",{"type":31,"tag":48,"props":3425,"children":3426},{},[],{"type":31,"tag":52,"props":3428,"children":3430},{"id":3429},"pattern-3-tests-qui-ne-testent-rien",[3431],{"type":40,"value":3432},"Pattern #3 : tests qui ne testent rien",{"type":31,"tag":32,"props":3434,"children":3435},{},[3436,3438,3444,3446,3452],{"type":40,"value":3437},"Celui-là me fait grincer des dents à chaque fois. Claude génère des tests qui ont l'air sérieux, avec des ",{"type":31,"tag":148,"props":3439,"children":3441},{"className":3440},[],[3442],{"type":40,"value":3443},"describe",{"type":40,"value":3445},", des ",{"type":31,"tag":148,"props":3447,"children":3449},{"className":3448},[],[3450],{"type":40,"value":3451},"vi.fn()",{"type":40,"value":3453},", des assertions, et qui ne testent en réalité aucun comportement métier. Exemple typique sur crmcoaching :",{"type":31,"tag":141,"props":3455,"children":3457},{"className":143,"code":3456,"language":145,"meta":8,"style":8},"// apps/api/src/application/use-cases/__tests__/create-mentoring-checkout-intent.test.ts\n// Test généré par Claude sans prompt de comportement\n\ndescribe('CreateMentoringCheckoutIntentUseCase', () => {\n  it('should call repository save', async () => {\n    const repo = { save: vi.fn().mockResolvedValue({ id: 'intent-1' }) };\n    const useCase = new CreateMentoringCheckoutIntentUseCase(repo as any);\n\n    await useCase.execute({ coachId: 'c1', clientId: 'cl1', offreId: 'o1' });\n\n    expect(repo.save).toHaveBeenCalledWith(\n      expect.objectContaining({ coachId: 'c1' }),\n    ); // vérifie un appel, pas un comportement\n  });\n});\n",[3458],{"type":31,"tag":148,"props":3459,"children":3460},{"__ignoreMap":8},[3461,3469,3477,3484,3518,3556,3646,3694,3701,3789,3796,3831,3880,3898,3914],{"type":31,"tag":152,"props":3462,"children":3463},{"class":154,"line":155},[3464],{"type":31,"tag":152,"props":3465,"children":3466},{"style":159},[3467],{"type":40,"value":3468},"// apps/api/src/application/use-cases/__tests__/create-mentoring-checkout-intent.test.ts\n",{"type":31,"tag":152,"props":3470,"children":3471},{"class":154,"line":165},[3472],{"type":31,"tag":152,"props":3473,"children":3474},{"style":159},[3475],{"type":40,"value":3476},"// Test généré par Claude sans prompt de comportement\n",{"type":31,"tag":152,"props":3478,"children":3479},{"class":154,"line":174},[3480],{"type":31,"tag":152,"props":3481,"children":3482},{"emptyLinePlaceholder":13},[3483],{"type":40,"value":180},{"type":31,"tag":152,"props":3485,"children":3486},{"class":154,"line":183},[3487,3491,3495,3500,3504,3509,3514],{"type":31,"tag":152,"props":3488,"children":3489},{"style":193},[3490],{"type":40,"value":3443},{"type":31,"tag":152,"props":3492,"children":3493},{"style":498},[3494],{"type":40,"value":410},{"type":31,"tag":152,"props":3496,"children":3497},{"style":534},[3498],{"type":40,"value":3499},"'CreateMentoringCheckoutIntentUseCase'",{"type":31,"tag":152,"props":3501,"children":3502},{"style":226},[3503],{"type":40,"value":430},{"type":31,"tag":152,"props":3505,"children":3506},{"style":226},[3507],{"type":40,"value":3508}," ()",{"type":31,"tag":152,"props":3510,"children":3511},{"style":266},[3512],{"type":40,"value":3513}," =>",{"type":31,"tag":152,"props":3515,"children":3516},{"style":226},[3517],{"type":40,"value":229},{"type":31,"tag":152,"props":3519,"children":3520},{"class":154,"line":205},[3521,3526,3530,3535,3539,3544,3548,3552],{"type":31,"tag":152,"props":3522,"children":3523},{"style":193},[3524],{"type":40,"value":3525},"  it",{"type":31,"tag":152,"props":3527,"children":3528},{"style":498},[3529],{"type":40,"value":410},{"type":31,"tag":152,"props":3531,"children":3532},{"style":534},[3533],{"type":40,"value":3534},"'should call repository save'",{"type":31,"tag":152,"props":3536,"children":3537},{"style":226},[3538],{"type":40,"value":430},{"type":31,"tag":152,"props":3540,"children":3541},{"style":209},[3542],{"type":40,"value":3543}," async",{"type":31,"tag":152,"props":3545,"children":3546},{"style":226},[3547],{"type":40,"value":3508},{"type":31,"tag":152,"props":3549,"children":3550},{"style":266},[3551],{"type":40,"value":3513},{"type":31,"tag":152,"props":3553,"children":3554},{"style":226},[3555],{"type":40,"value":229},{"type":31,"tag":152,"props":3557,"children":3558},{"class":154,"line":232},[3559,3563,3568,3572,3576,3581,3585,3590,3594,3599,3603,3607,3612,3616,3620,3624,3628,3633,3637,3641],{"type":31,"tag":152,"props":3560,"children":3561},{"style":209},[3562],{"type":40,"value":555},{"type":31,"tag":152,"props":3564,"children":3565},{"style":558},[3566],{"type":40,"value":3567}," repo",{"type":31,"tag":152,"props":3569,"children":3570},{"style":266},[3571],{"type":40,"value":566},{"type":31,"tag":152,"props":3573,"children":3574},{"style":226},[3575],{"type":40,"value":629},{"type":31,"tag":152,"props":3577,"children":3578},{"style":498},[3579],{"type":40,"value":3580}," save",{"type":31,"tag":152,"props":3582,"children":3583},{"style":580},[3584],{"type":40,"value":269},{"type":31,"tag":152,"props":3586,"children":3587},{"style":498},[3588],{"type":40,"value":3589}," vi",{"type":31,"tag":152,"props":3591,"children":3592},{"style":580},[3593],{"type":40,"value":583},{"type":31,"tag":152,"props":3595,"children":3596},{"style":193},[3597],{"type":40,"value":3598},"fn",{"type":31,"tag":152,"props":3600,"children":3601},{"style":498},[3602],{"type":40,"value":1488},{"type":31,"tag":152,"props":3604,"children":3605},{"style":580},[3606],{"type":40,"value":583},{"type":31,"tag":152,"props":3608,"children":3609},{"style":193},[3610],{"type":40,"value":3611},"mockResolvedValue",{"type":31,"tag":152,"props":3613,"children":3614},{"style":498},[3615],{"type":40,"value":410},{"type":31,"tag":152,"props":3617,"children":3618},{"style":226},[3619],{"type":40,"value":615},{"type":31,"tag":152,"props":3621,"children":3622},{"style":498},[3623],{"type":40,"value":634},{"type":31,"tag":152,"props":3625,"children":3626},{"style":580},[3627],{"type":40,"value":269},{"type":31,"tag":152,"props":3629,"children":3630},{"style":534},[3631],{"type":40,"value":3632}," 'intent-1'",{"type":31,"tag":152,"props":3634,"children":3635},{"style":226},[3636],{"type":40,"value":653},{"type":31,"tag":152,"props":3638,"children":3639},{"style":498},[3640],{"type":40,"value":829},{"type":31,"tag":152,"props":3642,"children":3643},{"style":226},[3644],{"type":40,"value":3645},"};\n",{"type":31,"tag":152,"props":3647,"children":3648},{"class":154,"line":246},[3649,3653,3658,3662,3666,3671,3676,3681,3686,3690],{"type":31,"tag":152,"props":3650,"children":3651},{"style":209},[3652],{"type":40,"value":555},{"type":31,"tag":152,"props":3654,"children":3655},{"style":558},[3656],{"type":40,"value":3657}," useCase",{"type":31,"tag":152,"props":3659,"children":3660},{"style":266},[3661],{"type":40,"value":566},{"type":31,"tag":152,"props":3663,"children":3664},{"style":519},[3665],{"type":40,"value":522},{"type":31,"tag":152,"props":3667,"children":3668},{"style":193},[3669],{"type":40,"value":3670}," CreateMentoringCheckoutIntentUseCase",{"type":31,"tag":152,"props":3672,"children":3673},{"style":498},[3674],{"type":40,"value":3675},"(repo ",{"type":31,"tag":152,"props":3677,"children":3678},{"style":209},[3679],{"type":40,"value":3680},"as",{"type":31,"tag":152,"props":3682,"children":3683},{"style":422},[3684],{"type":40,"value":3685}," any",{"type":31,"tag":152,"props":3687,"children":3688},{"style":498},[3689],{"type":40,"value":448},{"type":31,"tag":152,"props":3691,"children":3692},{"style":226},[3693],{"type":40,"value":546},{"type":31,"tag":152,"props":3695,"children":3696},{"class":154,"line":282},[3697],{"type":31,"tag":152,"props":3698,"children":3699},{"emptyLinePlaceholder":13},[3700],{"type":40,"value":180},{"type":31,"tag":152,"props":3702,"children":3703},{"class":154,"line":312},[3704,3708,3712,3716,3721,3725,3729,3733,3737,3742,3746,3750,3754,3759,3763,3768,3772,3777,3781,3785],{"type":31,"tag":152,"props":3705,"children":3706},{"style":209},[3707],{"type":40,"value":1363},{"type":31,"tag":152,"props":3709,"children":3710},{"style":498},[3711],{"type":40,"value":3657},{"type":31,"tag":152,"props":3713,"children":3714},{"style":580},[3715],{"type":40,"value":583},{"type":31,"tag":152,"props":3717,"children":3718},{"style":193},[3719],{"type":40,"value":3720},"execute",{"type":31,"tag":152,"props":3722,"children":3723},{"style":498},[3724],{"type":40,"value":410},{"type":31,"tag":152,"props":3726,"children":3727},{"style":226},[3728],{"type":40,"value":615},{"type":31,"tag":152,"props":3730,"children":3731},{"style":498},[3732],{"type":40,"value":435},{"type":31,"tag":152,"props":3734,"children":3735},{"style":580},[3736],{"type":40,"value":269},{"type":31,"tag":152,"props":3738,"children":3739},{"style":534},[3740],{"type":40,"value":3741}," 'c1'",{"type":31,"tag":152,"props":3743,"children":3744},{"style":226},[3745],{"type":40,"value":430},{"type":31,"tag":152,"props":3747,"children":3748},{"style":498},[3749],{"type":40,"value":2140},{"type":31,"tag":152,"props":3751,"children":3752},{"style":580},[3753],{"type":40,"value":269},{"type":31,"tag":152,"props":3755,"children":3756},{"style":534},[3757],{"type":40,"value":3758}," 'cl1'",{"type":31,"tag":152,"props":3760,"children":3761},{"style":226},[3762],{"type":40,"value":430},{"type":31,"tag":152,"props":3764,"children":3765},{"style":498},[3766],{"type":40,"value":3767}," offreId",{"type":31,"tag":152,"props":3769,"children":3770},{"style":580},[3771],{"type":40,"value":269},{"type":31,"tag":152,"props":3773,"children":3774},{"style":534},[3775],{"type":40,"value":3776}," 'o1'",{"type":31,"tag":152,"props":3778,"children":3779},{"style":226},[3780],{"type":40,"value":653},{"type":31,"tag":152,"props":3782,"children":3783},{"style":498},[3784],{"type":40,"value":448},{"type":31,"tag":152,"props":3786,"children":3787},{"style":226},[3788],{"type":40,"value":546},{"type":31,"tag":152,"props":3790,"children":3791},{"class":154,"line":342},[3792],{"type":31,"tag":152,"props":3793,"children":3794},{"emptyLinePlaceholder":13},[3795],{"type":40,"value":180},{"type":31,"tag":152,"props":3797,"children":3798},{"class":154,"line":372},[3799,3804,3809,3813,3818,3822,3827],{"type":31,"tag":152,"props":3800,"children":3801},{"style":193},[3802],{"type":40,"value":3803},"    expect",{"type":31,"tag":152,"props":3805,"children":3806},{"style":498},[3807],{"type":40,"value":3808},"(repo",{"type":31,"tag":152,"props":3810,"children":3811},{"style":580},[3812],{"type":40,"value":583},{"type":31,"tag":152,"props":3814,"children":3815},{"style":498},[3816],{"type":40,"value":3817},"save)",{"type":31,"tag":152,"props":3819,"children":3820},{"style":580},[3821],{"type":40,"value":583},{"type":31,"tag":152,"props":3823,"children":3824},{"style":193},[3825],{"type":40,"value":3826},"toHaveBeenCalledWith",{"type":31,"tag":152,"props":3828,"children":3829},{"style":498},[3830],{"type":40,"value":243},{"type":31,"tag":152,"props":3832,"children":3833},{"class":154,"line":386},[3834,3839,3843,3848,3852,3856,3860,3864,3868,3872,3876],{"type":31,"tag":152,"props":3835,"children":3836},{"style":498},[3837],{"type":40,"value":3838},"      expect",{"type":31,"tag":152,"props":3840,"children":3841},{"style":580},[3842],{"type":40,"value":583},{"type":31,"tag":152,"props":3844,"children":3845},{"style":193},[3846],{"type":40,"value":3847},"objectContaining",{"type":31,"tag":152,"props":3849,"children":3850},{"style":498},[3851],{"type":40,"value":410},{"type":31,"tag":152,"props":3853,"children":3854},{"style":226},[3855],{"type":40,"value":615},{"type":31,"tag":152,"props":3857,"children":3858},{"style":498},[3859],{"type":40,"value":435},{"type":31,"tag":152,"props":3861,"children":3862},{"style":580},[3863],{"type":40,"value":269},{"type":31,"tag":152,"props":3865,"children":3866},{"style":534},[3867],{"type":40,"value":3741},{"type":31,"tag":152,"props":3869,"children":3870},{"style":226},[3871],{"type":40,"value":653},{"type":31,"tag":152,"props":3873,"children":3874},{"style":498},[3875],{"type":40,"value":448},{"type":31,"tag":152,"props":3877,"children":3878},{"style":226},[3879],{"type":40,"value":279},{"type":31,"tag":152,"props":3881,"children":3882},{"class":154,"line":394},[3883,3888,3893],{"type":31,"tag":152,"props":3884,"children":3885},{"style":498},[3886],{"type":40,"value":3887},"    )",{"type":31,"tag":152,"props":3889,"children":3890},{"style":226},[3891],{"type":40,"value":3892},";",{"type":31,"tag":152,"props":3894,"children":3895},{"style":159},[3896],{"type":40,"value":3897}," // vérifie un appel, pas un comportement\n",{"type":31,"tag":152,"props":3899,"children":3900},{"class":154,"line":480},[3901,3906,3910],{"type":31,"tag":152,"props":3902,"children":3903},{"style":226},[3904],{"type":40,"value":3905},"  }",{"type":31,"tag":152,"props":3907,"children":3908},{"style":498},[3909],{"type":40,"value":448},{"type":31,"tag":152,"props":3911,"children":3912},{"style":226},[3913],{"type":40,"value":546},{"type":31,"tag":152,"props":3915,"children":3916},{"class":154,"line":489},[3917,3921,3925],{"type":31,"tag":152,"props":3918,"children":3919},{"style":226},[3920],{"type":40,"value":648},{"type":31,"tag":152,"props":3922,"children":3923},{"style":498},[3924],{"type":40,"value":448},{"type":31,"tag":152,"props":3926,"children":3927},{"style":226},[3928],{"type":40,"value":546},{"type":31,"tag":32,"props":3930,"children":3931},{},[3932],{"type":40,"value":3933},"Ce test ne dit rien. Il vérifie que la fonction appelle une autre fonction. C'est tautologique. Si vous changez l'implémentation pour utiliser un event store au lieu d'un repository, le test casse, sans qu'aucun comportement métier ait changé. C'est le pire des deux mondes : couplage fort à l'implémentation, zéro garantie de correction.",{"type":31,"tag":32,"props":3935,"children":3936},{},[3937,3939,3944],{"type":40,"value":3938},"Le contre-pattern, c'est ce que Dan North appelait ",{"type":31,"tag":99,"props":3940,"children":3941},{},[3942],{"type":40,"value":3943},"\"Tests as Specifications\"",{"type":40,"value":3945}," dans ses articles BDD fondateurs de 2006. Le test décrit un comportement observable :",{"type":31,"tag":141,"props":3947,"children":3949},{"className":143,"code":3948,"language":145,"meta":8,"style":8},"describe('CreateMentoringCheckoutIntentUseCase', () => {\n  it('étant donné une offre active, quand on crée l\\'intent, alors l\\'intent contient le prix de l\\'offre', async () => {\n    // Given\n    const offre = { id: 'o1', price: 150, currency: 'EUR', status: 'ACTIVE' };\n    const repo = new InMemoryCheckoutIntentRepository();\n    const offreRepo = new InMemoryOffreRepository([offre]);\n    const useCase = new CreateMentoringCheckoutIntentUseCase(repo, offreRepo);\n\n    // When\n    const result = await useCase.execute({ coachId: 'c1', clientId: 'cl1', offreId: 'o1' });\n\n    // Then\n    expect(result.amount).toBe(150);\n    expect(result.currency).toBe('EUR');\n    expect(result.status).toBe('PENDING');\n  });\n});\n",[3950],{"type":31,"tag":148,"props":3951,"children":3952},{"__ignoreMap":8},[3953,3984,4049,4057,4146,4178,4212,4252,4259,4267,4363,4370,4378,4425,4470,4515,4530],{"type":31,"tag":152,"props":3954,"children":3955},{"class":154,"line":155},[3956,3960,3964,3968,3972,3976,3980],{"type":31,"tag":152,"props":3957,"children":3958},{"style":193},[3959],{"type":40,"value":3443},{"type":31,"tag":152,"props":3961,"children":3962},{"style":498},[3963],{"type":40,"value":410},{"type":31,"tag":152,"props":3965,"children":3966},{"style":534},[3967],{"type":40,"value":3499},{"type":31,"tag":152,"props":3969,"children":3970},{"style":226},[3971],{"type":40,"value":430},{"type":31,"tag":152,"props":3973,"children":3974},{"style":226},[3975],{"type":40,"value":3508},{"type":31,"tag":152,"props":3977,"children":3978},{"style":266},[3979],{"type":40,"value":3513},{"type":31,"tag":152,"props":3981,"children":3982},{"style":226},[3983],{"type":40,"value":229},{"type":31,"tag":152,"props":3985,"children":3986},{"class":154,"line":165},[3987,3991,3995,4000,4006,4011,4015,4020,4024,4029,4033,4037,4041,4045],{"type":31,"tag":152,"props":3988,"children":3989},{"style":193},[3990],{"type":40,"value":3525},{"type":31,"tag":152,"props":3992,"children":3993},{"style":498},[3994],{"type":40,"value":410},{"type":31,"tag":152,"props":3996,"children":3997},{"style":534},[3998],{"type":40,"value":3999},"'étant donné une offre active, quand on crée l",{"type":31,"tag":152,"props":4001,"children":4003},{"style":4002},"--shiki-default:#F4B8E4;--shiki-dark:#79B8FF",[4004],{"type":40,"value":4005},"\\'",{"type":31,"tag":152,"props":4007,"children":4008},{"style":534},[4009],{"type":40,"value":4010},"intent, alors l",{"type":31,"tag":152,"props":4012,"children":4013},{"style":4002},[4014],{"type":40,"value":4005},{"type":31,"tag":152,"props":4016,"children":4017},{"style":534},[4018],{"type":40,"value":4019},"intent contient le prix de l",{"type":31,"tag":152,"props":4021,"children":4022},{"style":4002},[4023],{"type":40,"value":4005},{"type":31,"tag":152,"props":4025,"children":4026},{"style":534},[4027],{"type":40,"value":4028},"offre'",{"type":31,"tag":152,"props":4030,"children":4031},{"style":226},[4032],{"type":40,"value":430},{"type":31,"tag":152,"props":4034,"children":4035},{"style":209},[4036],{"type":40,"value":3543},{"type":31,"tag":152,"props":4038,"children":4039},{"style":226},[4040],{"type":40,"value":3508},{"type":31,"tag":152,"props":4042,"children":4043},{"style":266},[4044],{"type":40,"value":3513},{"type":31,"tag":152,"props":4046,"children":4047},{"style":226},[4048],{"type":40,"value":229},{"type":31,"tag":152,"props":4050,"children":4051},{"class":154,"line":174},[4052],{"type":31,"tag":152,"props":4053,"children":4054},{"style":159},[4055],{"type":40,"value":4056},"    // Given\n",{"type":31,"tag":152,"props":4058,"children":4059},{"class":154,"line":183},[4060,4064,4069,4073,4077,4081,4085,4089,4093,4098,4102,4107,4111,4116,4120,4125,4129,4133,4137,4141],{"type":31,"tag":152,"props":4061,"children":4062},{"style":209},[4063],{"type":40,"value":555},{"type":31,"tag":152,"props":4065,"children":4066},{"style":558},[4067],{"type":40,"value":4068}," offre",{"type":31,"tag":152,"props":4070,"children":4071},{"style":266},[4072],{"type":40,"value":566},{"type":31,"tag":152,"props":4074,"children":4075},{"style":226},[4076],{"type":40,"value":629},{"type":31,"tag":152,"props":4078,"children":4079},{"style":498},[4080],{"type":40,"value":634},{"type":31,"tag":152,"props":4082,"children":4083},{"style":580},[4084],{"type":40,"value":269},{"type":31,"tag":152,"props":4086,"children":4087},{"style":534},[4088],{"type":40,"value":3776},{"type":31,"tag":152,"props":4090,"children":4091},{"style":226},[4092],{"type":40,"value":430},{"type":31,"tag":152,"props":4094,"children":4095},{"style":498},[4096],{"type":40,"value":4097}," price",{"type":31,"tag":152,"props":4099,"children":4100},{"style":580},[4101],{"type":40,"value":269},{"type":31,"tag":152,"props":4103,"children":4104},{"style":1725},[4105],{"type":40,"value":4106}," 150",{"type":31,"tag":152,"props":4108,"children":4109},{"style":226},[4110],{"type":40,"value":430},{"type":31,"tag":152,"props":4112,"children":4113},{"style":498},[4114],{"type":40,"value":4115}," currency",{"type":31,"tag":152,"props":4117,"children":4118},{"style":580},[4119],{"type":40,"value":269},{"type":31,"tag":152,"props":4121,"children":4122},{"style":534},[4123],{"type":40,"value":4124}," 'EUR'",{"type":31,"tag":152,"props":4126,"children":4127},{"style":226},[4128],{"type":40,"value":430},{"type":31,"tag":152,"props":4130,"children":4131},{"style":498},[4132],{"type":40,"value":1453},{"type":31,"tag":152,"props":4134,"children":4135},{"style":580},[4136],{"type":40,"value":269},{"type":31,"tag":152,"props":4138,"children":4139},{"style":534},[4140],{"type":40,"value":1282},{"type":31,"tag":152,"props":4142,"children":4143},{"style":226},[4144],{"type":40,"value":4145}," };\n",{"type":31,"tag":152,"props":4147,"children":4148},{"class":154,"line":205},[4149,4153,4157,4161,4165,4170,4174],{"type":31,"tag":152,"props":4150,"children":4151},{"style":209},[4152],{"type":40,"value":555},{"type":31,"tag":152,"props":4154,"children":4155},{"style":558},[4156],{"type":40,"value":3567},{"type":31,"tag":152,"props":4158,"children":4159},{"style":266},[4160],{"type":40,"value":566},{"type":31,"tag":152,"props":4162,"children":4163},{"style":519},[4164],{"type":40,"value":522},{"type":31,"tag":152,"props":4166,"children":4167},{"style":193},[4168],{"type":40,"value":4169}," InMemoryCheckoutIntentRepository",{"type":31,"tag":152,"props":4171,"children":4172},{"style":498},[4173],{"type":40,"value":1488},{"type":31,"tag":152,"props":4175,"children":4176},{"style":226},[4177],{"type":40,"value":546},{"type":31,"tag":152,"props":4179,"children":4180},{"class":154,"line":232},[4181,4185,4190,4194,4198,4203,4208],{"type":31,"tag":152,"props":4182,"children":4183},{"style":209},[4184],{"type":40,"value":555},{"type":31,"tag":152,"props":4186,"children":4187},{"style":558},[4188],{"type":40,"value":4189}," offreRepo",{"type":31,"tag":152,"props":4191,"children":4192},{"style":266},[4193],{"type":40,"value":566},{"type":31,"tag":152,"props":4195,"children":4196},{"style":519},[4197],{"type":40,"value":522},{"type":31,"tag":152,"props":4199,"children":4200},{"style":193},[4201],{"type":40,"value":4202}," InMemoryOffreRepository",{"type":31,"tag":152,"props":4204,"children":4205},{"style":498},[4206],{"type":40,"value":4207},"([offre])",{"type":31,"tag":152,"props":4209,"children":4210},{"style":226},[4211],{"type":40,"value":546},{"type":31,"tag":152,"props":4213,"children":4214},{"class":154,"line":246},[4215,4219,4223,4227,4231,4235,4239,4243,4248],{"type":31,"tag":152,"props":4216,"children":4217},{"style":209},[4218],{"type":40,"value":555},{"type":31,"tag":152,"props":4220,"children":4221},{"style":558},[4222],{"type":40,"value":3657},{"type":31,"tag":152,"props":4224,"children":4225},{"style":266},[4226],{"type":40,"value":566},{"type":31,"tag":152,"props":4228,"children":4229},{"style":519},[4230],{"type":40,"value":522},{"type":31,"tag":152,"props":4232,"children":4233},{"style":193},[4234],{"type":40,"value":3670},{"type":31,"tag":152,"props":4236,"children":4237},{"style":498},[4238],{"type":40,"value":3808},{"type":31,"tag":152,"props":4240,"children":4241},{"style":226},[4242],{"type":40,"value":430},{"type":31,"tag":152,"props":4244,"children":4245},{"style":498},[4246],{"type":40,"value":4247}," offreRepo)",{"type":31,"tag":152,"props":4249,"children":4250},{"style":226},[4251],{"type":40,"value":546},{"type":31,"tag":152,"props":4253,"children":4254},{"class":154,"line":282},[4255],{"type":31,"tag":152,"props":4256,"children":4257},{"emptyLinePlaceholder":13},[4258],{"type":40,"value":180},{"type":31,"tag":152,"props":4260,"children":4261},{"class":154,"line":312},[4262],{"type":31,"tag":152,"props":4263,"children":4264},{"style":159},[4265],{"type":40,"value":4266},"    // When\n",{"type":31,"tag":152,"props":4268,"children":4269},{"class":154,"line":342},[4270,4274,4279,4283,4287,4291,4295,4299,4303,4307,4311,4315,4319,4323,4327,4331,4335,4339,4343,4347,4351,4355,4359],{"type":31,"tag":152,"props":4271,"children":4272},{"style":209},[4273],{"type":40,"value":555},{"type":31,"tag":152,"props":4275,"children":4276},{"style":558},[4277],{"type":40,"value":4278}," result",{"type":31,"tag":152,"props":4280,"children":4281},{"style":266},[4282],{"type":40,"value":566},{"type":31,"tag":152,"props":4284,"children":4285},{"style":209},[4286],{"type":40,"value":571},{"type":31,"tag":152,"props":4288,"children":4289},{"style":498},[4290],{"type":40,"value":3657},{"type":31,"tag":152,"props":4292,"children":4293},{"style":580},[4294],{"type":40,"value":583},{"type":31,"tag":152,"props":4296,"children":4297},{"style":193},[4298],{"type":40,"value":3720},{"type":31,"tag":152,"props":4300,"children":4301},{"style":498},[4302],{"type":40,"value":410},{"type":31,"tag":152,"props":4304,"children":4305},{"style":226},[4306],{"type":40,"value":615},{"type":31,"tag":152,"props":4308,"children":4309},{"style":498},[4310],{"type":40,"value":435},{"type":31,"tag":152,"props":4312,"children":4313},{"style":580},[4314],{"type":40,"value":269},{"type":31,"tag":152,"props":4316,"children":4317},{"style":534},[4318],{"type":40,"value":3741},{"type":31,"tag":152,"props":4320,"children":4321},{"style":226},[4322],{"type":40,"value":430},{"type":31,"tag":152,"props":4324,"children":4325},{"style":498},[4326],{"type":40,"value":2140},{"type":31,"tag":152,"props":4328,"children":4329},{"style":580},[4330],{"type":40,"value":269},{"type":31,"tag":152,"props":4332,"children":4333},{"style":534},[4334],{"type":40,"value":3758},{"type":31,"tag":152,"props":4336,"children":4337},{"style":226},[4338],{"type":40,"value":430},{"type":31,"tag":152,"props":4340,"children":4341},{"style":498},[4342],{"type":40,"value":3767},{"type":31,"tag":152,"props":4344,"children":4345},{"style":580},[4346],{"type":40,"value":269},{"type":31,"tag":152,"props":4348,"children":4349},{"style":534},[4350],{"type":40,"value":3776},{"type":31,"tag":152,"props":4352,"children":4353},{"style":226},[4354],{"type":40,"value":653},{"type":31,"tag":152,"props":4356,"children":4357},{"style":498},[4358],{"type":40,"value":448},{"type":31,"tag":152,"props":4360,"children":4361},{"style":226},[4362],{"type":40,"value":546},{"type":31,"tag":152,"props":4364,"children":4365},{"class":154,"line":372},[4366],{"type":31,"tag":152,"props":4367,"children":4368},{"emptyLinePlaceholder":13},[4369],{"type":40,"value":180},{"type":31,"tag":152,"props":4371,"children":4372},{"class":154,"line":386},[4373],{"type":31,"tag":152,"props":4374,"children":4375},{"style":159},[4376],{"type":40,"value":4377},"    // Then\n",{"type":31,"tag":152,"props":4379,"children":4380},{"class":154,"line":394},[4381,4385,4390,4394,4399,4403,4408,4412,4417,4421],{"type":31,"tag":152,"props":4382,"children":4383},{"style":193},[4384],{"type":40,"value":3803},{"type":31,"tag":152,"props":4386,"children":4387},{"style":498},[4388],{"type":40,"value":4389},"(result",{"type":31,"tag":152,"props":4391,"children":4392},{"style":580},[4393],{"type":40,"value":583},{"type":31,"tag":152,"props":4395,"children":4396},{"style":498},[4397],{"type":40,"value":4398},"amount)",{"type":31,"tag":152,"props":4400,"children":4401},{"style":580},[4402],{"type":40,"value":583},{"type":31,"tag":152,"props":4404,"children":4405},{"style":193},[4406],{"type":40,"value":4407},"toBe",{"type":31,"tag":152,"props":4409,"children":4410},{"style":498},[4411],{"type":40,"value":410},{"type":31,"tag":152,"props":4413,"children":4414},{"style":1725},[4415],{"type":40,"value":4416},"150",{"type":31,"tag":152,"props":4418,"children":4419},{"style":498},[4420],{"type":40,"value":448},{"type":31,"tag":152,"props":4422,"children":4423},{"style":226},[4424],{"type":40,"value":546},{"type":31,"tag":152,"props":4426,"children":4427},{"class":154,"line":480},[4428,4432,4436,4440,4445,4449,4453,4457,4462,4466],{"type":31,"tag":152,"props":4429,"children":4430},{"style":193},[4431],{"type":40,"value":3803},{"type":31,"tag":152,"props":4433,"children":4434},{"style":498},[4435],{"type":40,"value":4389},{"type":31,"tag":152,"props":4437,"children":4438},{"style":580},[4439],{"type":40,"value":583},{"type":31,"tag":152,"props":4441,"children":4442},{"style":498},[4443],{"type":40,"value":4444},"currency)",{"type":31,"tag":152,"props":4446,"children":4447},{"style":580},[4448],{"type":40,"value":583},{"type":31,"tag":152,"props":4450,"children":4451},{"style":193},[4452],{"type":40,"value":4407},{"type":31,"tag":152,"props":4454,"children":4455},{"style":498},[4456],{"type":40,"value":410},{"type":31,"tag":152,"props":4458,"children":4459},{"style":534},[4460],{"type":40,"value":4461},"'EUR'",{"type":31,"tag":152,"props":4463,"children":4464},{"style":498},[4465],{"type":40,"value":448},{"type":31,"tag":152,"props":4467,"children":4468},{"style":226},[4469],{"type":40,"value":546},{"type":31,"tag":152,"props":4471,"children":4472},{"class":154,"line":489},[4473,4477,4481,4485,4490,4494,4498,4502,4507,4511],{"type":31,"tag":152,"props":4474,"children":4475},{"style":193},[4476],{"type":40,"value":3803},{"type":31,"tag":152,"props":4478,"children":4479},{"style":498},[4480],{"type":40,"value":4389},{"type":31,"tag":152,"props":4482,"children":4483},{"style":580},[4484],{"type":40,"value":583},{"type":31,"tag":152,"props":4486,"children":4487},{"style":498},[4488],{"type":40,"value":4489},"status)",{"type":31,"tag":152,"props":4491,"children":4492},{"style":580},[4493],{"type":40,"value":583},{"type":31,"tag":152,"props":4495,"children":4496},{"style":193},[4497],{"type":40,"value":4407},{"type":31,"tag":152,"props":4499,"children":4500},{"style":498},[4501],{"type":40,"value":410},{"type":31,"tag":152,"props":4503,"children":4504},{"style":534},[4505],{"type":40,"value":4506},"'PENDING'",{"type":31,"tag":152,"props":4508,"children":4509},{"style":498},[4510],{"type":40,"value":448},{"type":31,"tag":152,"props":4512,"children":4513},{"style":226},[4514],{"type":40,"value":546},{"type":31,"tag":152,"props":4516,"children":4517},{"class":154,"line":549},[4518,4522,4526],{"type":31,"tag":152,"props":4519,"children":4520},{"style":226},[4521],{"type":40,"value":3905},{"type":31,"tag":152,"props":4523,"children":4524},{"style":498},[4525],{"type":40,"value":448},{"type":31,"tag":152,"props":4527,"children":4528},{"style":226},[4529],{"type":40,"value":546},{"type":31,"tag":152,"props":4531,"children":4532},{"class":154,"line":664},[4533,4537,4541],{"type":31,"tag":152,"props":4534,"children":4535},{"style":226},[4536],{"type":40,"value":648},{"type":31,"tag":152,"props":4538,"children":4539},{"style":498},[4540],{"type":40,"value":448},{"type":31,"tag":152,"props":4542,"children":4543},{"style":226},[4544],{"type":40,"value":546},{"type":31,"tag":32,"props":4546,"children":4547},{},[4548,4550,4556],{"type":40,"value":4549},"L'implémentation peut changer, le test reste valable. C'est exactement la philosophie défendue dans ",{"type":31,"tag":64,"props":4551,"children":4553},{"href":4552},"/fr/pratiques-agiles/adopter-behaviour-driven-development-bdd-guide-agile",[4554],{"type":40,"value":4555},"l'adoption du Behaviour-Driven Development",{"type":40,"value":4557}," et dans la Definition of Done bien posée.",{"type":31,"tag":32,"props":4559,"children":4560},{},[4561],{"type":40,"value":4562},"Sur crmcoaching, après avoir appliqué ce changement systématiquement, le ratio de tests \"behavior-level\" est passé de 15% à 70%. La couverture brute a parfois baissé. La couverture utile a triplé.",{"type":31,"tag":48,"props":4564,"children":4565},{},[],{"type":31,"tag":52,"props":4567,"children":4569},{"id":4568},"pattern-4-catch-all-silencieux",[4570],{"type":40,"value":4571},"Pattern #4 : catch-all silencieux",{"type":31,"tag":32,"props":4573,"children":4574},{},[4575],{"type":40,"value":4576},"C'est le pattern le plus dangereux, parce qu'il masque les bugs au lieu de les révéler. Claude écrit volontiers :",{"type":31,"tag":141,"props":4578,"children":4580},{"className":143,"code":4579,"language":145,"meta":8,"style":8},"// apps/api/src/infrastructure/adapters/brevo-notification.adapter.ts\n\nasync sendSlotConfirmation(clientEmail: string, slotId: string): Promise\u003Cvoid> {\n  try {\n    await this.brevoService.sendTransactionalEmail({\n      to: [{ email: clientEmail }],\n      templateId: 12,\n      params: { slotId },\n    });\n  } catch (e) {\n    console.error('notification failed', e);\n    // la suite s'exécute comme si tout allait bien\n  }\n}\n",[4581],{"type":31,"tag":148,"props":4582,"children":4583},{"__ignoreMap":8},[4584,4592,4599,4641,4653,4688,4732,4752,4775,4790,4802,4841,4849,4856],{"type":31,"tag":152,"props":4585,"children":4586},{"class":154,"line":155},[4587],{"type":31,"tag":152,"props":4588,"children":4589},{"style":159},[4590],{"type":40,"value":4591},"// apps/api/src/infrastructure/adapters/brevo-notification.adapter.ts\n",{"type":31,"tag":152,"props":4593,"children":4594},{"class":154,"line":165},[4595],{"type":31,"tag":152,"props":4596,"children":4597},{"emptyLinePlaceholder":13},[4598],{"type":40,"value":180},{"type":31,"tag":152,"props":4600,"children":4601},{"class":154,"line":174},[4602,4607,4612,4617,4621,4626,4632,4637],{"type":31,"tag":152,"props":4603,"children":4604},{"style":498},[4605],{"type":40,"value":4606},"async ",{"type":31,"tag":152,"props":4608,"children":4609},{"style":193},[4610],{"type":40,"value":4611},"sendSlotConfirmation",{"type":31,"tag":152,"props":4613,"children":4614},{"style":498},[4615],{"type":40,"value":4616},"(clientEmail: string",{"type":31,"tag":152,"props":4618,"children":4619},{"style":226},[4620],{"type":40,"value":430},{"type":31,"tag":152,"props":4622,"children":4623},{"style":498},[4624],{"type":40,"value":4625}," slotId: string): ",{"type":31,"tag":152,"props":4627,"children":4629},{"style":4628},"--shiki-default:#E5C890;--shiki-default-font-style:italic;--shiki-dark:#79B8FF;--shiki-dark-font-style:inherit",[4630],{"type":40,"value":4631},"Promise",{"type":31,"tag":152,"props":4633,"children":4634},{"style":266},[4635],{"type":40,"value":4636},"\u003Cvoid>",{"type":31,"tag":152,"props":4638,"children":4639},{"style":226},[4640],{"type":40,"value":229},{"type":31,"tag":152,"props":4642,"children":4643},{"class":154,"line":183},[4644,4649],{"type":31,"tag":152,"props":4645,"children":4646},{"style":498},[4647],{"type":40,"value":4648},"  try ",{"type":31,"tag":152,"props":4650,"children":4651},{"style":226},[4652],{"type":40,"value":919},{"type":31,"tag":152,"props":4654,"children":4655},{"class":154,"line":205},[4656,4660,4664,4668,4672,4676,4680,4684],{"type":31,"tag":152,"props":4657,"children":4658},{"style":209},[4659],{"type":40,"value":1363},{"type":31,"tag":152,"props":4661,"children":4662},{"style":574},[4663],{"type":40,"value":577},{"type":31,"tag":152,"props":4665,"children":4666},{"style":580},[4667],{"type":40,"value":583},{"type":31,"tag":152,"props":4669,"children":4670},{"style":498},[4671],{"type":40,"value":1572},{"type":31,"tag":152,"props":4673,"children":4674},{"style":580},[4675],{"type":40,"value":583},{"type":31,"tag":152,"props":4677,"children":4678},{"style":193},[4679],{"type":40,"value":1581},{"type":31,"tag":152,"props":4681,"children":4682},{"style":498},[4683],{"type":40,"value":410},{"type":31,"tag":152,"props":4685,"children":4686},{"style":226},[4687],{"type":40,"value":919},{"type":31,"tag":152,"props":4689,"children":4690},{"class":154,"line":232},[4691,4695,4699,4703,4707,4711,4715,4720,4724,4728],{"type":31,"tag":152,"props":4692,"children":4693},{"style":498},[4694],{"type":40,"value":1598},{"type":31,"tag":152,"props":4696,"children":4697},{"style":580},[4698],{"type":40,"value":269},{"type":31,"tag":152,"props":4700,"children":4701},{"style":498},[4702],{"type":40,"value":1607},{"type":31,"tag":152,"props":4704,"children":4705},{"style":226},[4706],{"type":40,"value":615},{"type":31,"tag":152,"props":4708,"children":4709},{"style":498},[4710],{"type":40,"value":941},{"type":31,"tag":152,"props":4712,"children":4713},{"style":580},[4714],{"type":40,"value":269},{"type":31,"tag":152,"props":4716,"children":4717},{"style":498},[4718],{"type":40,"value":4719}," clientEmail ",{"type":31,"tag":152,"props":4721,"children":4722},{"style":226},[4723],{"type":40,"value":648},{"type":31,"tag":152,"props":4725,"children":4726},{"style":498},[4727],{"type":40,"value":1705},{"type":31,"tag":152,"props":4729,"children":4730},{"style":226},[4731],{"type":40,"value":279},{"type":31,"tag":152,"props":4733,"children":4734},{"class":154,"line":246},[4735,4739,4743,4748],{"type":31,"tag":152,"props":4736,"children":4737},{"style":498},[4738],{"type":40,"value":1718},{"type":31,"tag":152,"props":4740,"children":4741},{"style":580},[4742],{"type":40,"value":269},{"type":31,"tag":152,"props":4744,"children":4745},{"style":1725},[4746],{"type":40,"value":4747}," 12",{"type":31,"tag":152,"props":4749,"children":4750},{"style":226},[4751],{"type":40,"value":279},{"type":31,"tag":152,"props":4753,"children":4754},{"class":154,"line":282},[4755,4759,4763,4767,4771],{"type":31,"tag":152,"props":4756,"children":4757},{"style":498},[4758],{"type":40,"value":1741},{"type":31,"tag":152,"props":4760,"children":4761},{"style":580},[4762],{"type":40,"value":269},{"type":31,"tag":152,"props":4764,"children":4765},{"style":226},[4766],{"type":40,"value":629},{"type":31,"tag":152,"props":4768,"children":4769},{"style":498},[4770],{"type":40,"value":2767},{"type":31,"tag":152,"props":4772,"children":4773},{"style":226},[4774],{"type":40,"value":972},{"type":31,"tag":152,"props":4776,"children":4777},{"class":154,"line":312},[4778,4782,4786],{"type":31,"tag":152,"props":4779,"children":4780},{"style":226},[4781],{"type":40,"value":981},{"type":31,"tag":152,"props":4783,"children":4784},{"style":498},[4785],{"type":40,"value":448},{"type":31,"tag":152,"props":4787,"children":4788},{"style":226},[4789],{"type":40,"value":546},{"type":31,"tag":152,"props":4791,"children":4792},{"class":154,"line":342},[4793,4797],{"type":31,"tag":152,"props":4794,"children":4795},{"style":226},[4796],{"type":40,"value":3905},{"type":31,"tag":152,"props":4798,"children":4799},{"style":498},[4800],{"type":40,"value":4801}," catch (e) {\n",{"type":31,"tag":152,"props":4803,"children":4804},{"class":154,"line":372},[4805,4810,4815,4819,4824,4828,4833,4837],{"type":31,"tag":152,"props":4806,"children":4807},{"style":498},[4808],{"type":40,"value":4809},"    console.",{"type":31,"tag":152,"props":4811,"children":4812},{"style":193},[4813],{"type":40,"value":4814},"error",{"type":31,"tag":152,"props":4816,"children":4817},{"style":226},[4818],{"type":40,"value":410},{"type":31,"tag":152,"props":4820,"children":4821},{"style":534},[4822],{"type":40,"value":4823},"'notification failed'",{"type":31,"tag":152,"props":4825,"children":4826},{"style":226},[4827],{"type":40,"value":430},{"type":31,"tag":152,"props":4829,"children":4830},{"style":260},[4831],{"type":40,"value":4832}," e",{"type":31,"tag":152,"props":4834,"children":4835},{"style":226},[4836],{"type":40,"value":448},{"type":31,"tag":152,"props":4838,"children":4839},{"style":498},[4840],{"type":40,"value":546},{"type":31,"tag":152,"props":4842,"children":4843},{"class":154,"line":386},[4844],{"type":31,"tag":152,"props":4845,"children":4846},{"style":159},[4847],{"type":40,"value":4848},"    // la suite s'exécute comme si tout allait bien\n",{"type":31,"tag":152,"props":4850,"children":4851},{"class":154,"line":394},[4852],{"type":31,"tag":152,"props":4853,"children":4854},{"style":226},[4855],{"type":40,"value":2224},{"type":31,"tag":152,"props":4857,"children":4858},{"class":154,"line":480},[4859],{"type":31,"tag":152,"props":4860,"children":4861},{"style":498},[4862],{"type":40,"value":2233},{"type":31,"tag":32,"props":4864,"children":4865},{},[4866,4868,4874],{"type":40,"value":4867},"Et la suite du code continue normalement. Le slot a-t-il été confirmé par email ? On ne sait pas. Le ",{"type":31,"tag":148,"props":4869,"children":4871},{"className":4870},[],[4872],{"type":40,"value":4873},"console.error",{"type":40,"value":4875}," est-il regardé par quelqu'un en prod ? Probablement pas. Le client voit \"Réservation confirmée\" alors que Brevo n'a rien envoyé.",{"type":31,"tag":32,"props":4877,"children":4878},{},[4879,4881,4887,4889,4895],{"type":40,"value":4880},"Le contre-pattern craft repose sur trois règles. D'abord, ne jamais avaler une exception sans politique explicite : soit on re-throw, soit on dégrade volontairement (tracé dans une métrique), soit on rollback. Ensuite, ne jamais utiliser ",{"type":31,"tag":148,"props":4882,"children":4884},{"className":4883},[],[4885],{"type":40,"value":4886},"catch (e)",{"type":40,"value":4888}," générique sans typer l'exception attendue : une erreur réseau Brevo ne se traite pas comme une ",{"type":31,"tag":148,"props":4890,"children":4892},{"className":4891},[],[4893],{"type":40,"value":4894},"DomainException",{"type":40,"value":4896},". Enfin, instrumenter chaque catch avec une métrique ou une alerte :",{"type":31,"tag":141,"props":4898,"children":4900},{"className":143,"code":4899,"language":145,"meta":8,"style":8},"async sendSlotConfirmation(clientEmail: string, slotId: string): Promise\u003Cvoid> {\n  try {\n    await this.brevoService.sendTransactionalEmail({\n      to: [{ email: clientEmail }],\n      templateId: 12,\n      params: { slotId },\n    });\n  } catch (err) {\n    this.logger.error('brevo.slot_confirmation.failed', {\n      clientEmail,\n      slotId,\n      error: err instanceof Error ? err.message : String(err),\n    });\n    this.metricsService.increment('notification_failures_total', { type: 'slot_confirmation' });\n    throw new NotificationDeliveryException(`Confirmation slot ${slotId} non envoyée`);\n  }\n}\n",[4901],{"type":31,"tag":148,"props":4902,"children":4903},{"__ignoreMap":8},[4904,4939,4950,4985,5028,5047,5070,5085,5097,5126,5138,5150,5215,5227,5272,5319,5326],{"type":31,"tag":152,"props":4905,"children":4906},{"class":154,"line":155},[4907,4911,4915,4919,4923,4927,4931,4935],{"type":31,"tag":152,"props":4908,"children":4909},{"style":498},[4910],{"type":40,"value":4606},{"type":31,"tag":152,"props":4912,"children":4913},{"style":193},[4914],{"type":40,"value":4611},{"type":31,"tag":152,"props":4916,"children":4917},{"style":498},[4918],{"type":40,"value":4616},{"type":31,"tag":152,"props":4920,"children":4921},{"style":226},[4922],{"type":40,"value":430},{"type":31,"tag":152,"props":4924,"children":4925},{"style":498},[4926],{"type":40,"value":4625},{"type":31,"tag":152,"props":4928,"children":4929},{"style":4628},[4930],{"type":40,"value":4631},{"type":31,"tag":152,"props":4932,"children":4933},{"style":266},[4934],{"type":40,"value":4636},{"type":31,"tag":152,"props":4936,"children":4937},{"style":226},[4938],{"type":40,"value":229},{"type":31,"tag":152,"props":4940,"children":4941},{"class":154,"line":165},[4942,4946],{"type":31,"tag":152,"props":4943,"children":4944},{"style":498},[4945],{"type":40,"value":4648},{"type":31,"tag":152,"props":4947,"children":4948},{"style":226},[4949],{"type":40,"value":919},{"type":31,"tag":152,"props":4951,"children":4952},{"class":154,"line":174},[4953,4957,4961,4965,4969,4973,4977,4981],{"type":31,"tag":152,"props":4954,"children":4955},{"style":209},[4956],{"type":40,"value":1363},{"type":31,"tag":152,"props":4958,"children":4959},{"style":574},[4960],{"type":40,"value":577},{"type":31,"tag":152,"props":4962,"children":4963},{"style":580},[4964],{"type":40,"value":583},{"type":31,"tag":152,"props":4966,"children":4967},{"style":498},[4968],{"type":40,"value":1572},{"type":31,"tag":152,"props":4970,"children":4971},{"style":580},[4972],{"type":40,"value":583},{"type":31,"tag":152,"props":4974,"children":4975},{"style":193},[4976],{"type":40,"value":1581},{"type":31,"tag":152,"props":4978,"children":4979},{"style":498},[4980],{"type":40,"value":410},{"type":31,"tag":152,"props":4982,"children":4983},{"style":226},[4984],{"type":40,"value":919},{"type":31,"tag":152,"props":4986,"children":4987},{"class":154,"line":183},[4988,4992,4996,5000,5004,5008,5012,5016,5020,5024],{"type":31,"tag":152,"props":4989,"children":4990},{"style":498},[4991],{"type":40,"value":1598},{"type":31,"tag":152,"props":4993,"children":4994},{"style":580},[4995],{"type":40,"value":269},{"type":31,"tag":152,"props":4997,"children":4998},{"style":498},[4999],{"type":40,"value":1607},{"type":31,"tag":152,"props":5001,"children":5002},{"style":226},[5003],{"type":40,"value":615},{"type":31,"tag":152,"props":5005,"children":5006},{"style":498},[5007],{"type":40,"value":941},{"type":31,"tag":152,"props":5009,"children":5010},{"style":580},[5011],{"type":40,"value":269},{"type":31,"tag":152,"props":5013,"children":5014},{"style":498},[5015],{"type":40,"value":4719},{"type":31,"tag":152,"props":5017,"children":5018},{"style":226},[5019],{"type":40,"value":648},{"type":31,"tag":152,"props":5021,"children":5022},{"style":498},[5023],{"type":40,"value":1705},{"type":31,"tag":152,"props":5025,"children":5026},{"style":226},[5027],{"type":40,"value":279},{"type":31,"tag":152,"props":5029,"children":5030},{"class":154,"line":205},[5031,5035,5039,5043],{"type":31,"tag":152,"props":5032,"children":5033},{"style":498},[5034],{"type":40,"value":1718},{"type":31,"tag":152,"props":5036,"children":5037},{"style":580},[5038],{"type":40,"value":269},{"type":31,"tag":152,"props":5040,"children":5041},{"style":1725},[5042],{"type":40,"value":4747},{"type":31,"tag":152,"props":5044,"children":5045},{"style":226},[5046],{"type":40,"value":279},{"type":31,"tag":152,"props":5048,"children":5049},{"class":154,"line":232},[5050,5054,5058,5062,5066],{"type":31,"tag":152,"props":5051,"children":5052},{"style":498},[5053],{"type":40,"value":1741},{"type":31,"tag":152,"props":5055,"children":5056},{"style":580},[5057],{"type":40,"value":269},{"type":31,"tag":152,"props":5059,"children":5060},{"style":226},[5061],{"type":40,"value":629},{"type":31,"tag":152,"props":5063,"children":5064},{"style":498},[5065],{"type":40,"value":2767},{"type":31,"tag":152,"props":5067,"children":5068},{"style":226},[5069],{"type":40,"value":972},{"type":31,"tag":152,"props":5071,"children":5072},{"class":154,"line":246},[5073,5077,5081],{"type":31,"tag":152,"props":5074,"children":5075},{"style":226},[5076],{"type":40,"value":981},{"type":31,"tag":152,"props":5078,"children":5079},{"style":498},[5080],{"type":40,"value":448},{"type":31,"tag":152,"props":5082,"children":5083},{"style":226},[5084],{"type":40,"value":546},{"type":31,"tag":152,"props":5086,"children":5087},{"class":154,"line":282},[5088,5092],{"type":31,"tag":152,"props":5089,"children":5090},{"style":226},[5091],{"type":40,"value":3905},{"type":31,"tag":152,"props":5093,"children":5094},{"style":498},[5095],{"type":40,"value":5096}," catch (err) {\n",{"type":31,"tag":152,"props":5098,"children":5099},{"class":154,"line":312},[5100,5105,5109,5113,5118,5122],{"type":31,"tag":152,"props":5101,"children":5102},{"style":498},[5103],{"type":40,"value":5104},"    this.logger.",{"type":31,"tag":152,"props":5106,"children":5107},{"style":193},[5108],{"type":40,"value":4814},{"type":31,"tag":152,"props":5110,"children":5111},{"style":226},[5112],{"type":40,"value":410},{"type":31,"tag":152,"props":5114,"children":5115},{"style":534},[5116],{"type":40,"value":5117},"'brevo.slot_confirmation.failed'",{"type":31,"tag":152,"props":5119,"children":5120},{"style":226},[5121],{"type":40,"value":430},{"type":31,"tag":152,"props":5123,"children":5124},{"style":226},[5125],{"type":40,"value":229},{"type":31,"tag":152,"props":5127,"children":5128},{"class":154,"line":342},[5129,5134],{"type":31,"tag":152,"props":5130,"children":5131},{"style":260},[5132],{"type":40,"value":5133},"      clientEmail",{"type":31,"tag":152,"props":5135,"children":5136},{"style":226},[5137],{"type":40,"value":279},{"type":31,"tag":152,"props":5139,"children":5140},{"class":154,"line":372},[5141,5146],{"type":31,"tag":152,"props":5142,"children":5143},{"style":260},[5144],{"type":40,"value":5145},"      slotId",{"type":31,"tag":152,"props":5147,"children":5148},{"style":226},[5149],{"type":40,"value":279},{"type":31,"tag":152,"props":5151,"children":5152},{"class":154,"line":386},[5153,5159,5163,5168,5173,5178,5183,5188,5192,5197,5201,5206,5211],{"type":31,"tag":152,"props":5154,"children":5156},{"style":5155},"--shiki-default:#C6D0F5;--shiki-dark:#FFAB70",[5157],{"type":40,"value":5158},"      error",{"type":31,"tag":152,"props":5160,"children":5161},{"style":226},[5162],{"type":40,"value":269},{"type":31,"tag":152,"props":5164,"children":5165},{"style":260},[5166],{"type":40,"value":5167}," err",{"type":31,"tag":152,"props":5169,"children":5170},{"style":260},[5171],{"type":40,"value":5172}," instanceof",{"type":31,"tag":152,"props":5174,"children":5175},{"style":260},[5176],{"type":40,"value":5177}," Error",{"type":31,"tag":152,"props":5179,"children":5180},{"style":498},[5181],{"type":40,"value":5182}," ? ",{"type":31,"tag":152,"props":5184,"children":5185},{"style":260},[5186],{"type":40,"value":5187},"err",{"type":31,"tag":152,"props":5189,"children":5190},{"style":498},[5191],{"type":40,"value":583},{"type":31,"tag":152,"props":5193,"children":5194},{"style":5155},[5195],{"type":40,"value":5196},"message",{"type":31,"tag":152,"props":5198,"children":5199},{"style":226},[5200],{"type":40,"value":2329},{"type":31,"tag":152,"props":5202,"children":5203},{"style":260},[5204],{"type":40,"value":5205}," String",{"type":31,"tag":152,"props":5207,"children":5208},{"style":498},[5209],{"type":40,"value":5210},"(err)",{"type":31,"tag":152,"props":5212,"children":5213},{"style":226},[5214],{"type":40,"value":279},{"type":31,"tag":152,"props":5216,"children":5217},{"class":154,"line":394},[5218,5223],{"type":31,"tag":152,"props":5219,"children":5220},{"style":226},[5221],{"type":40,"value":5222},"    })",{"type":31,"tag":152,"props":5224,"children":5225},{"style":498},[5226],{"type":40,"value":546},{"type":31,"tag":152,"props":5228,"children":5229},{"class":154,"line":480},[5230,5235,5240,5244,5248,5254,5258,5263,5267],{"type":31,"tag":152,"props":5231,"children":5232},{"style":498},[5233],{"type":40,"value":5234},"    this.metricsService.increment(",{"type":31,"tag":152,"props":5236,"children":5237},{"style":534},[5238],{"type":40,"value":5239},"'notification_failures_total'",{"type":31,"tag":152,"props":5241,"children":5242},{"style":226},[5243],{"type":40,"value":430},{"type":31,"tag":152,"props":5245,"children":5246},{"style":226},[5247],{"type":40,"value":629},{"type":31,"tag":152,"props":5249,"children":5251},{"style":5250},"--shiki-default:#C6D0F5;--shiki-dark:#B392F0",[5252],{"type":40,"value":5253}," type",{"type":31,"tag":152,"props":5255,"children":5256},{"style":226},[5257],{"type":40,"value":269},{"type":31,"tag":152,"props":5259,"children":5260},{"style":534},[5261],{"type":40,"value":5262}," 'slot_confirmation'",{"type":31,"tag":152,"props":5264,"children":5265},{"style":226},[5266],{"type":40,"value":653},{"type":31,"tag":152,"props":5268,"children":5269},{"style":498},[5270],{"type":40,"value":5271},");\n",{"type":31,"tag":152,"props":5273,"children":5274},{"class":154,"line":489},[5275,5280,5285,5289,5294,5298,5302,5306,5311,5315],{"type":31,"tag":152,"props":5276,"children":5277},{"style":498},[5278],{"type":40,"value":5279},"    throw new ",{"type":31,"tag":152,"props":5281,"children":5282},{"style":193},[5283],{"type":40,"value":5284},"NotificationDeliveryException",{"type":31,"tag":152,"props":5286,"children":5287},{"style":226},[5288],{"type":40,"value":410},{"type":31,"tag":152,"props":5290,"children":5291},{"style":534},[5292],{"type":40,"value":5293},"`Confirmation slot ",{"type":31,"tag":152,"props":5295,"children":5296},{"style":707},[5297],{"type":40,"value":710},{"type":31,"tag":152,"props":5299,"children":5300},{"style":498},[5301],{"type":40,"value":2475},{"type":31,"tag":152,"props":5303,"children":5304},{"style":707},[5305],{"type":40,"value":648},{"type":31,"tag":152,"props":5307,"children":5308},{"style":534},[5309],{"type":40,"value":5310}," non envoyée`",{"type":31,"tag":152,"props":5312,"children":5313},{"style":226},[5314],{"type":40,"value":448},{"type":31,"tag":152,"props":5316,"children":5317},{"style":498},[5318],{"type":40,"value":546},{"type":31,"tag":152,"props":5320,"children":5321},{"class":154,"line":549},[5322],{"type":31,"tag":152,"props":5323,"children":5324},{"style":226},[5325],{"type":40,"value":2224},{"type":31,"tag":152,"props":5327,"children":5328},{"class":154,"line":664},[5329],{"type":31,"tag":152,"props":5330,"children":5331},{"style":498},[5332],{"type":40,"value":2233},{"type":31,"tag":32,"props":5334,"children":5335},{},[5336,5338,5343,5345,5351],{"type":40,"value":5337},"Michael Nygard a documenté ce sujet en profondeur dans ",{"type":31,"tag":99,"props":5339,"children":5340},{},[5341],{"type":40,"value":5342},"Release It!",{"type":40,"value":5344}," (2007). Les ",{"type":31,"tag":64,"props":5346,"children":5348},{"href":5347},"/fr/architecture-craft/patterns-resilience-circuit-breaker-retry",[5349],{"type":40,"value":5350},"patterns de résilience type circuit breaker et retry",{"type":40,"value":5352}," n'ont de sens que si les erreurs sont visibles. Un catch-all silencieux casse toute la stratégie de résilience en amont.",{"type":31,"tag":48,"props":5354,"children":5355},{},[],{"type":31,"tag":52,"props":5357,"children":5359},{"id":5358},"pattern-5-dépendances-non-auditées",[5360],{"type":40,"value":5361},"Pattern #5 : dépendances non auditées",{"type":31,"tag":32,"props":5363,"children":5364},{},[5365,5367,5373,5375,5381,5383,5389,5391,5397],{"type":40,"value":5366},"Le dernier pattern est le plus invisible. Claude propose une dépendance pour résoudre un problème : \"Ajoute ",{"type":31,"tag":148,"props":5368,"children":5370},{"className":5369},[],[5371],{"type":40,"value":5372},"stripe",{"type":40,"value":5374}," pour les checkouts\", \"Utilise ",{"type":31,"tag":148,"props":5376,"children":5378},{"className":5377},[],[5379],{"type":40,"value":5380},"jose",{"type":40,"value":5382}," pour signer ce token\", \"Importe ",{"type":31,"tag":148,"props":5384,"children":5386},{"className":5385},[],[5387],{"type":40,"value":5388},"date-fns",{"type":40,"value":5390}," pour ce calcul de durée\". Le développeur lance ",{"type":31,"tag":148,"props":5392,"children":5394},{"className":5393},[],[5395],{"type":40,"value":5396},"pnpm add \u003Cpkg>",{"type":40,"value":5398},", ça compile, ça passe les tests, ça merge. Et l'artefact entre dans le repo, sans audit, sans justification.",{"type":31,"tag":32,"props":5400,"children":5401},{},[5402,5404,5410],{"type":40,"value":5403},"Le problème, ce sont les chiffres du Snyk Open Source Security Report 2024 : les attaques sur la supply chain ont augmenté de 156% en un an. Les écosystèmes les plus touchés incluent npm, PyPI et Maven Central, précisément ceux que Claude suggère le plus. Sur le cas xz-utils (CVE-2024-3094, mars 2024), une backdoor s'est glissée pendant 2 ans dans un package que tout le monde utilisait sans relire. Le sujet de fond est traité dans ",{"type":31,"tag":64,"props":5405,"children":5407},{"href":5406},"/fr/intelligence-artificielle/llm-securite-code-vulnerabilites",[5408],{"type":40,"value":5409},"les vulnérabilités de sécurité dans le code LLM-généré",{"type":40,"value":583},{"type":31,"tag":32,"props":5412,"children":5413},{},[5414,5416,5422,5424,5430],{"type":40,"value":5415},"Le contre-pattern craft repose sur 3 réflexes. D'abord, refuser toute nouvelle dépendance qui n'a pas été justifiée par un commentaire de PR (quelle alternative native Node ? quel score de vulnérabilités npm audit ? combien de mainteneurs actifs ?). Ensuite, mesurer la ",{"type":31,"tag":148,"props":5417,"children":5419},{"className":5418},[],[5420],{"type":40,"value":5421},"time-to-patch",{"type":40,"value":5423}," sur les CVE critiques (en dessous de 7 jours = sain). Enfin, automatiser la veille via ",{"type":31,"tag":64,"props":5425,"children":5427},{"href":5426},"/fr/dette-technique/dependabot-craft-gestion-dependances",[5428],{"type":40,"value":5429},"Dependabot configuré craft",{"type":40,"value":5431}," avec auto-merge sur les patches et review humaine sur les majors.",{"type":31,"tag":32,"props":5433,"children":5434},{},[5435,5437,5443],{"type":40,"value":5436},"Sur crmcoaching, j'audite chaque dépendance que Claude propose. Je vérifie le nombre de mainteneurs, la date du dernier commit, le score ",{"type":31,"tag":148,"props":5438,"children":5440},{"className":5439},[],[5441],{"type":40,"value":5442},"pnpm audit",{"type":40,"value":5444},". 30 secondes par dépendance. C'est ce qui fait la différence entre un repo sain et un repo qui exfiltre des données dans 2 ans.",{"type":31,"tag":48,"props":5446,"children":5447},{},[],{"type":31,"tag":52,"props":5449,"children":5451},{"id":5450},"les-5-garde-fous-craft-à-installer-dès-lundi",[5452],{"type":40,"value":5453},"Les 5 garde-fous craft à installer dès lundi",{"type":31,"tag":32,"props":5455,"children":5456},{},[5457],{"type":40,"value":5458},"Voici la grille condensée. Mettez-la en checklist GitHub PR template.",{"type":31,"tag":5460,"props":5461,"children":5462},"table",{},[5463,5487],{"type":31,"tag":5464,"props":5465,"children":5466},"thead",{},[5467],{"type":31,"tag":5468,"props":5469,"children":5470},"tr",{},[5471,5477,5482],{"type":31,"tag":5472,"props":5473,"children":5474},"th",{},[5475],{"type":40,"value":5476},"Pattern",{"type":31,"tag":5472,"props":5478,"children":5479},{},[5480],{"type":40,"value":5481},"Signal en review",{"type":31,"tag":5472,"props":5483,"children":5484},{},[5485],{"type":40,"value":5486},"Contre-pattern craft",{"type":31,"tag":5488,"props":5489,"children":5490},"tbody",{},[5491,5510,5552,5576,5600],{"type":31,"tag":5468,"props":5492,"children":5493},{},[5494,5500,5505],{"type":31,"tag":5495,"props":5496,"children":5497},"td",{},[5498],{"type":40,"value":5499},"God Function",{"type":31,"tag":5495,"props":5501,"children":5502},{},[5503],{"type":40,"value":5504},"Fonction > 40 lignes ou > 3 niveaux d'indentation",{"type":31,"tag":5495,"props":5506,"children":5507},{},[5508],{"type":40,"value":5509},"Découpe SRP en sous-fonctions nommées",{"type":31,"tag":5468,"props":5511,"children":5512},{},[5513,5518,5542],{"type":31,"tag":5495,"props":5514,"children":5515},{},[5516],{"type":40,"value":5517},"Couplage ORM",{"type":31,"tag":5495,"props":5519,"children":5520},{},[5521,5526,5528,5534,5536],{"type":31,"tag":148,"props":5522,"children":5524},{"className":5523},[],[5525],{"type":40,"value":2314},{"type":40,"value":5527}," injecté dans ",{"type":31,"tag":148,"props":5529,"children":5531},{"className":5530},[],[5532],{"type":40,"value":5533},"application/",{"type":40,"value":5535}," ou ",{"type":31,"tag":148,"props":5537,"children":5539},{"className":5538},[],[5540],{"type":40,"value":5541},"domain/",{"type":31,"tag":5495,"props":5543,"children":5544},{},[5545,5547],{"type":40,"value":5546},"Interface Repository (port), adapter Prisma en ",{"type":31,"tag":148,"props":5548,"children":5550},{"className":5549},[],[5551],{"type":40,"value":2917},{"type":31,"tag":5468,"props":5553,"children":5554},{},[5555,5560,5571],{"type":31,"tag":5495,"props":5556,"children":5557},{},[5558],{"type":40,"value":5559},"Tests vides",{"type":31,"tag":5495,"props":5561,"children":5562},{},[5563,5569],{"type":31,"tag":148,"props":5564,"children":5566},{"className":5565},[],[5567],{"type":40,"value":5568},"expect(repo.save).toHaveBeenCalled()",{"type":40,"value":5570}," sans assertion comportementale",{"type":31,"tag":5495,"props":5572,"children":5573},{},[5574],{"type":40,"value":5575},"Format Given/When/Then sur comportement observable",{"type":31,"tag":5468,"props":5577,"children":5578},{},[5579,5584,5595],{"type":31,"tag":5495,"props":5580,"children":5581},{},[5582],{"type":40,"value":5583},"Catch-all silencieux",{"type":31,"tag":5495,"props":5585,"children":5586},{},[5587,5593],{"type":31,"tag":148,"props":5588,"children":5590},{"className":5589},[],[5591],{"type":40,"value":5592},"catch (e) { console.error(e) }",{"type":40,"value":5594}," sans politique",{"type":31,"tag":5495,"props":5596,"children":5597},{},[5598],{"type":40,"value":5599},"Re-throw typé, métrique, ou rollback",{"type":31,"tag":5468,"props":5601,"children":5602},{},[5603,5608,5621],{"type":31,"tag":5495,"props":5604,"children":5605},{},[5606],{"type":40,"value":5607},"Dépendance non auditée",{"type":31,"tag":5495,"props":5609,"children":5610},{},[5611,5613,5619],{"type":40,"value":5612},"Entrée ",{"type":31,"tag":148,"props":5614,"children":5616},{"className":5615},[],[5617],{"type":40,"value":5618},"package.json",{"type":40,"value":5620}," sans commentaire de justification",{"type":31,"tag":5495,"props":5622,"children":5623},{},[5624,5626,5631],{"type":40,"value":5625},"Audit 30 sec (",{"type":31,"tag":148,"props":5627,"children":5629},{"className":5628},[],[5630],{"type":40,"value":5442},{"type":40,"value":5632},") + Dependabot configuré craft",{"type":31,"tag":32,"props":5634,"children":5635},{},[5636],{"type":40,"value":5637},"Cette grille tient en 5 minutes par PR. Elle attrape 80% des patterns dangereux que j'ai vus en construisant crmcoaching et lors de mes accompagnements. Elle s'inscrit naturellement dans la philosophie Boy Scout Rule : on laisse le code un peu mieux qu'on l'a trouvé, à chaque PR.",{"type":31,"tag":48,"props":5639,"children":5640},{},[],{"type":31,"tag":5642,"props":5643,"children":5648},"cta",{"cta":5644,"href":5645,"title":5646,"type":5647},"Coder comme un senior →","https://app.kamanga.fr/forms/mentoring","Vous voulez voir ces patterns dans une PR Claude avant qu'ils ne deviennent de la dette ?","call",[5649],{"type":31,"tag":32,"props":5650,"children":5651},{},[5652],{"type":40,"value":5653},"Repérer une God Function ou un catch-all silencieux dans une suggestion de Claude, ça ne s'apprend pas en lisant un article : ça se travaille. En mentoring 1:1, je relis votre code avec vous, on rejoue vos prompts, et on installe ensemble le réflexe de review qui transforme Claude en exécutant discipliné. Vous repartez en voyant ce que le modèle ne voit pas.",{"type":31,"tag":48,"props":5655,"children":5656},{},[],{"type":31,"tag":52,"props":5658,"children":5660},{"id":5659},"ce-que-ça-change-concrètement",[5661],{"type":40,"value":5662},"Ce que ça change concrètement",{"type":31,"tag":32,"props":5664,"children":5665},{},[5666],{"type":40,"value":5667},"Sur crmcoaching, après avoir installé cette grille et appliqué une vraie discipline de code review, voici les chiffres avant/après mesurés sur 6 mois.",{"type":31,"tag":5460,"props":5669,"children":5670},{},[5671,5692],{"type":31,"tag":5464,"props":5672,"children":5673},{},[5674],{"type":31,"tag":5468,"props":5675,"children":5676},{},[5677,5682,5687],{"type":31,"tag":5472,"props":5678,"children":5679},{},[5680],{"type":40,"value":5681},"Métrique",{"type":31,"tag":5472,"props":5683,"children":5684},{},[5685],{"type":40,"value":5686},"Avant grille",{"type":31,"tag":5472,"props":5688,"children":5689},{},[5690],{"type":40,"value":5691},"Après 6 mois",{"type":31,"tag":5488,"props":5693,"children":5694},{},[5695,5713,5731,5749,5767],{"type":31,"tag":5468,"props":5696,"children":5697},{},[5698,5703,5708],{"type":31,"tag":5495,"props":5699,"children":5700},{},[5701],{"type":40,"value":5702},"Fonctions > 40 lignes dans le repo",{"type":31,"tag":5495,"props":5704,"children":5705},{},[5706],{"type":40,"value":5707},"22% des fonctions",{"type":31,"tag":5495,"props":5709,"children":5710},{},[5711],{"type":40,"value":5712},"4% des fonctions",{"type":31,"tag":5468,"props":5714,"children":5715},{},[5716,5721,5726],{"type":31,"tag":5495,"props":5717,"children":5718},{},[5719],{"type":40,"value":5720},"Couverture de tests behavior-level",{"type":31,"tag":5495,"props":5722,"children":5723},{},[5724],{"type":40,"value":5725},"15%",{"type":31,"tag":5495,"props":5727,"children":5728},{},[5729],{"type":40,"value":5730},"70%",{"type":31,"tag":5468,"props":5732,"children":5733},{},[5734,5739,5744],{"type":31,"tag":5495,"props":5735,"children":5736},{},[5737],{"type":40,"value":5738},"Incidents prod liés à exception swallowed",{"type":31,"tag":5495,"props":5740,"children":5741},{},[5742],{"type":40,"value":5743},"4 par trimestre",{"type":31,"tag":5495,"props":5745,"children":5746},{},[5747],{"type":40,"value":5748},"0 par trimestre",{"type":31,"tag":5468,"props":5750,"children":5751},{},[5752,5757,5762],{"type":31,"tag":5495,"props":5753,"children":5754},{},[5755],{"type":40,"value":5756},"Time-to-patch CVE critique",{"type":31,"tag":5495,"props":5758,"children":5759},{},[5760],{"type":40,"value":5761},"38 jours",{"type":31,"tag":5495,"props":5763,"children":5764},{},[5765],{"type":40,"value":5766},"6 jours",{"type":31,"tag":5468,"props":5768,"children":5769},{},[5770,5775,5780],{"type":31,"tag":5495,"props":5771,"children":5772},{},[5773],{"type":40,"value":5774},"Heures consacrées au refactoring d'urgence",{"type":31,"tag":5495,"props":5776,"children":5777},{},[5778],{"type":40,"value":5779},"12h/semaine",{"type":31,"tag":5495,"props":5781,"children":5782},{},[5783],{"type":40,"value":5784},"3h/semaine",{"type":31,"tag":32,"props":5786,"children":5787},{},[5788,5790,5796],{"type":40,"value":5789},"Le gain est mesurable, et il est financier. Une heure de dev senior coûte entre 80 et 150 euros chargée. Économiser 9 heures par semaine, c'est une différence considérable sur l'année. Pour une équipe qui a peur de \"ralentir\" en imposant des règles de review, le calcul retourne le sens : c'est l'absence de règles qui ralentit, pas leur présence. C'est exactement l'angle que je détaille dans ",{"type":31,"tag":64,"props":5791,"children":5793},{"href":5792},"/fr/dette-technique/ingenierie-logicielle-avantage-concurrentiel",[5794],{"type":40,"value":5795},"l'ingénierie logicielle comme avantage concurrentiel",{"type":40,"value":583},{"type":31,"tag":48,"props":5798,"children":5799},{},[],{"type":31,"tag":52,"props":5801,"children":5803},{"id":5802},"conclusion",[5804],{"type":40,"value":5805},"Conclusion",{"type":31,"tag":32,"props":5807,"children":5808},{},[5809],{"type":40,"value":5810},"Ce que je veux que vous reteniez de cet article, c'est que Claude n'écrit pas de mauvais code par malveillance. Il écrit le code statistiquement moyen de son training data, et ce code moyen est plein d'anti-patterns silencieux que les équipes humaines apprenaient à éviter en 5 ans de mentoring. Sans grille explicite, ces patterns rentrent dans votre repo à 2 PR par jour, et au bout de 12 mois votre dette technique a triplé.",{"type":31,"tag":32,"props":5812,"children":5813},{},[5814],{"type":40,"value":5815},"La bonne nouvelle, c'est que Claude répond très bien à un prompt précis et à un contre-pattern nommé. Il n'a pas d'ego. Il ne défend pas ses choix. Si vous lui dites \"réécris ce use case en respectant le SRP, chaque helper de moins de 20 lignes\", il s'exécute proprement. Le craft, en 2026, consiste à savoir nommer les patterns qu'on attend, à les imposer en review, et à transformer Claude en exécutant discipliné plutôt qu'en générateur de moyenne statistique.",{"type":31,"tag":32,"props":5817,"children":5818},{},[5819],{"type":40,"value":5820},"Si en lisant ces lignes vous reconnaissez votre situation, vous avez deux choix. Vous pouvez laisser les 5 patterns s'installer un peu plus chaque jour. Ou vous pouvez commencer lundi matin, par une grille de 5 questions en review, et reprendre le contrôle de votre codebase.",{"type":31,"tag":32,"props":5822,"children":5823},{},[5824,5826,5833],{"type":40,"value":5825},"Pour suivre la suite des patterns craft que je documente chaque semaine, retrouvez-moi sur ",{"type":31,"tag":64,"props":5827,"children":5830},{"href":5828,"rel":5829},"https://www.instagram.com/kamangacode/",[68],[5831],{"type":40,"value":5832},"mon profil Instagram kamangacode",{"type":40,"value":583},{"type":31,"tag":48,"props":5835,"children":5836},{},[],{"type":31,"tag":5642,"props":5838,"children":5843},{"cta":5839,"href":5840,"title":5841,"type":5842},"Les 100 pratiques que l'IA n'enseigne pas →","https://kamanga.fr/referentiel-craft","Ces 5 garde-fous ne sont qu'un début : il en existe 100","product",[5844],{"type":31,"tag":32,"props":5845,"children":5846},{},[5847],{"type":40,"value":5848},"La grille de review décrite ici neutralise 5 anti-patterns que Claude reproduit en silence. Elle fait partie d'un référentiel bien plus large : le Craft Bundle, les 100 pratiques craft que j'applique pour coder propre. Ce sont celles que l'IA ne vous apprendra jamais, parce qu'elle ne les a jamais vues tenir en production sur le long terme.",{"type":31,"tag":48,"props":5850,"children":5851},{},[],{"type":31,"tag":52,"props":5853,"children":5855},{"id":5854},"faq-sur-les-anti-patterns-claude-et-la-review-craft",[5856],{"type":40,"value":5857},"FAQ sur les anti-patterns Claude et la review craft",{"type":31,"tag":5859,"props":5860,"children":5861},"details",{},[5862,5868],{"type":31,"tag":5863,"props":5864,"children":5865},"summary",{},[5866],{"type":40,"value":5867},"1. Comment introduire cette grille sans braquer une équipe qui aime Claude ?",{"type":31,"tag":32,"props":5869,"children":5870},{},[5871],{"type":40,"value":5872},"La meilleure approche que j'ai vue, c'est de présenter la grille non comme \"Claude écrit du mauvais code\" mais comme \"Claude écrit le code moyen, et notre standard est plus haut que la moyenne\". L'équipe ne se sent pas attaquée, elle se sent élevée. Combiné à une démo concrète sur leur propre repo (3 exemples de God Function trouvés en 5 minutes), l'adhésion vient en 2 sprints. C'est aussi ce que permet une vraie culture engineering de rituels bien posée.",{"type":31,"tag":5859,"props":5874,"children":5875},{},[5876,5881],{"type":31,"tag":5863,"props":5877,"children":5878},{},[5879],{"type":40,"value":5880},"2. Faut-il refuser Claude sur les use cases critiques (paiement, auth) ?",{"type":31,"tag":32,"props":5882,"children":5883},{},[5884,5886,5891],{"type":40,"value":5885},"Non, mais il faut prompter différemment. Sur du critique, je donne explicitement à Claude le contexte de concurrence, de criticité, et les patterns attendus. Exemple : ",{"type":31,"tag":99,"props":5887,"children":5888},{},[5889],{"type":40,"value":5890},"\"Ce use case gère un checkout Stripe sur un SaaS multi-tenant. Utilise une transaction Prisma, type les exceptions, ne swallow rien.\"",{"type":40,"value":5892}," Le résultat est radicalement meilleur.",{"type":31,"tag":5859,"props":5894,"children":5895},{},[5896,5901],{"type":31,"tag":5863,"props":5897,"children":5898},{},[5899],{"type":40,"value":5900},"3. Comment automatiser la détection de ces 5 patterns ?",{"type":31,"tag":32,"props":5902,"children":5903},{},[5904,5906,5912,5914,5920,5922,5927,5929,5934],{"type":40,"value":5905},"Partiellement. Biome détecte les fonctions trop longues (",{"type":31,"tag":148,"props":5907,"children":5909},{"className":5908},[],[5910],{"type":40,"value":5911},"noExcessiveLinesPerFunction",{"type":40,"value":5913},"), la complexité cognitive (",{"type":31,"tag":148,"props":5915,"children":5917},{"className":5916},[],[5918],{"type":40,"value":5919},"noExcessiveCognitiveComplexity",{"type":40,"value":5921},"), et les ",{"type":31,"tag":148,"props":5923,"children":5925},{"className":5924},[],[5926],{"type":40,"value":4886},{"type":40,"value":5928}," génériques. Les patterns \"tests vides\" et \"dépendances non auditées\" demandent une vigilance humaine ou des outils spécialisés (Vitest coverage + mutation testing pour les tests, ",{"type":31,"tag":148,"props":5930,"children":5932},{"className":5931},[],[5933],{"type":40,"value":5442},{"type":40,"value":5935}," + Dependabot pour les packages npm). L'arsenal complet est détaillé dans les outils d'analyse statique en 2026.",{"type":31,"tag":5859,"props":5937,"children":5938},{},[5939,5944],{"type":31,"tag":5863,"props":5940,"children":5941},{},[5942],{"type":40,"value":5943},"4. Le pattern God Function vient-il vraiment de Claude ou existait-il déjà ?",{"type":31,"tag":32,"props":5945,"children":5946},{},[5947],{"type":40,"value":5948},"Il existait déjà, mais Claude l'amplifie. Avant 2023, une fonction de 80 lignes existait dans 8% des PR humaines selon mes mesures. En 2025, elle existe dans 23% des PR contenant du code IA-généré non révisé. L'IA ne crée pas le pattern, elle le multiplie par 3.",{"type":31,"tag":5859,"props":5950,"children":5951},{},[5952,5957],{"type":31,"tag":5863,"props":5953,"children":5954},{},[5955],{"type":40,"value":5956},"5. Quelle taille maximum recommander pour une fonction ?",{"type":31,"tag":32,"props":5958,"children":5959},{},[5960,5962,5966,5968,5973],{"type":40,"value":5961},"Robert C. Martin disait dans ",{"type":31,"tag":99,"props":5963,"children":5964},{},[5965],{"type":40,"value":103},{"type":40,"value":5967}," : \"Functions should be small. Then they should be smaller than that.\" Concrètement, je m'impose 20 lignes maximum pour une fonction métier, 5 niveaux d'indentation maximum, 3 paramètres maximum (au-delà, c'est un objet). Ce sont des règles arbitraires, mais elles forcent à découper. Sur crmcoaching, 94% des fonctions respectent ces seuils, et Biome (",{"type":31,"tag":148,"props":5969,"children":5971},{"className":5970},[],[5972],{"type":40,"value":5911},{"type":40,"value":5974},") fait échouer le lint si on dépasse.",{"type":31,"tag":5859,"props":5976,"children":5977},{},[5978,5983],{"type":31,"tag":5863,"props":5979,"children":5980},{},[5981],{"type":40,"value":5982},"6. Les tests behavior-level ne ralentissent-ils pas la CI ?",{"type":31,"tag":32,"props":5984,"children":5985},{},[5986],{"type":40,"value":5987},"Au contraire. Les tests behavior-level sont souvent plus rapides que les tests unitaires couplés à l'implémentation, parce qu'ils ne re-testent pas la même chose à 5 endroits. Sur crmcoaching, la CI tourne en 4 minutes pour 1 200 tests behavior-level. Le facteur limitant n'est plus le temps, c'est la qualité du test, ce qui est aussi le sujet de fond traité dans la checklist pour tester du code généré par IA.",{"type":31,"tag":48,"props":5989,"children":5990},{},[],{"type":31,"tag":5642,"props":5992,"children":5997},{"cta":5993,"href":5994,"title":5995,"type":5996},"Évaluer la maturité de mon équipe →","/mes-ressources","Ressource gratuite : Engineering Maturity Assessment","resource",[5998],{"type":31,"tag":32,"props":5999,"children":6000},{},[6001],{"type":40,"value":6002},"L'EMA est l'outil que je propose au début de chaque mission. Il mesure la maturité de votre équipe sur plusieurs axes engineering : qualité du code, gouvernance IA, dette technique, code review. Quelques minutes pour identifier lequel des 5 patterns vous touche le plus, et où concentrer vos efforts en priorité.",{"type":31,"tag":6004,"props":6005,"children":6006},"style",{},[6007],{"type":40,"value":6008},"html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}",{"title":8,"searchDepth":165,"depth":165,"links":6010},[6011,6012,6013,6014,6015,6016,6017,6018,6019,6020],{"id":54,"depth":165,"text":57},{"id":126,"depth":165,"text":129},{"id":2300,"depth":165,"text":2303},{"id":3429,"depth":165,"text":3432},{"id":4568,"depth":165,"text":4571},{"id":5358,"depth":165,"text":5361},{"id":5450,"depth":165,"text":5453},{"id":5659,"depth":165,"text":5662},{"id":5802,"depth":165,"text":5805},{"id":5854,"depth":165,"text":5857},"markdown","content:fr:intelligence-artificielle:5-patterns-dangereux-claude.md","content","fr/intelligence-artificielle/5-patterns-dangereux-claude.md","fr/intelligence-artificielle/5-patterns-dangereux-claude","md",{"_path":6028,"_dir":6,"_draft":7,"_partial":7,"_locale":8,"title":6029,"description":6030,"id":2094,"date":6031,"listed":13,"nocomments":7,"hidden":7,"categories":6032,"tags":6033,"cover":6035,"readingTime":6036,"body":6041,"_type":6021,"_id":8444,"_source":6023,"_file":8445,"_stem":8446,"_extension":6026},"/fr/intelligence-artificielle/bug-claude-vendredi-dernier","Le bug que Claude vous a fait coder vendredi dernier (sans que vous le sachiez)","Anatomie d'une race condition générée par IA dans le module slot-hold de crmcoaching, et la méthode craft pour la voir avant la prod.","2026-05-04",[6],[16,6034,19,18,20],"race-condition","covers/articles/bug-claude-vendredi-dernier.jpg",{"text":6037,"minutes":6038,"time":6039,"words":6040},"12 min read",11.12,667200,2224,{"type":28,"children":6042,"toc":8435},[6043,6059,6064,6073,6076,6082,6094,6122,6143,6169,6172,6178,6190,6707,6733,6752,6764,6767,6776,6779,6785,6790,7315,7320,7489,7533,7552,7555,7561,7566,7583,7600,7632,7664,8141,8146,8149,8153,8158,8255,8268,8271,8280,8283,8287,8292,8297,8302,8314,8317,8323,8341,8354,8381,8394,8407,8420,8423,8431],{"type":31,"tag":32,"props":6044,"children":6045},{},[6046],{"type":31,"tag":36,"props":6047,"children":6048},{},[6049,6051,6057],{"type":40,"value":6050},"Un vendredi de février 2026, je relisais une PR que Claude venait d'écrire pour le module de réservation de créneau (slot-hold) de crmcoaching. 47 lignes, tests verts, tout avait l'air propre. Sauf qu'au beau milieu du use case ",{"type":31,"tag":148,"props":6052,"children":6054},{"className":6053},[],[6055],{"type":40,"value":6056},"holdSlot",{"type":40,"value":6058}," se cachait une race condition qui, en prod, aurait permis à deux clients de réserver le même créneau au même instant. Personne ne l'avait vue. Pas même moi, au premier regard.",{"type":31,"tag":32,"props":6060,"children":6061},{},[6062],{"type":40,"value":6063},"C'est ce genre de PR qui m'a fait changer ma méthode de review depuis que je développe crmcoaching avec Claude. Voici ce que j'ai appris à repérer, pourquoi Claude écrit ce genre de code, et la grille en 4 points que j'applique aujourd'hui sur chaque PR IA-générée.",{"type":31,"tag":32,"props":6065,"children":6066},{},[6067],{"type":31,"tag":6068,"props":6069,"children":6072},"img",{"alt":6070,"src":6071},"Le module client de crmcoaching, que je développe avec Claude","/images/crm/client.png",[],{"type":31,"tag":48,"props":6074,"children":6075},{},[],{"type":31,"tag":52,"props":6077,"children":6079},{"id":6078},"pourquoi-les-bugs-claude-passent-en-review",[6080],{"type":40,"value":6081},"Pourquoi les bugs Claude passent en review",{"type":31,"tag":32,"props":6083,"children":6084},{},[6085,6087,6092],{"type":40,"value":6086},"Le constat est simple, et il est documenté. Selon le ",{"type":31,"tag":64,"props":6088,"children":6090},{"href":66,"rel":6089},[68],[6091],{"type":40,"value":71},{"type":40,"value":6093},", les équipes qui s'appuient sur Claude voient le ratio de code \"moved or refactored\" baisser de 39%, et le code \"copied\" augmenter de 8 fois. Concrètement, le code IA-généré ressemble à du code propre, mais il transporte des patterns silencieux que la review humaine n'attrape plus.",{"type":31,"tag":32,"props":6095,"children":6096},{},[6097,6099,6104,6106,6112,6114,6120],{"type":40,"value":6098},"Le vendredi dont je parle, la PR portait sur ",{"type":31,"tag":148,"props":6100,"children":6102},{"className":6101},[],[6103],{"type":40,"value":6056},{"type":40,"value":6105}," : un use case NestJS qui lisait le statut du créneau en base, vérifiait qu'il était ",{"type":31,"tag":148,"props":6107,"children":6109},{"className":6108},[],[6110],{"type":40,"value":6111},"AVAILABLE",{"type":40,"value":6113},", puis écrivait ",{"type":31,"tag":148,"props":6115,"children":6117},{"className":6116},[],[6118],{"type":40,"value":6119},"HELD",{"type":40,"value":6121},". Tests verts parce que les tests unitaires mockaient le repository Prisma. Tests d'intégration verts parce qu'ils tournaient en séquentiel. La race condition était invisible jusqu'au jour où deux clients allaient soumettre leur réservation à 50 ms d'écart.",{"type":31,"tag":80,"props":6123,"children":6124},{},[6125],{"type":31,"tag":32,"props":6126,"children":6127},{},[6128,6133,6135,6141],{"type":31,"tag":36,"props":6129,"children":6130},{},[6131],{"type":40,"value":6132},"Ce que j'observe sur crmcoaching",{"type":40,"value":6134}," : je mesure régulièrement mon taux d'acceptation des suggestions Claude sur les PR du projet. Autour de 73% des suggestions sont acceptées telles quelles. Sur les PR que je retravaille, la majorité des retouches concernent le nommage ou le style. Jamais une race condition ou un problème de concurrence ne remonte spontanément. Le filtre humain ne voit plus ce genre de bug, exactement comme le décrit le ",{"type":31,"tag":64,"props":6136,"children":6138},{"href":6137},"/fr/intelligence-artificielle/ia-code-review-retour-experience",[6139],{"type":40,"value":6140},"retour d'expérience sur la code review IA",{"type":40,"value":6142}," que j'ai publié l'année dernière.",{"type":31,"tag":32,"props":6144,"children":6145},{},[6146,6148,6153,6155,6160,6162,6167],{"type":40,"value":6147},"C'est exactement ce que Bruce Schneier appelait ",{"type":31,"tag":99,"props":6149,"children":6150},{},[6151],{"type":40,"value":6152},"\"Security is a process, not a product\"",{"type":40,"value":6154}," dans son livre fondateur de 2000. La robustesse d'un ",{"type":31,"tag":148,"props":6156,"children":6158},{"className":6157},[],[6159],{"type":40,"value":6056},{"type":40,"value":6161}," n'est pas dans le code lui-même, elle est dans la discipline de review qui le précède. Si la discipline tombe, le code ne peut pas la remplacer. C'est la même logique qui anime ",{"type":31,"tag":64,"props":6163,"children":6164},{"href":115},[6165],{"type":40,"value":6166},"les principes de clean code et software craftsmanship",{"type":40,"value":6168}," que je rappelle systématiquement en mission.",{"type":31,"tag":48,"props":6170,"children":6171},{},[],{"type":31,"tag":52,"props":6173,"children":6175},{"id":6174},"anatomie-dune-race-condition-typique-générée-par-ia",[6176],{"type":40,"value":6177},"Anatomie d'une race condition typique générée par IA",{"type":31,"tag":32,"props":6179,"children":6180},{},[6181,6183,6188],{"type":40,"value":6182},"Reprenons le code que Claude m'avait produit pour ",{"type":31,"tag":148,"props":6184,"children":6186},{"className":6185},[],[6187],{"type":40,"value":6056},{"type":40,"value":6189},". Voici la version simplifiée qui illustre le pattern :",{"type":31,"tag":141,"props":6191,"children":6193},{"className":143,"code":6192,"language":145,"meta":8,"style":8},"// apps/api/src/application/slot-hold/hold-slot.use-case.ts\n@Injectable()\nexport class HoldSlotUseCase {\n  constructor(private readonly prisma: PrismaService) {}\n\n  async execute(slotId: string, clientId: string): Promise\u003Cvoid> {\n    const slot = await this.prisma.slot.findUniqueOrThrow({\n      where: { id: slotId },\n    });\n\n    if (slot.status !== 'AVAILABLE') {\n      throw new Error('Slot not available');\n    }\n\n    await this.prisma.slot.update({\n      where: { id: slotId },\n      data: { status: 'HELD', heldByClientId: clientId },\n    });\n  }\n}\n",[6194],{"type":31,"tag":148,"props":6195,"children":6196},{"__ignoreMap":8},[6197,6205,6220,6240,6281,6288,6360,6416,6447,6462,6469,6506,6539,6547,6554,6597,6628,6678,6693,6700],{"type":31,"tag":152,"props":6198,"children":6199},{"class":154,"line":155},[6200],{"type":31,"tag":152,"props":6201,"children":6202},{"style":159},[6203],{"type":40,"value":6204},"// apps/api/src/application/slot-hold/hold-slot.use-case.ts\n",{"type":31,"tag":152,"props":6206,"children":6207},{"class":154,"line":165},[6208,6212,6216],{"type":31,"tag":152,"props":6209,"children":6210},{"style":187},[6211],{"type":40,"value":190},{"type":31,"tag":152,"props":6213,"children":6214},{"style":193},[6215],{"type":40,"value":196},{"type":31,"tag":152,"props":6217,"children":6218},{"style":199},[6219],{"type":40,"value":202},{"type":31,"tag":152,"props":6221,"children":6222},{"class":154,"line":174},[6223,6227,6231,6236],{"type":31,"tag":152,"props":6224,"children":6225},{"style":209},[6226],{"type":40,"value":212},{"type":31,"tag":152,"props":6228,"children":6229},{"style":209},[6230],{"type":40,"value":217},{"type":31,"tag":152,"props":6232,"children":6233},{"style":220},[6234],{"type":40,"value":6235}," HoldSlotUseCase",{"type":31,"tag":152,"props":6237,"children":6238},{"style":226},[6239],{"type":40,"value":229},{"type":31,"tag":152,"props":6241,"children":6242},{"class":154,"line":183},[6243,6247,6251,6256,6260,6264,6268,6273,6277],{"type":31,"tag":152,"props":6244,"children":6245},{"style":209},[6246],{"type":40,"value":238},{"type":31,"tag":152,"props":6248,"children":6249},{"style":226},[6250],{"type":40,"value":410},{"type":31,"tag":152,"props":6252,"children":6253},{"style":209},[6254],{"type":40,"value":6255},"private",{"type":31,"tag":152,"props":6257,"children":6258},{"style":209},[6259],{"type":40,"value":257},{"type":31,"tag":152,"props":6261,"children":6262},{"style":260},[6263],{"type":40,"value":263},{"type":31,"tag":152,"props":6265,"children":6266},{"style":266},[6267],{"type":40,"value":269},{"type":31,"tag":152,"props":6269,"children":6270},{"style":220},[6271],{"type":40,"value":6272}," PrismaService",{"type":31,"tag":152,"props":6274,"children":6275},{"style":226},[6276],{"type":40,"value":448},{"type":31,"tag":152,"props":6278,"children":6279},{"style":226},[6280],{"type":40,"value":383},{"type":31,"tag":152,"props":6282,"children":6283},{"class":154,"line":205},[6284],{"type":31,"tag":152,"props":6285,"children":6286},{"emptyLinePlaceholder":13},[6287],{"type":40,"value":180},{"type":31,"tag":152,"props":6289,"children":6290},{"class":154,"line":232},[6291,6295,6299,6303,6307,6311,6315,6319,6323,6327,6331,6335,6339,6343,6347,6352,6356],{"type":31,"tag":152,"props":6292,"children":6293},{"style":209},[6294],{"type":40,"value":400},{"type":31,"tag":152,"props":6296,"children":6297},{"style":193},[6298],{"type":40,"value":405},{"type":31,"tag":152,"props":6300,"children":6301},{"style":226},[6302],{"type":40,"value":410},{"type":31,"tag":152,"props":6304,"children":6305},{"style":260},[6306],{"type":40,"value":2475},{"type":31,"tag":152,"props":6308,"children":6309},{"style":266},[6310],{"type":40,"value":269},{"type":31,"tag":152,"props":6312,"children":6313},{"style":422},[6314],{"type":40,"value":425},{"type":31,"tag":152,"props":6316,"children":6317},{"style":226},[6318],{"type":40,"value":430},{"type":31,"tag":152,"props":6320,"children":6321},{"style":260},[6322],{"type":40,"value":2140},{"type":31,"tag":152,"props":6324,"children":6325},{"style":266},[6326],{"type":40,"value":269},{"type":31,"tag":152,"props":6328,"children":6329},{"style":422},[6330],{"type":40,"value":425},{"type":31,"tag":152,"props":6332,"children":6333},{"style":226},[6334],{"type":40,"value":448},{"type":31,"tag":152,"props":6336,"children":6337},{"style":266},[6338],{"type":40,"value":269},{"type":31,"tag":152,"props":6340,"children":6341},{"style":220},[6342],{"type":40,"value":457},{"type":31,"tag":152,"props":6344,"children":6345},{"style":460},[6346],{"type":40,"value":463},{"type":31,"tag":152,"props":6348,"children":6349},{"style":422},[6350],{"type":40,"value":6351},"void",{"type":31,"tag":152,"props":6353,"children":6354},{"style":460},[6355],{"type":40,"value":473},{"type":31,"tag":152,"props":6357,"children":6358},{"style":226},[6359],{"type":40,"value":229},{"type":31,"tag":152,"props":6361,"children":6362},{"class":154,"line":246},[6363,6367,6371,6375,6379,6383,6387,6391,6395,6399,6403,6408,6412],{"type":31,"tag":152,"props":6364,"children":6365},{"style":209},[6366],{"type":40,"value":555},{"type":31,"tag":152,"props":6368,"children":6369},{"style":558},[6370],{"type":40,"value":2697},{"type":31,"tag":152,"props":6372,"children":6373},{"style":266},[6374],{"type":40,"value":566},{"type":31,"tag":152,"props":6376,"children":6377},{"style":209},[6378],{"type":40,"value":571},{"type":31,"tag":152,"props":6380,"children":6381},{"style":574},[6382],{"type":40,"value":577},{"type":31,"tag":152,"props":6384,"children":6385},{"style":580},[6386],{"type":40,"value":583},{"type":31,"tag":152,"props":6388,"children":6389},{"style":498},[6390],{"type":40,"value":588},{"type":31,"tag":152,"props":6392,"children":6393},{"style":580},[6394],{"type":40,"value":583},{"type":31,"tag":152,"props":6396,"children":6397},{"style":498},[6398],{"type":40,"value":2726},{"type":31,"tag":152,"props":6400,"children":6401},{"style":580},[6402],{"type":40,"value":583},{"type":31,"tag":152,"props":6404,"children":6405},{"style":193},[6406],{"type":40,"value":6407},"findUniqueOrThrow",{"type":31,"tag":152,"props":6409,"children":6410},{"style":498},[6411],{"type":40,"value":410},{"type":31,"tag":152,"props":6413,"children":6414},{"style":226},[6415],{"type":40,"value":919},{"type":31,"tag":152,"props":6417,"children":6418},{"class":154,"line":282},[6419,6423,6427,6431,6435,6439,6443],{"type":31,"tag":152,"props":6420,"children":6421},{"style":498},[6422],{"type":40,"value":928},{"type":31,"tag":152,"props":6424,"children":6425},{"style":580},[6426],{"type":40,"value":269},{"type":31,"tag":152,"props":6428,"children":6429},{"style":226},[6430],{"type":40,"value":629},{"type":31,"tag":152,"props":6432,"children":6433},{"style":498},[6434],{"type":40,"value":634},{"type":31,"tag":152,"props":6436,"children":6437},{"style":580},[6438],{"type":40,"value":269},{"type":31,"tag":152,"props":6440,"children":6441},{"style":498},[6442],{"type":40,"value":2767},{"type":31,"tag":152,"props":6444,"children":6445},{"style":226},[6446],{"type":40,"value":972},{"type":31,"tag":152,"props":6448,"children":6449},{"class":154,"line":312},[6450,6454,6458],{"type":31,"tag":152,"props":6451,"children":6452},{"style":226},[6453],{"type":40,"value":981},{"type":31,"tag":152,"props":6455,"children":6456},{"style":498},[6457],{"type":40,"value":448},{"type":31,"tag":152,"props":6459,"children":6460},{"style":226},[6461],{"type":40,"value":546},{"type":31,"tag":152,"props":6463,"children":6464},{"class":154,"line":342},[6465],{"type":31,"tag":152,"props":6466,"children":6467},{"emptyLinePlaceholder":13},[6468],{"type":40,"value":180},{"type":31,"tag":152,"props":6470,"children":6471},{"class":154,"line":372},[6472,6476,6481,6485,6489,6493,6498,6502],{"type":31,"tag":152,"props":6473,"children":6474},{"style":209},[6475],{"type":40,"value":495},{"type":31,"tag":152,"props":6477,"children":6478},{"style":498},[6479],{"type":40,"value":6480}," (slot",{"type":31,"tag":152,"props":6482,"children":6483},{"style":580},[6484],{"type":40,"value":583},{"type":31,"tag":152,"props":6486,"children":6487},{"style":498},[6488],{"type":40,"value":814},{"type":31,"tag":152,"props":6490,"children":6491},{"style":266},[6492],{"type":40,"value":758},{"type":31,"tag":152,"props":6494,"children":6495},{"style":534},[6496],{"type":40,"value":6497}," 'AVAILABLE'",{"type":31,"tag":152,"props":6499,"children":6500},{"style":498},[6501],{"type":40,"value":829},{"type":31,"tag":152,"props":6503,"children":6504},{"style":226},[6505],{"type":40,"value":919},{"type":31,"tag":152,"props":6507,"children":6508},{"class":154,"line":386},[6509,6514,6518,6522,6526,6531,6535],{"type":31,"tag":152,"props":6510,"children":6511},{"style":209},[6512],{"type":40,"value":6513},"      throw",{"type":31,"tag":152,"props":6515,"children":6516},{"style":519},[6517],{"type":40,"value":522},{"type":31,"tag":152,"props":6519,"children":6520},{"style":193},[6521],{"type":40,"value":5177},{"type":31,"tag":152,"props":6523,"children":6524},{"style":498},[6525],{"type":40,"value":410},{"type":31,"tag":152,"props":6527,"children":6528},{"style":534},[6529],{"type":40,"value":6530},"'Slot not available'",{"type":31,"tag":152,"props":6532,"children":6533},{"style":498},[6534],{"type":40,"value":448},{"type":31,"tag":152,"props":6536,"children":6537},{"style":226},[6538],{"type":40,"value":546},{"type":31,"tag":152,"props":6540,"children":6541},{"class":154,"line":394},[6542],{"type":31,"tag":152,"props":6543,"children":6544},{"style":226},[6545],{"type":40,"value":6546},"    }\n",{"type":31,"tag":152,"props":6548,"children":6549},{"class":154,"line":480},[6550],{"type":31,"tag":152,"props":6551,"children":6552},{"emptyLinePlaceholder":13},[6553],{"type":40,"value":180},{"type":31,"tag":152,"props":6555,"children":6556},{"class":154,"line":489},[6557,6561,6565,6569,6573,6577,6581,6585,6589,6593],{"type":31,"tag":152,"props":6558,"children":6559},{"style":209},[6560],{"type":40,"value":1363},{"type":31,"tag":152,"props":6562,"children":6563},{"style":574},[6564],{"type":40,"value":577},{"type":31,"tag":152,"props":6566,"children":6567},{"style":580},[6568],{"type":40,"value":583},{"type":31,"tag":152,"props":6570,"children":6571},{"style":498},[6572],{"type":40,"value":588},{"type":31,"tag":152,"props":6574,"children":6575},{"style":580},[6576],{"type":40,"value":583},{"type":31,"tag":152,"props":6578,"children":6579},{"style":498},[6580],{"type":40,"value":2726},{"type":31,"tag":152,"props":6582,"children":6583},{"style":580},[6584],{"type":40,"value":583},{"type":31,"tag":152,"props":6586,"children":6587},{"style":193},[6588],{"type":40,"value":1392},{"type":31,"tag":152,"props":6590,"children":6591},{"style":498},[6592],{"type":40,"value":410},{"type":31,"tag":152,"props":6594,"children":6595},{"style":226},[6596],{"type":40,"value":919},{"type":31,"tag":152,"props":6598,"children":6599},{"class":154,"line":549},[6600,6604,6608,6612,6616,6620,6624],{"type":31,"tag":152,"props":6601,"children":6602},{"style":498},[6603],{"type":40,"value":928},{"type":31,"tag":152,"props":6605,"children":6606},{"style":580},[6607],{"type":40,"value":269},{"type":31,"tag":152,"props":6609,"children":6610},{"style":226},[6611],{"type":40,"value":629},{"type":31,"tag":152,"props":6613,"children":6614},{"style":498},[6615],{"type":40,"value":634},{"type":31,"tag":152,"props":6617,"children":6618},{"style":580},[6619],{"type":40,"value":269},{"type":31,"tag":152,"props":6621,"children":6622},{"style":498},[6623],{"type":40,"value":2767},{"type":31,"tag":152,"props":6625,"children":6626},{"style":226},[6627],{"type":40,"value":972},{"type":31,"tag":152,"props":6629,"children":6630},{"class":154,"line":664},[6631,6635,6639,6643,6647,6651,6656,6660,6665,6669,6674],{"type":31,"tag":152,"props":6632,"children":6633},{"style":498},[6634],{"type":40,"value":1124},{"type":31,"tag":152,"props":6636,"children":6637},{"style":580},[6638],{"type":40,"value":269},{"type":31,"tag":152,"props":6640,"children":6641},{"style":226},[6642],{"type":40,"value":629},{"type":31,"tag":152,"props":6644,"children":6645},{"style":498},[6646],{"type":40,"value":1453},{"type":31,"tag":152,"props":6648,"children":6649},{"style":580},[6650],{"type":40,"value":269},{"type":31,"tag":152,"props":6652,"children":6653},{"style":534},[6654],{"type":40,"value":6655}," 'HELD'",{"type":31,"tag":152,"props":6657,"children":6658},{"style":226},[6659],{"type":40,"value":430},{"type":31,"tag":152,"props":6661,"children":6662},{"style":498},[6663],{"type":40,"value":6664}," heldByClientId",{"type":31,"tag":152,"props":6666,"children":6667},{"style":580},[6668],{"type":40,"value":269},{"type":31,"tag":152,"props":6670,"children":6671},{"style":498},[6672],{"type":40,"value":6673}," clientId ",{"type":31,"tag":152,"props":6675,"children":6676},{"style":226},[6677],{"type":40,"value":972},{"type":31,"tag":152,"props":6679,"children":6680},{"class":154,"line":734},[6681,6685,6689],{"type":31,"tag":152,"props":6682,"children":6683},{"style":226},[6684],{"type":40,"value":981},{"type":31,"tag":152,"props":6686,"children":6687},{"style":498},[6688],{"type":40,"value":448},{"type":31,"tag":152,"props":6690,"children":6691},{"style":226},[6692],{"type":40,"value":546},{"type":31,"tag":152,"props":6694,"children":6695},{"class":154,"line":796},[6696],{"type":31,"tag":152,"props":6697,"children":6698},{"style":226},[6699],{"type":40,"value":2224},{"type":31,"tag":152,"props":6701,"children":6702},{"class":154,"line":862},[6703],{"type":31,"tag":152,"props":6704,"children":6705},{"style":226},[6706],{"type":40,"value":2233},{"type":31,"tag":32,"props":6708,"children":6709},{},[6710,6712,6718,6720,6725,6727,6732],{"type":40,"value":6711},"Le bug est à deux endroits. D'abord, la lecture de ",{"type":31,"tag":148,"props":6713,"children":6715},{"className":6714},[],[6716],{"type":40,"value":6717},"slot.status",{"type":40,"value":6719}," n'est pas verrouillée : deux requêtes parallèles peuvent toutes les deux lire ",{"type":31,"tag":148,"props":6721,"children":6723},{"className":6722},[],[6724],{"type":40,"value":6111},{"type":40,"value":6726}," et valider la condition indépendamment. Ensuite, l'écriture utilise la valeur lue en mémoire au lieu de demander à Postgres de faire le calcul atomique avec une condition. Résultat : deux clients se retrouvent avec le même créneau marqué ",{"type":31,"tag":148,"props":6728,"children":6730},{"className":6729},[],[6731],{"type":40,"value":6119},{"type":40,"value":583},{"type":31,"tag":32,"props":6734,"children":6735},{},[6736,6738,6743,6745,6750],{"type":40,"value":6737},"Pourquoi Claude écrit ce code-là ? Parce que c'est le pattern dominant dans son training data. Sur GitHub, des dizaines de milliers d'exemples Prisma montrent exactement cette séquence ",{"type":31,"tag":148,"props":6739,"children":6741},{"className":6740},[],[6742],{"type":40,"value":606},{"type":40,"value":6744}," + ",{"type":31,"tag":148,"props":6746,"children":6748},{"className":6747},[],[6749],{"type":40,"value":1392},{"type":40,"value":6751},". Claude n'a pas conscience que dans un contexte de réservation, la concurrence est la norme et non l'exception. Il code comme un développeur junior bien intentionné qui n'a jamais vu de prod sous charge.",{"type":31,"tag":32,"props":6753,"children":6754},{},[6755,6757,6762],{"type":40,"value":6756},"C'est aussi ce que Martin Fowler a documenté dans ",{"type":31,"tag":99,"props":6758,"children":6759},{},[6760],{"type":40,"value":6761},"Refactoring",{"type":40,"value":6763}," (2018) : le code qui marche dans un test unitaire n'est pas le code qui marche en production. La différence est dans les conditions d'exécution, et l'IA n'a pas accès à ces conditions au moment où elle génère. C'est exactement le genre de risque qui transforme un repo récent en legacy à évaluer urgemment à 12 mois si la discipline de review ne se met pas en place rapidement.",{"type":31,"tag":48,"props":6765,"children":6766},{},[],{"type":31,"tag":5642,"props":6768,"children":6770},{"cta":5644,"href":5645,"title":6769,"type":5647},"Vous voulez développer le réflexe qui attrape ces bugs avant la prod ?",[6771],{"type":31,"tag":32,"props":6772,"children":6773},{},[6774],{"type":40,"value":6775},"Repérer une race condition dans une PR Claude, ça ne s'apprend pas en lisant un article : ça se travaille. En mentoring 1:1, je relis votre code et vos PR IA-générées avec vous, et je vous transmets la grille de lecture que j'applique sur crmcoaching. En quelques sessions, vous arrêtez de relire les accolades et vous commencez à voir ce que le modèle ne voit pas.",{"type":31,"tag":48,"props":6777,"children":6778},{},[],{"type":31,"tag":52,"props":6780,"children":6782},{"id":6781},"le-fix-craft-transaction-atomique-et-garde-explicite",[6783],{"type":40,"value":6784},"Le fix craft : transaction atomique et garde explicite",{"type":31,"tag":32,"props":6786,"children":6787},{},[6788],{"type":40,"value":6789},"Voici la version que j'ai réécrite avec Claude, en lui donnant le bon contexte cette fois :",{"type":31,"tag":141,"props":6791,"children":6793},{"className":143,"code":6792,"language":145,"meta":8,"style":8},"// apps/api/src/application/slot-hold/hold-slot.use-case.ts\n@Injectable()\nexport class HoldSlotUseCase {\n  constructor(private readonly prisma: PrismaService) {}\n\n  async execute(slotId: string, clientId: string): Promise\u003Cvoid> {\n    await this.prisma.$transaction(\n      async (tx) => {\n        const result = await tx.slot.updateMany({\n          where: { id: slotId, status: 'AVAILABLE' },\n          data: { status: 'HELD', heldByClientId: clientId },\n        });\n\n        if (result.count !== 1) {\n          throw new SlotAlreadyHeldError(slotId);\n        }\n      },\n      { isolationLevel: 'Serializable' },\n    );\n  }\n}\n",[6794],{"type":31,"tag":148,"props":6795,"children":6796},{"__ignoreMap":8},[6797,6804,6819,6838,6877,6884,6955,6987,7016,7066,7114,7162,7178,7185,7224,7249,7257,7264,7290,7301,7308],{"type":31,"tag":152,"props":6798,"children":6799},{"class":154,"line":155},[6800],{"type":31,"tag":152,"props":6801,"children":6802},{"style":159},[6803],{"type":40,"value":6204},{"type":31,"tag":152,"props":6805,"children":6806},{"class":154,"line":165},[6807,6811,6815],{"type":31,"tag":152,"props":6808,"children":6809},{"style":187},[6810],{"type":40,"value":190},{"type":31,"tag":152,"props":6812,"children":6813},{"style":193},[6814],{"type":40,"value":196},{"type":31,"tag":152,"props":6816,"children":6817},{"style":199},[6818],{"type":40,"value":202},{"type":31,"tag":152,"props":6820,"children":6821},{"class":154,"line":174},[6822,6826,6830,6834],{"type":31,"tag":152,"props":6823,"children":6824},{"style":209},[6825],{"type":40,"value":212},{"type":31,"tag":152,"props":6827,"children":6828},{"style":209},[6829],{"type":40,"value":217},{"type":31,"tag":152,"props":6831,"children":6832},{"style":220},[6833],{"type":40,"value":6235},{"type":31,"tag":152,"props":6835,"children":6836},{"style":226},[6837],{"type":40,"value":229},{"type":31,"tag":152,"props":6839,"children":6840},{"class":154,"line":183},[6841,6845,6849,6853,6857,6861,6865,6869,6873],{"type":31,"tag":152,"props":6842,"children":6843},{"style":209},[6844],{"type":40,"value":238},{"type":31,"tag":152,"props":6846,"children":6847},{"style":226},[6848],{"type":40,"value":410},{"type":31,"tag":152,"props":6850,"children":6851},{"style":209},[6852],{"type":40,"value":6255},{"type":31,"tag":152,"props":6854,"children":6855},{"style":209},[6856],{"type":40,"value":257},{"type":31,"tag":152,"props":6858,"children":6859},{"style":260},[6860],{"type":40,"value":263},{"type":31,"tag":152,"props":6862,"children":6863},{"style":266},[6864],{"type":40,"value":269},{"type":31,"tag":152,"props":6866,"children":6867},{"style":220},[6868],{"type":40,"value":6272},{"type":31,"tag":152,"props":6870,"children":6871},{"style":226},[6872],{"type":40,"value":448},{"type":31,"tag":152,"props":6874,"children":6875},{"style":226},[6876],{"type":40,"value":383},{"type":31,"tag":152,"props":6878,"children":6879},{"class":154,"line":205},[6880],{"type":31,"tag":152,"props":6881,"children":6882},{"emptyLinePlaceholder":13},[6883],{"type":40,"value":180},{"type":31,"tag":152,"props":6885,"children":6886},{"class":154,"line":232},[6887,6891,6895,6899,6903,6907,6911,6915,6919,6923,6927,6931,6935,6939,6943,6947,6951],{"type":31,"tag":152,"props":6888,"children":6889},{"style":209},[6890],{"type":40,"value":400},{"type":31,"tag":152,"props":6892,"children":6893},{"style":193},[6894],{"type":40,"value":405},{"type":31,"tag":152,"props":6896,"children":6897},{"style":226},[6898],{"type":40,"value":410},{"type":31,"tag":152,"props":6900,"children":6901},{"style":260},[6902],{"type":40,"value":2475},{"type":31,"tag":152,"props":6904,"children":6905},{"style":266},[6906],{"type":40,"value":269},{"type":31,"tag":152,"props":6908,"children":6909},{"style":422},[6910],{"type":40,"value":425},{"type":31,"tag":152,"props":6912,"children":6913},{"style":226},[6914],{"type":40,"value":430},{"type":31,"tag":152,"props":6916,"children":6917},{"style":260},[6918],{"type":40,"value":2140},{"type":31,"tag":152,"props":6920,"children":6921},{"style":266},[6922],{"type":40,"value":269},{"type":31,"tag":152,"props":6924,"children":6925},{"style":422},[6926],{"type":40,"value":425},{"type":31,"tag":152,"props":6928,"children":6929},{"style":226},[6930],{"type":40,"value":448},{"type":31,"tag":152,"props":6932,"children":6933},{"style":266},[6934],{"type":40,"value":269},{"type":31,"tag":152,"props":6936,"children":6937},{"style":220},[6938],{"type":40,"value":457},{"type":31,"tag":152,"props":6940,"children":6941},{"style":460},[6942],{"type":40,"value":463},{"type":31,"tag":152,"props":6944,"children":6945},{"style":422},[6946],{"type":40,"value":6351},{"type":31,"tag":152,"props":6948,"children":6949},{"style":460},[6950],{"type":40,"value":473},{"type":31,"tag":152,"props":6952,"children":6953},{"style":226},[6954],{"type":40,"value":229},{"type":31,"tag":152,"props":6956,"children":6957},{"class":154,"line":246},[6958,6962,6966,6970,6974,6978,6983],{"type":31,"tag":152,"props":6959,"children":6960},{"style":209},[6961],{"type":40,"value":1363},{"type":31,"tag":152,"props":6963,"children":6964},{"style":574},[6965],{"type":40,"value":577},{"type":31,"tag":152,"props":6967,"children":6968},{"style":580},[6969],{"type":40,"value":583},{"type":31,"tag":152,"props":6971,"children":6972},{"style":498},[6973],{"type":40,"value":588},{"type":31,"tag":152,"props":6975,"children":6976},{"style":580},[6977],{"type":40,"value":583},{"type":31,"tag":152,"props":6979,"children":6980},{"style":193},[6981],{"type":40,"value":6982},"$transaction",{"type":31,"tag":152,"props":6984,"children":6985},{"style":498},[6986],{"type":40,"value":243},{"type":31,"tag":152,"props":6988,"children":6989},{"class":154,"line":282},[6990,6995,6999,7004,7008,7012],{"type":31,"tag":152,"props":6991,"children":6992},{"style":209},[6993],{"type":40,"value":6994},"      async",{"type":31,"tag":152,"props":6996,"children":6997},{"style":226},[6998],{"type":40,"value":501},{"type":31,"tag":152,"props":7000,"children":7001},{"style":260},[7002],{"type":40,"value":7003},"tx",{"type":31,"tag":152,"props":7005,"children":7006},{"style":226},[7007],{"type":40,"value":448},{"type":31,"tag":152,"props":7009,"children":7010},{"style":266},[7011],{"type":40,"value":3513},{"type":31,"tag":152,"props":7013,"children":7014},{"style":226},[7015],{"type":40,"value":229},{"type":31,"tag":152,"props":7017,"children":7018},{"class":154,"line":312},[7019,7024,7028,7032,7036,7041,7045,7049,7053,7058,7062],{"type":31,"tag":152,"props":7020,"children":7021},{"style":209},[7022],{"type":40,"value":7023},"        const",{"type":31,"tag":152,"props":7025,"children":7026},{"style":558},[7027],{"type":40,"value":4278},{"type":31,"tag":152,"props":7029,"children":7030},{"style":266},[7031],{"type":40,"value":566},{"type":31,"tag":152,"props":7033,"children":7034},{"style":209},[7035],{"type":40,"value":571},{"type":31,"tag":152,"props":7037,"children":7038},{"style":498},[7039],{"type":40,"value":7040}," tx",{"type":31,"tag":152,"props":7042,"children":7043},{"style":580},[7044],{"type":40,"value":583},{"type":31,"tag":152,"props":7046,"children":7047},{"style":498},[7048],{"type":40,"value":2726},{"type":31,"tag":152,"props":7050,"children":7051},{"style":580},[7052],{"type":40,"value":583},{"type":31,"tag":152,"props":7054,"children":7055},{"style":193},[7056],{"type":40,"value":7057},"updateMany",{"type":31,"tag":152,"props":7059,"children":7060},{"style":498},[7061],{"type":40,"value":410},{"type":31,"tag":152,"props":7063,"children":7064},{"style":226},[7065],{"type":40,"value":919},{"type":31,"tag":152,"props":7067,"children":7068},{"class":154,"line":342},[7069,7074,7078,7082,7086,7090,7094,7098,7102,7106,7110],{"type":31,"tag":152,"props":7070,"children":7071},{"style":498},[7072],{"type":40,"value":7073},"          where",{"type":31,"tag":152,"props":7075,"children":7076},{"style":580},[7077],{"type":40,"value":269},{"type":31,"tag":152,"props":7079,"children":7080},{"style":226},[7081],{"type":40,"value":629},{"type":31,"tag":152,"props":7083,"children":7084},{"style":498},[7085],{"type":40,"value":634},{"type":31,"tag":152,"props":7087,"children":7088},{"style":580},[7089],{"type":40,"value":269},{"type":31,"tag":152,"props":7091,"children":7092},{"style":498},[7093],{"type":40,"value":2606},{"type":31,"tag":152,"props":7095,"children":7096},{"style":226},[7097],{"type":40,"value":430},{"type":31,"tag":152,"props":7099,"children":7100},{"style":498},[7101],{"type":40,"value":1453},{"type":31,"tag":152,"props":7103,"children":7104},{"style":580},[7105],{"type":40,"value":269},{"type":31,"tag":152,"props":7107,"children":7108},{"style":534},[7109],{"type":40,"value":6497},{"type":31,"tag":152,"props":7111,"children":7112},{"style":226},[7113],{"type":40,"value":2670},{"type":31,"tag":152,"props":7115,"children":7116},{"class":154,"line":372},[7117,7122,7126,7130,7134,7138,7142,7146,7150,7154,7158],{"type":31,"tag":152,"props":7118,"children":7119},{"style":498},[7120],{"type":40,"value":7121},"          data",{"type":31,"tag":152,"props":7123,"children":7124},{"style":580},[7125],{"type":40,"value":269},{"type":31,"tag":152,"props":7127,"children":7128},{"style":226},[7129],{"type":40,"value":629},{"type":31,"tag":152,"props":7131,"children":7132},{"style":498},[7133],{"type":40,"value":1453},{"type":31,"tag":152,"props":7135,"children":7136},{"style":580},[7137],{"type":40,"value":269},{"type":31,"tag":152,"props":7139,"children":7140},{"style":534},[7141],{"type":40,"value":6655},{"type":31,"tag":152,"props":7143,"children":7144},{"style":226},[7145],{"type":40,"value":430},{"type":31,"tag":152,"props":7147,"children":7148},{"style":498},[7149],{"type":40,"value":6664},{"type":31,"tag":152,"props":7151,"children":7152},{"style":580},[7153],{"type":40,"value":269},{"type":31,"tag":152,"props":7155,"children":7156},{"style":498},[7157],{"type":40,"value":6673},{"type":31,"tag":152,"props":7159,"children":7160},{"style":226},[7161],{"type":40,"value":972},{"type":31,"tag":152,"props":7163,"children":7164},{"class":154,"line":386},[7165,7170,7174],{"type":31,"tag":152,"props":7166,"children":7167},{"style":226},[7168],{"type":40,"value":7169},"        }",{"type":31,"tag":152,"props":7171,"children":7172},{"style":498},[7173],{"type":40,"value":448},{"type":31,"tag":152,"props":7175,"children":7176},{"style":226},[7177],{"type":40,"value":546},{"type":31,"tag":152,"props":7179,"children":7180},{"class":154,"line":394},[7181],{"type":31,"tag":152,"props":7182,"children":7183},{"emptyLinePlaceholder":13},[7184],{"type":40,"value":180},{"type":31,"tag":152,"props":7186,"children":7187},{"class":154,"line":480},[7188,7193,7198,7202,7207,7211,7216,7220],{"type":31,"tag":152,"props":7189,"children":7190},{"style":209},[7191],{"type":40,"value":7192},"        if",{"type":31,"tag":152,"props":7194,"children":7195},{"style":498},[7196],{"type":40,"value":7197}," (result",{"type":31,"tag":152,"props":7199,"children":7200},{"style":580},[7201],{"type":40,"value":583},{"type":31,"tag":152,"props":7203,"children":7204},{"style":498},[7205],{"type":40,"value":7206},"count ",{"type":31,"tag":152,"props":7208,"children":7209},{"style":266},[7210],{"type":40,"value":758},{"type":31,"tag":152,"props":7212,"children":7213},{"style":1725},[7214],{"type":40,"value":7215}," 1",{"type":31,"tag":152,"props":7217,"children":7218},{"style":498},[7219],{"type":40,"value":829},{"type":31,"tag":152,"props":7221,"children":7222},{"style":226},[7223],{"type":40,"value":919},{"type":31,"tag":152,"props":7225,"children":7226},{"class":154,"line":489},[7227,7232,7236,7241,7245],{"type":31,"tag":152,"props":7228,"children":7229},{"style":209},[7230],{"type":40,"value":7231},"          throw",{"type":31,"tag":152,"props":7233,"children":7234},{"style":519},[7235],{"type":40,"value":522},{"type":31,"tag":152,"props":7237,"children":7238},{"style":193},[7239],{"type":40,"value":7240}," SlotAlreadyHeldError",{"type":31,"tag":152,"props":7242,"children":7243},{"style":498},[7244],{"type":40,"value":3266},{"type":31,"tag":152,"props":7246,"children":7247},{"style":226},[7248],{"type":40,"value":546},{"type":31,"tag":152,"props":7250,"children":7251},{"class":154,"line":549},[7252],{"type":31,"tag":152,"props":7253,"children":7254},{"style":226},[7255],{"type":40,"value":7256},"        }\n",{"type":31,"tag":152,"props":7258,"children":7259},{"class":154,"line":664},[7260],{"type":31,"tag":152,"props":7261,"children":7262},{"style":226},[7263],{"type":40,"value":1338},{"type":31,"tag":152,"props":7265,"children":7266},{"class":154,"line":734},[7267,7272,7277,7281,7286],{"type":31,"tag":152,"props":7268,"children":7269},{"style":226},[7270],{"type":40,"value":7271},"      {",{"type":31,"tag":152,"props":7273,"children":7274},{"style":498},[7275],{"type":40,"value":7276}," isolationLevel",{"type":31,"tag":152,"props":7278,"children":7279},{"style":580},[7280],{"type":40,"value":269},{"type":31,"tag":152,"props":7282,"children":7283},{"style":534},[7284],{"type":40,"value":7285}," 'Serializable'",{"type":31,"tag":152,"props":7287,"children":7288},{"style":226},[7289],{"type":40,"value":2670},{"type":31,"tag":152,"props":7291,"children":7292},{"class":154,"line":796},[7293,7297],{"type":31,"tag":152,"props":7294,"children":7295},{"style":498},[7296],{"type":40,"value":3887},{"type":31,"tag":152,"props":7298,"children":7299},{"style":226},[7300],{"type":40,"value":546},{"type":31,"tag":152,"props":7302,"children":7303},{"class":154,"line":862},[7304],{"type":31,"tag":152,"props":7305,"children":7306},{"style":226},[7307],{"type":40,"value":2224},{"type":31,"tag":152,"props":7309,"children":7310},{"class":154,"line":922},[7311],{"type":31,"tag":152,"props":7312,"children":7313},{"style":226},[7314],{"type":40,"value":2233},{"type":31,"tag":32,"props":7316,"children":7317},{},[7318],{"type":40,"value":7319},"avec l'exception typée dans le domaine :",{"type":31,"tag":141,"props":7321,"children":7323},{"className":143,"code":7322,"language":145,"meta":8,"style":8},"// apps/api/src/domain/slot-hold/slot-already-held.error.ts\nexport class SlotAlreadyHeldError extends Error {\n  constructor(public readonly slotId: string) {\n    super(`Slot ${slotId} is no longer available`);\n    this.name = 'SlotAlreadyHeldError';\n  }\n}\n",[7324],{"type":31,"tag":148,"props":7325,"children":7326},{"__ignoreMap":8},[7327,7335,7363,7403,7445,7475,7482],{"type":31,"tag":152,"props":7328,"children":7329},{"class":154,"line":155},[7330],{"type":31,"tag":152,"props":7331,"children":7332},{"style":159},[7333],{"type":40,"value":7334},"// apps/api/src/domain/slot-hold/slot-already-held.error.ts\n",{"type":31,"tag":152,"props":7336,"children":7337},{"class":154,"line":165},[7338,7342,7346,7350,7355,7359],{"type":31,"tag":152,"props":7339,"children":7340},{"style":209},[7341],{"type":40,"value":212},{"type":31,"tag":152,"props":7343,"children":7344},{"style":209},[7345],{"type":40,"value":217},{"type":31,"tag":152,"props":7347,"children":7348},{"style":220},[7349],{"type":40,"value":7240},{"type":31,"tag":152,"props":7351,"children":7352},{"style":209},[7353],{"type":40,"value":7354}," extends",{"type":31,"tag":152,"props":7356,"children":7357},{"style":220},[7358],{"type":40,"value":5177},{"type":31,"tag":152,"props":7360,"children":7361},{"style":226},[7362],{"type":40,"value":229},{"type":31,"tag":152,"props":7364,"children":7365},{"class":154,"line":174},[7366,7370,7374,7379,7383,7387,7391,7395,7399],{"type":31,"tag":152,"props":7367,"children":7368},{"style":209},[7369],{"type":40,"value":238},{"type":31,"tag":152,"props":7371,"children":7372},{"style":226},[7373],{"type":40,"value":410},{"type":31,"tag":152,"props":7375,"children":7376},{"style":209},[7377],{"type":40,"value":7378},"public",{"type":31,"tag":152,"props":7380,"children":7381},{"style":209},[7382],{"type":40,"value":257},{"type":31,"tag":152,"props":7384,"children":7385},{"style":260},[7386],{"type":40,"value":2606},{"type":31,"tag":152,"props":7388,"children":7389},{"style":266},[7390],{"type":40,"value":269},{"type":31,"tag":152,"props":7392,"children":7393},{"style":422},[7394],{"type":40,"value":425},{"type":31,"tag":152,"props":7396,"children":7397},{"style":226},[7398],{"type":40,"value":448},{"type":31,"tag":152,"props":7400,"children":7401},{"style":226},[7402],{"type":40,"value":229},{"type":31,"tag":152,"props":7404,"children":7405},{"class":154,"line":183},[7406,7411,7415,7420,7424,7428,7432,7437,7441],{"type":31,"tag":152,"props":7407,"children":7408},{"style":422},[7409],{"type":40,"value":7410},"    super",{"type":31,"tag":152,"props":7412,"children":7413},{"style":498},[7414],{"type":40,"value":410},{"type":31,"tag":152,"props":7416,"children":7417},{"style":534},[7418],{"type":40,"value":7419},"`Slot ",{"type":31,"tag":152,"props":7421,"children":7422},{"style":707},[7423],{"type":40,"value":710},{"type":31,"tag":152,"props":7425,"children":7426},{"style":498},[7427],{"type":40,"value":2475},{"type":31,"tag":152,"props":7429,"children":7430},{"style":707},[7431],{"type":40,"value":648},{"type":31,"tag":152,"props":7433,"children":7434},{"style":534},[7435],{"type":40,"value":7436}," is no longer available`",{"type":31,"tag":152,"props":7438,"children":7439},{"style":498},[7440],{"type":40,"value":448},{"type":31,"tag":152,"props":7442,"children":7443},{"style":226},[7444],{"type":40,"value":546},{"type":31,"tag":152,"props":7446,"children":7447},{"class":154,"line":205},[7448,7452,7456,7461,7466,7471],{"type":31,"tag":152,"props":7449,"children":7450},{"style":574},[7451],{"type":40,"value":2100},{"type":31,"tag":152,"props":7453,"children":7454},{"style":580},[7455],{"type":40,"value":583},{"type":31,"tag":152,"props":7457,"children":7458},{"style":498},[7459],{"type":40,"value":7460},"name ",{"type":31,"tag":152,"props":7462,"children":7463},{"style":266},[7464],{"type":40,"value":7465},"=",{"type":31,"tag":152,"props":7467,"children":7468},{"style":534},[7469],{"type":40,"value":7470}," 'SlotAlreadyHeldError'",{"type":31,"tag":152,"props":7472,"children":7473},{"style":226},[7474],{"type":40,"value":546},{"type":31,"tag":152,"props":7476,"children":7477},{"class":154,"line":232},[7478],{"type":31,"tag":152,"props":7479,"children":7480},{"style":226},[7481],{"type":40,"value":2224},{"type":31,"tag":152,"props":7483,"children":7484},{"class":154,"line":246},[7485],{"type":31,"tag":152,"props":7486,"children":7487},{"style":226},[7488],{"type":40,"value":2233},{"type":31,"tag":32,"props":7490,"children":7491},{},[7492,7494,7500,7502,7508,7510,7515,7517,7523,7525,7531],{"type":40,"value":7493},"Trois changements comptent. D'abord le recours à ",{"type":31,"tag":148,"props":7495,"children":7497},{"className":7496},[],[7498],{"type":40,"value":7499},"prisma.$transaction",{"type":40,"value":7501}," avec ",{"type":31,"tag":148,"props":7503,"children":7505},{"className":7504},[],[7506],{"type":40,"value":7507},"isolationLevel: 'Serializable'",{"type":40,"value":7509}," qui rend l'opération atomique : soit tout passe, soit rien ne passe, et Postgres empêche deux transactions concurrentes de lire le même état incohérent. Ensuite l'",{"type":31,"tag":148,"props":7511,"children":7513},{"className":7512},[],[7514],{"type":40,"value":7057},{"type":40,"value":7516}," conditionnel (avec ",{"type":31,"tag":148,"props":7518,"children":7520},{"className":7519},[],[7521],{"type":40,"value":7522},"where: { status: 'AVAILABLE' }",{"type":40,"value":7524},") qui fait vérifier la condition par Postgres au moment de l'écriture, pas par la mémoire Node.js au moment de la lecture. Enfin l'exception typée ",{"type":31,"tag":148,"props":7526,"children":7528},{"className":7527},[],[7529],{"type":40,"value":7530},"SlotAlreadyHeldError",{"type":40,"value":7532}," qui porte le contexte nécessaire aux couches supérieures.",{"type":31,"tag":32,"props":7534,"children":7535},{},[7536,7538,7543,7545,7551],{"type":40,"value":7537},"Quand je prompte Claude pour ce fix, je ne dis pas \"ajoute une transaction\". Je dis : ",{"type":31,"tag":99,"props":7539,"children":7540},{},[7541],{"type":40,"value":7542},"\"Ce use case sera appelé en concurrence. Deux clients peuvent réserver le même créneau à 10 ms d'écart. Réécris-le pour qu'il reste correct sous cette contrainte, en utilisant les primitives Prisma adaptées.\"",{"type":40,"value":7544}," Le résultat est radicalement meilleur. Claude n'invente pas, il applique. Le craft consiste à lui donner le bon contexte pour qu'il applique le bon pattern, comme le formalise une vraie ",{"type":31,"tag":64,"props":7546,"children":7548},{"href":7547},"/fr/dette-technique/definition-of-done-qualite",[7549],{"type":40,"value":7550},"Definition of Done sur la qualité",{"type":40,"value":583},{"type":31,"tag":48,"props":7553,"children":7554},{},[],{"type":31,"tag":52,"props":7556,"children":7558},{"id":7557},"les-4-garde-fous-à-appliquer-dès-lundi",[7559],{"type":40,"value":7560},"Les 4 garde-fous à appliquer dès lundi",{"type":31,"tag":32,"props":7562,"children":7563},{},[7564],{"type":40,"value":7565},"Voici les 4 points que je passe systématiquement en review sur chaque PR Claude qui touche à de l'état partagé (DB, cache, fichier, queue).",{"type":31,"tag":32,"props":7567,"children":7568},{},[7569,7574,7576,7581],{"type":31,"tag":36,"props":7570,"children":7571},{},[7572],{"type":40,"value":7573},"Garde-fou 1 : la concurrence est-elle nommée explicitement ?",{"type":40,"value":7575}," Pour toute fonction qui lit puis écrit, je me pose la question : ",{"type":31,"tag":99,"props":7577,"children":7578},{},[7579],{"type":40,"value":7580},"\"Ce use case peut-il être appelé par 2 requêtes simultanées ? Si oui, que se passe-t-il ?\"",{"type":40,"value":7582}," Si la réponse est \"je ne sais pas\", la PR retourne en draft.",{"type":31,"tag":32,"props":7584,"children":7585},{},[7586,7591,7593,7598],{"type":31,"tag":36,"props":7587,"children":7588},{},[7589],{"type":40,"value":7590},"Garde-fou 2 : les écritures qui dépendent de lectures passent-elles par une transaction ?",{"type":40,"value":7592}," Pas de read-modify-write hors ",{"type":31,"tag":148,"props":7594,"children":7596},{"className":7595},[],[7597],{"type":40,"value":7499},{"type":40,"value":7599},". C'est la règle. Si Claude n'a pas utilisé une transaction avec un niveau d'isolation explicite, c'est un signal qu'il a écrit le pattern naïf.",{"type":31,"tag":32,"props":7601,"children":7602},{},[7603,7608,7610,7616,7618,7624,7626,7630],{"type":31,"tag":36,"props":7604,"children":7605},{},[7606],{"type":40,"value":7607},"Garde-fou 3 : les exceptions sont-elles typées et porteuses de contexte ?",{"type":40,"value":7609}," ",{"type":31,"tag":148,"props":7611,"children":7613},{"className":7612},[],[7614],{"type":40,"value":7615},"throw new Error('Slot not available')",{"type":40,"value":7617}," est insuffisant. ",{"type":31,"tag":148,"props":7619,"children":7621},{"className":7620},[],[7622],{"type":40,"value":7623},"throw new SlotAlreadyHeldError(slotId)",{"type":40,"value":7625}," permet à la couche supérieure de prendre des décisions différenciées, et à l'observabilité de remonter les bons signaux. Ce détail est ce qui sépare le code junior du code senior, et c'est aussi ce qui permet de construire les ",{"type":31,"tag":64,"props":7627,"children":7628},{"href":5347},[7629],{"type":40,"value":5350},{"type":40,"value":7631}," en aval.",{"type":31,"tag":32,"props":7633,"children":7634},{},[7635,7640,7642,7648,7650,7655,7657,7662],{"type":31,"tag":36,"props":7636,"children":7637},{},[7638],{"type":40,"value":7639},"Garde-fou 4 : un test de concurrence existe-t-il ?",{"type":40,"value":7641}," Pour toute méthode critique, j'exige un test Vitest qui soumet le use case en parallèle via ",{"type":31,"tag":148,"props":7643,"children":7645},{"className":7644},[],[7646],{"type":40,"value":7647},"Promise.all",{"type":40,"value":7649}," sur le même créneau, et qui vérifie que l'état final est cohérent (un seul ",{"type":31,"tag":148,"props":7651,"children":7653},{"className":7652},[],[7654],{"type":40,"value":6119},{"type":40,"value":7656},", une seule erreur ",{"type":31,"tag":148,"props":7658,"children":7660},{"className":7659},[],[7661],{"type":40,"value":7530},{"type":40,"value":7663},"). Si ce test n'existe pas, Claude ne l'a pas écrit. C'est à la review de l'exiger.",{"type":31,"tag":141,"props":7665,"children":7667},{"className":143,"code":7666,"language":145,"meta":8,"style":8},"// Exemple de test de concurrence Vitest\nit('ne doit accorder le créneau qu'à un seul client en concurrence', async () => {\n  const slotId = 'slot-test-id';\n  const results = await Promise.allSettled([\n    holdSlotUseCase.execute(slotId, 'client-A'),\n    holdSlotUseCase.execute(slotId, 'client-B'),\n  ]);\n\n  const fulfilled = results.filter((r) => r.status === 'fulfilled');\n  const rejected = results.filter((r) => r.status === 'rejected');\n\n  expect(fulfilled).toHaveLength(1);\n  expect(rejected).toHaveLength(1);\n  expect((rejected[0] as PromiseRejectedResult).reason).toBeInstanceOf(SlotAlreadyHeldError);\n});\n",[7668],{"type":31,"tag":148,"props":7669,"children":7670},{"__ignoreMap":8},[7671,7679,7711,7732,7766,7804,7840,7848,7855,7928,7997,8004,8039,8071,8129],{"type":31,"tag":152,"props":7672,"children":7673},{"class":154,"line":155},[7674],{"type":31,"tag":152,"props":7675,"children":7676},{"style":159},[7677],{"type":40,"value":7678},"// Exemple de test de concurrence Vitest\n",{"type":31,"tag":152,"props":7680,"children":7681},{"class":154,"line":165},[7682,7687,7691,7696,7701,7706],{"type":31,"tag":152,"props":7683,"children":7684},{"style":193},[7685],{"type":40,"value":7686},"it",{"type":31,"tag":152,"props":7688,"children":7689},{"style":498},[7690],{"type":40,"value":410},{"type":31,"tag":152,"props":7692,"children":7693},{"style":534},[7694],{"type":40,"value":7695},"'ne doit accorder le créneau qu'",{"type":31,"tag":152,"props":7697,"children":7698},{"style":498},[7699],{"type":40,"value":7700},"à un seul client en concurrence",{"type":31,"tag":152,"props":7702,"children":7703},{"style":534},[7704],{"type":40,"value":7705},"', async () => ",{"type":31,"tag":152,"props":7707,"children":7709},{"style":7708},"--shiki-default:#A6D189;--shiki-default-font-style:inherit;--shiki-dark:#FDAEB7;--shiki-dark-font-style:italic",[7710],{"type":40,"value":919},{"type":31,"tag":152,"props":7712,"children":7713},{"class":154,"line":174},[7714,7719,7723,7728],{"type":31,"tag":152,"props":7715,"children":7716},{"style":498},[7717],{"type":40,"value":7718},"  const slotId ",{"type":31,"tag":152,"props":7720,"children":7721},{"style":266},[7722],{"type":40,"value":7465},{"type":31,"tag":152,"props":7724,"children":7725},{"style":534},[7726],{"type":40,"value":7727}," 'slot-test-id'",{"type":31,"tag":152,"props":7729,"children":7730},{"style":498},[7731],{"type":40,"value":546},{"type":31,"tag":152,"props":7733,"children":7734},{"class":154,"line":183},[7735,7740,7744,7748,7752,7756,7761],{"type":31,"tag":152,"props":7736,"children":7737},{"style":498},[7738],{"type":40,"value":7739},"  const results ",{"type":31,"tag":152,"props":7741,"children":7742},{"style":266},[7743],{"type":40,"value":7465},{"type":31,"tag":152,"props":7745,"children":7746},{"style":209},[7747],{"type":40,"value":571},{"type":31,"tag":152,"props":7749,"children":7750},{"style":4628},[7751],{"type":40,"value":457},{"type":31,"tag":152,"props":7753,"children":7754},{"style":580},[7755],{"type":40,"value":583},{"type":31,"tag":152,"props":7757,"children":7758},{"style":193},[7759],{"type":40,"value":7760},"allSettled",{"type":31,"tag":152,"props":7762,"children":7763},{"style":498},[7764],{"type":40,"value":7765},"([\n",{"type":31,"tag":152,"props":7767,"children":7768},{"class":154,"line":205},[7769,7774,7778,7782,7787,7791,7796,7800],{"type":31,"tag":152,"props":7770,"children":7771},{"style":498},[7772],{"type":40,"value":7773},"    holdSlotUseCase",{"type":31,"tag":152,"props":7775,"children":7776},{"style":580},[7777],{"type":40,"value":583},{"type":31,"tag":152,"props":7779,"children":7780},{"style":193},[7781],{"type":40,"value":3720},{"type":31,"tag":152,"props":7783,"children":7784},{"style":498},[7785],{"type":40,"value":7786},"(slotId",{"type":31,"tag":152,"props":7788,"children":7789},{"style":226},[7790],{"type":40,"value":430},{"type":31,"tag":152,"props":7792,"children":7793},{"style":534},[7794],{"type":40,"value":7795}," 'client-A'",{"type":31,"tag":152,"props":7797,"children":7798},{"style":498},[7799],{"type":40,"value":448},{"type":31,"tag":152,"props":7801,"children":7802},{"style":226},[7803],{"type":40,"value":279},{"type":31,"tag":152,"props":7805,"children":7806},{"class":154,"line":232},[7807,7811,7815,7819,7823,7827,7832,7836],{"type":31,"tag":152,"props":7808,"children":7809},{"style":498},[7810],{"type":40,"value":7773},{"type":31,"tag":152,"props":7812,"children":7813},{"style":580},[7814],{"type":40,"value":583},{"type":31,"tag":152,"props":7816,"children":7817},{"style":193},[7818],{"type":40,"value":3720},{"type":31,"tag":152,"props":7820,"children":7821},{"style":498},[7822],{"type":40,"value":7786},{"type":31,"tag":152,"props":7824,"children":7825},{"style":226},[7826],{"type":40,"value":430},{"type":31,"tag":152,"props":7828,"children":7829},{"style":534},[7830],{"type":40,"value":7831}," 'client-B'",{"type":31,"tag":152,"props":7833,"children":7834},{"style":498},[7835],{"type":40,"value":448},{"type":31,"tag":152,"props":7837,"children":7838},{"style":226},[7839],{"type":40,"value":279},{"type":31,"tag":152,"props":7841,"children":7842},{"class":154,"line":246},[7843],{"type":31,"tag":152,"props":7844,"children":7845},{"style":498},[7846],{"type":40,"value":7847},"  ]);\n",{"type":31,"tag":152,"props":7849,"children":7850},{"class":154,"line":282},[7851],{"type":31,"tag":152,"props":7852,"children":7853},{"emptyLinePlaceholder":13},[7854],{"type":40,"value":180},{"type":31,"tag":152,"props":7856,"children":7857},{"class":154,"line":312},[7858,7863,7867,7872,7876,7881,7885,7889,7894,7898,7902,7907,7911,7915,7919,7924],{"type":31,"tag":152,"props":7859,"children":7860},{"style":498},[7861],{"type":40,"value":7862},"  const fulfilled ",{"type":31,"tag":152,"props":7864,"children":7865},{"style":266},[7866],{"type":40,"value":7465},{"type":31,"tag":152,"props":7868,"children":7869},{"style":498},[7870],{"type":40,"value":7871}," results",{"type":31,"tag":152,"props":7873,"children":7874},{"style":580},[7875],{"type":40,"value":583},{"type":31,"tag":152,"props":7877,"children":7878},{"style":193},[7879],{"type":40,"value":7880},"filter",{"type":31,"tag":152,"props":7882,"children":7883},{"style":498},[7884],{"type":40,"value":410},{"type":31,"tag":152,"props":7886,"children":7887},{"style":226},[7888],{"type":40,"value":410},{"type":31,"tag":152,"props":7890,"children":7891},{"style":260},[7892],{"type":40,"value":7893},"r",{"type":31,"tag":152,"props":7895,"children":7896},{"style":226},[7897],{"type":40,"value":448},{"type":31,"tag":152,"props":7899,"children":7900},{"style":266},[7901],{"type":40,"value":3513},{"type":31,"tag":152,"props":7903,"children":7904},{"style":498},[7905],{"type":40,"value":7906}," r",{"type":31,"tag":152,"props":7908,"children":7909},{"style":580},[7910],{"type":40,"value":583},{"type":31,"tag":152,"props":7912,"children":7913},{"style":498},[7914],{"type":40,"value":814},{"type":31,"tag":152,"props":7916,"children":7917},{"style":266},[7918],{"type":40,"value":819},{"type":31,"tag":152,"props":7920,"children":7921},{"style":534},[7922],{"type":40,"value":7923}," 'fulfilled'",{"type":31,"tag":152,"props":7925,"children":7926},{"style":498},[7927],{"type":40,"value":5271},{"type":31,"tag":152,"props":7929,"children":7930},{"class":154,"line":342},[7931,7936,7940,7944,7948,7952,7956,7960,7964,7968,7972,7976,7980,7984,7988,7993],{"type":31,"tag":152,"props":7932,"children":7933},{"style":498},[7934],{"type":40,"value":7935},"  const rejected ",{"type":31,"tag":152,"props":7937,"children":7938},{"style":266},[7939],{"type":40,"value":7465},{"type":31,"tag":152,"props":7941,"children":7942},{"style":498},[7943],{"type":40,"value":7871},{"type":31,"tag":152,"props":7945,"children":7946},{"style":580},[7947],{"type":40,"value":583},{"type":31,"tag":152,"props":7949,"children":7950},{"style":193},[7951],{"type":40,"value":7880},{"type":31,"tag":152,"props":7953,"children":7954},{"style":498},[7955],{"type":40,"value":410},{"type":31,"tag":152,"props":7957,"children":7958},{"style":226},[7959],{"type":40,"value":410},{"type":31,"tag":152,"props":7961,"children":7962},{"style":260},[7963],{"type":40,"value":7893},{"type":31,"tag":152,"props":7965,"children":7966},{"style":226},[7967],{"type":40,"value":448},{"type":31,"tag":152,"props":7969,"children":7970},{"style":266},[7971],{"type":40,"value":3513},{"type":31,"tag":152,"props":7973,"children":7974},{"style":498},[7975],{"type":40,"value":7906},{"type":31,"tag":152,"props":7977,"children":7978},{"style":580},[7979],{"type":40,"value":583},{"type":31,"tag":152,"props":7981,"children":7982},{"style":498},[7983],{"type":40,"value":814},{"type":31,"tag":152,"props":7985,"children":7986},{"style":266},[7987],{"type":40,"value":819},{"type":31,"tag":152,"props":7989,"children":7990},{"style":534},[7991],{"type":40,"value":7992}," 'rejected'",{"type":31,"tag":152,"props":7994,"children":7995},{"style":498},[7996],{"type":40,"value":5271},{"type":31,"tag":152,"props":7998,"children":7999},{"class":154,"line":372},[8000],{"type":31,"tag":152,"props":8001,"children":8002},{"emptyLinePlaceholder":13},[8003],{"type":40,"value":180},{"type":31,"tag":152,"props":8005,"children":8006},{"class":154,"line":386},[8007,8012,8017,8021,8026,8030,8035],{"type":31,"tag":152,"props":8008,"children":8009},{"style":193},[8010],{"type":40,"value":8011},"  expect",{"type":31,"tag":152,"props":8013,"children":8014},{"style":498},[8015],{"type":40,"value":8016},"(fulfilled)",{"type":31,"tag":152,"props":8018,"children":8019},{"style":580},[8020],{"type":40,"value":583},{"type":31,"tag":152,"props":8022,"children":8023},{"style":193},[8024],{"type":40,"value":8025},"toHaveLength",{"type":31,"tag":152,"props":8027,"children":8028},{"style":498},[8029],{"type":40,"value":410},{"type":31,"tag":152,"props":8031,"children":8032},{"style":1725},[8033],{"type":40,"value":8034},"1",{"type":31,"tag":152,"props":8036,"children":8037},{"style":498},[8038],{"type":40,"value":5271},{"type":31,"tag":152,"props":8040,"children":8041},{"class":154,"line":394},[8042,8046,8051,8055,8059,8063,8067],{"type":31,"tag":152,"props":8043,"children":8044},{"style":193},[8045],{"type":40,"value":8011},{"type":31,"tag":152,"props":8047,"children":8048},{"style":498},[8049],{"type":40,"value":8050},"(rejected)",{"type":31,"tag":152,"props":8052,"children":8053},{"style":580},[8054],{"type":40,"value":583},{"type":31,"tag":152,"props":8056,"children":8057},{"style":193},[8058],{"type":40,"value":8025},{"type":31,"tag":152,"props":8060,"children":8061},{"style":498},[8062],{"type":40,"value":410},{"type":31,"tag":152,"props":8064,"children":8065},{"style":1725},[8066],{"type":40,"value":8034},{"type":31,"tag":152,"props":8068,"children":8069},{"style":498},[8070],{"type":40,"value":5271},{"type":31,"tag":152,"props":8072,"children":8073},{"class":154,"line":480},[8074,8078,8083,8088,8093,8097,8102,8106,8110,8115,8119,8124],{"type":31,"tag":152,"props":8075,"children":8076},{"style":193},[8077],{"type":40,"value":8011},{"type":31,"tag":152,"props":8079,"children":8080},{"style":498},[8081],{"type":40,"value":8082},"((rejected[",{"type":31,"tag":152,"props":8084,"children":8085},{"style":1725},[8086],{"type":40,"value":8087},"0",{"type":31,"tag":152,"props":8089,"children":8090},{"style":498},[8091],{"type":40,"value":8092},"] ",{"type":31,"tag":152,"props":8094,"children":8095},{"style":209},[8096],{"type":40,"value":3680},{"type":31,"tag":152,"props":8098,"children":8099},{"style":220},[8100],{"type":40,"value":8101}," PromiseRejectedResult",{"type":31,"tag":152,"props":8103,"children":8104},{"style":498},[8105],{"type":40,"value":448},{"type":31,"tag":152,"props":8107,"children":8108},{"style":580},[8109],{"type":40,"value":583},{"type":31,"tag":152,"props":8111,"children":8112},{"style":498},[8113],{"type":40,"value":8114},"reason)",{"type":31,"tag":152,"props":8116,"children":8117},{"style":580},[8118],{"type":40,"value":583},{"type":31,"tag":152,"props":8120,"children":8121},{"style":193},[8122],{"type":40,"value":8123},"toBeInstanceOf",{"type":31,"tag":152,"props":8125,"children":8126},{"style":498},[8127],{"type":40,"value":8128},"(SlotAlreadyHeldError);\n",{"type":31,"tag":152,"props":8130,"children":8131},{"class":154,"line":489},[8132,8137],{"type":31,"tag":152,"props":8133,"children":8134},{"style":498},[8135],{"type":40,"value":8136},"})",{"type":31,"tag":152,"props":8138,"children":8139},{"style":226},[8140],{"type":40,"value":546},{"type":31,"tag":32,"props":8142,"children":8143},{},[8144],{"type":40,"value":8145},"Ces 4 garde-fous tiennent en 2 minutes par PR. Ils attrapent 90% des bugs de concurrence que j'ai vus passer en prod sur des codebases IA-heavy. Le coût d'application est bas. Le coût d'omission peut, lui, se chiffrer en heures de débogage sur un incident un vendredi soir.",{"type":31,"tag":48,"props":8147,"children":8148},{},[],{"type":31,"tag":52,"props":8150,"children":8151},{"id":5659},[8152],{"type":40,"value":5662},{"type":31,"tag":32,"props":8154,"children":8155},{},[8156],{"type":40,"value":8157},"Sur les 3 dernières missions où j'ai déployé cette grille de review, voici les chiffres avant/après mesurés sur 4 mois.",{"type":31,"tag":5460,"props":8159,"children":8160},{},[8161,8180],{"type":31,"tag":5464,"props":8162,"children":8163},{},[8164],{"type":31,"tag":5468,"props":8165,"children":8166},{},[8167,8171,8175],{"type":31,"tag":5472,"props":8168,"children":8169},{},[8170],{"type":40,"value":5681},{"type":31,"tag":5472,"props":8172,"children":8173},{},[8174],{"type":40,"value":5686},{"type":31,"tag":5472,"props":8176,"children":8177},{},[8178],{"type":40,"value":8179},"Après 4 mois",{"type":31,"tag":5488,"props":8181,"children":8182},{},[8183,8201,8219,8237],{"type":31,"tag":5468,"props":8184,"children":8185},{},[8186,8191,8196],{"type":31,"tag":5495,"props":8187,"children":8188},{},[8189],{"type":40,"value":8190},"Bugs de concurrence trouvés en review",{"type":31,"tag":5495,"props":8192,"children":8193},{},[8194],{"type":40,"value":8195},"2 par mois en moyenne",{"type":31,"tag":5495,"props":8197,"children":8198},{},[8199],{"type":40,"value":8200},"11 par mois en moyenne",{"type":31,"tag":5468,"props":8202,"children":8203},{},[8204,8209,8214],{"type":31,"tag":5495,"props":8205,"children":8206},{},[8207],{"type":40,"value":8208},"Bugs de concurrence remontés depuis la prod",{"type":31,"tag":5495,"props":8210,"children":8211},{},[8212],{"type":40,"value":8213},"5 par trimestre",{"type":31,"tag":5495,"props":8215,"children":8216},{},[8217],{"type":40,"value":8218},"1 par trimestre",{"type":31,"tag":5468,"props":8220,"children":8221},{},[8222,8227,8232],{"type":31,"tag":5495,"props":8223,"children":8224},{},[8225],{"type":40,"value":8226},"Temps moyen de review d'une PR Claude",{"type":31,"tag":5495,"props":8228,"children":8229},{},[8230],{"type":40,"value":8231},"8 minutes",{"type":31,"tag":5495,"props":8233,"children":8234},{},[8235],{"type":40,"value":8236},"11 minutes",{"type":31,"tag":5468,"props":8238,"children":8239},{},[8240,8245,8250],{"type":31,"tag":5495,"props":8241,"children":8242},{},[8243],{"type":40,"value":8244},"Confiance équipe dans le code IA-généré (sondage 1-10)",{"type":31,"tag":5495,"props":8246,"children":8247},{},[8248],{"type":40,"value":8249},"6,2",{"type":31,"tag":5495,"props":8251,"children":8252},{},[8253],{"type":40,"value":8254},"8,1",{"type":31,"tag":32,"props":8256,"children":8257},{},[8258,8260,8266],{"type":40,"value":8259},"Le coût est de 3 minutes supplémentaires par PR. Le gain est de 4 bugs de prod évités par trimestre. Sur une équipe de 5 développeurs avec 60 PR par mois, c'est environ 3 heures par semaine investies pour éviter 8 à 12 incidents par an. Le rapport est nettement favorable. C'est aussi ce qu'une ",{"type":31,"tag":64,"props":8261,"children":8263},{"href":8262},"/fr/dette-technique/revue-de-code-java-guide-exemples",[8264],{"type":40,"value":8265},"revue de code structurée et appliquée à l'ère IA",{"type":40,"value":8267}," permet d'enclencher : pas un contrôle qualité figé, mais un filet adaptatif qui suit là où l'IA produit ses angles morts.",{"type":31,"tag":48,"props":8269,"children":8270},{},[],{"type":31,"tag":5642,"props":8272,"children":8274},{"cta":5839,"href":5840,"title":8273,"type":5842},"Ces 4 garde-fous ne sont qu'un début : il en existe 100",[8275],{"type":31,"tag":32,"props":8276,"children":8277},{},[8278],{"type":40,"value":8279},"La grille de review concurrence décrite ici fait partie d'un référentiel plus large : le Craft Bundle, les 100 pratiques craft que j'applique pour écrire du code propre et robuste, celles que l'IA ne vous apprendra jamais parce qu'elle ne les a jamais vues tourner en prod. De quoi transformer vos réflexes, une pratique à la fois.",{"type":31,"tag":48,"props":8281,"children":8282},{},[],{"type":31,"tag":52,"props":8284,"children":8285},{"id":5802},[8286],{"type":40,"value":5805},{"type":31,"tag":32,"props":8288,"children":8289},{},[8290],{"type":40,"value":8291},"Ce que je veux que vous reteniez de cet article, c'est que Claude n'écrit pas de bugs au sens où on l'entendait avant. Il écrit du code qui passe les tests qu'on lui demande de passer, dans les conditions qu'on lui décrit. Quand ces conditions ne couvrent pas la concurrence, la latence réseau, les partial failures, le code est silencieusement faux. Le bug est là, mais il dort.",{"type":31,"tag":32,"props":8293,"children":8294},{},[8295],{"type":40,"value":8296},"Votre rôle de senior, en 2026, n'est pas de relire les accolades. C'est de poser à chaque PR Claude les 4 questions que l'IA ne se pose pas elle-même. Si vous tenez cette discipline, vous transformez Claude d'un junior risqué en un copilote fiable. Si vous la lâchez, vous accumulez de la dette qui se révèlera un vendredi soir, quand il ne faudra surtout pas qu'elle se révèle.",{"type":31,"tag":32,"props":8298,"children":8299},{},[8300],{"type":40,"value":8301},"Si en lisant ces lignes vous reconnaissez votre situation, vous avez deux choix. Vous pouvez attendre votre prochain incident pour réagir. Ou vous pouvez commencer lundi matin, par une grille de review en 4 points, et apprendre à voir ce que Claude vous fait coder sans que vous le sachiez.",{"type":31,"tag":32,"props":8303,"children":8304},{},[8305,8307,8312],{"type":40,"value":8306},"Pour la suite des patterns craft + IA en format court, retrouvez-moi sur ",{"type":31,"tag":64,"props":8308,"children":8310},{"href":5828,"rel":8309},[68],[8311],{"type":40,"value":5832},{"type":40,"value":8313},", où je publie chaque semaine les pièges que je vois revenir en mission.",{"type":31,"tag":48,"props":8315,"children":8316},{},[],{"type":31,"tag":52,"props":8318,"children":8320},{"id":8319},"faq-sur-les-bugs-claude-et-la-review-ia-générée",[8321],{"type":40,"value":8322},"FAQ sur les bugs Claude et la review IA-générée",{"type":31,"tag":5859,"props":8324,"children":8325},{},[8326,8331],{"type":31,"tag":5863,"props":8327,"children":8328},{},[8329],{"type":40,"value":8330},"1. Comment justifier auprès de mon équipe le temps supplémentaire de review ?",{"type":31,"tag":32,"props":8332,"children":8333},{},[8334,8336,8340],{"type":40,"value":8335},"Le calcul est simple. 3 minutes de review supplémentaires par PR, sur 60 PR par mois, c'est 3 heures par mois. Un seul incident de race condition en prod sur une fonctionnalité critique peut coûter entre 5 000 et 50 000 euros en remédiation, perte de confiance client et heures de war room. Le ROI est calculable et défendable devant n'importe quel CTO, et c'est exactement l'angle que je détaille dans ",{"type":31,"tag":64,"props":8337,"children":8338},{"href":5792},[8339],{"type":40,"value":5795},{"type":40,"value":583},{"type":31,"tag":5859,"props":8342,"children":8343},{},[8344,8349],{"type":31,"tag":5863,"props":8345,"children":8346},{},[8347],{"type":40,"value":8348},"2. Faut-il refuser systématiquement les PR Claude qui touchent à l'état partagé ?",{"type":31,"tag":32,"props":8350,"children":8351},{},[8352],{"type":40,"value":8353},"Non, ce serait contre-productif et casserait la vélocité. Ce qu'il faut, c'est instrumenter la review avec les 4 garde-fous décrits ici, et exiger explicitement que Claude soit re-prompté avec le contexte de concurrence quand il manque. Le test : si vous ne savez pas répondre à \"que se passe-t-il si 2 appels simultanés\", la PR retourne en draft.",{"type":31,"tag":5859,"props":8355,"children":8356},{},[8357,8362],{"type":31,"tag":5863,"props":8358,"children":8359},{},[8360],{"type":40,"value":8361},"3. Les tests automatisés ne devraient-ils pas attraper ces bugs ?",{"type":31,"tag":32,"props":8363,"children":8364},{},[8365,8367,8372,8374,8380],{"type":40,"value":8366},"En théorie oui, en pratique non. Les tests unitaires mockent la DB, donc ils ne voient pas la concurrence. Les tests d'intégration tournent en séquentiel par défaut, donc ils ne déclenchent pas la race. Il faut écrire des tests de concurrence explicites (via ",{"type":31,"tag":148,"props":8368,"children":8370},{"className":8369},[],[8371],{"type":40,"value":7647},{"type":40,"value":8373}," sur la même ressource en Vitest), et ces tests, Claude ne les écrit jamais spontanément. C'est aussi ce que pointe ",{"type":31,"tag":64,"props":8375,"children":8377},{"href":8376},"/fr/intelligence-artificielle/tester-code-genere-ia-checklist",[8378],{"type":40,"value":8379},"la checklist pour tester du code généré par IA",{"type":40,"value":583},{"type":31,"tag":5859,"props":8382,"children":8383},{},[8384,8389],{"type":31,"tag":5863,"props":8385,"children":8386},{},[8387],{"type":40,"value":8388},"4. Quels autres patterns dangereux faut-il surveiller dans le code Claude ?",{"type":31,"tag":32,"props":8390,"children":8391},{},[8392],{"type":40,"value":8393},"J'en ai documenté 5 récurrents : la God Function, le couplage métier/ORM, les tests qui ne testent rien, le catch-all silencieux et les dépendances non auditées. Chacun mérite un traitement spécifique en review. Le sujet est aussi lié aux vulnérabilités de sécurité dans le code LLM-généré pour les patterns les plus sensibles.",{"type":31,"tag":5859,"props":8395,"children":8396},{},[8397,8402],{"type":31,"tag":5863,"props":8398,"children":8399},{},[8400],{"type":40,"value":8401},"5. Comment former mon équipe à voir ces bugs sans alourdir la charge cognitive ?",{"type":31,"tag":32,"props":8403,"children":8404},{},[8405],{"type":40,"value":8406},"La meilleure méthode que j'ai vue fonctionner, c'est de transformer la grille en 4 garde-fous en checklist GitHub PR template, visible à chaque review. Les juniors la suivent par discipline, les seniors la suivent par réflexe, et au bout de 3 mois tout le monde l'a intégrée sans s'en rendre compte. Le rituel s'inscrit dans une culture engineering de rituels craft qui transforme les bonnes intentions en habitudes durables.",{"type":31,"tag":5859,"props":8408,"children":8409},{},[8410,8415],{"type":31,"tag":5863,"props":8411,"children":8412},{},[8413],{"type":40,"value":8414},"6. Est-ce que ce problème va disparaître avec les prochaines versions de Claude ?",{"type":31,"tag":32,"props":8416,"children":8417},{},[8418],{"type":40,"value":8419},"Non, et c'est important de le comprendre. Le problème n'est pas dans la qualité du modèle, il est dans l'absence de contexte d'exécution au moment de la génération. Tant que Claude génère du code sans observer la prod réelle (charge, concurrence, latence), il continuera à produire des patterns qui passent les tests et plantent sous contrainte. L'amélioration viendra des outils d'exécution autour de l'IA, pas du modèle lui-même.",{"type":31,"tag":48,"props":8421,"children":8422},{},[],{"type":31,"tag":5642,"props":8424,"children":8425},{"cta":5993,"href":5994,"title":5995,"type":5996},[8426],{"type":31,"tag":32,"props":8427,"children":8428},{},[8429],{"type":40,"value":8430},"L'EMA est l'outil que je propose au début de chaque mission. Il mesure la maturité de votre équipe sur plusieurs axes engineering, dont la code review, la gouvernance IA et la résilience prod. Quelques minutes pour identifier où votre filet de review craque le plus, et où concentrer vos efforts en priorité.",{"type":31,"tag":6004,"props":8432,"children":8433},{},[8434],{"type":40,"value":6008},{"title":8,"searchDepth":165,"depth":165,"links":8436},[8437,8438,8439,8440,8441,8442,8443],{"id":6078,"depth":165,"text":6081},{"id":6174,"depth":165,"text":6177},{"id":6781,"depth":165,"text":6784},{"id":7557,"depth":165,"text":7560},{"id":5659,"depth":165,"text":5662},{"id":5802,"depth":165,"text":5805},{"id":8319,"depth":165,"text":8322},"content:fr:intelligence-artificielle:bug-claude-vendredi-dernier.md","fr/intelligence-artificielle/bug-claude-vendredi-dernier.md","fr/intelligence-artificielle/bug-claude-vendredi-dernier",1782669247376]