{"pageProps":{"locale":{"code":"fr","domain":"frenchstack.fr","lang":"fr-FR","json":{"TRANSLATE":"Traduire en","EN":"Anglais","FR":"Français","NO_TRANSLATION_AVAILABLE":"Aucune traduction disponible","PROFILE_OF":"Profil de","FILTER_BY_TAG":"Filtrer par tag","REMOVE_FILTER":"Supprimer le filtre","RESULT":"Résulat","RESULTS":"Résulats","FORM_CONTACT_SUPPORT":"Support","FORM_CONTACT_SALES":"Devis","FORM_CONTACT_BUGS":"Rapport de bug","FORM_LOADING":"Chargement","FORM_SEND":"Envoyer","FORM_VERIFY":"Vérifier","FORM_NAME":"Nom","FORM_TOPIC":"Sujet","FORM_PHONE":"Téléphone","FORM_EMAIL":"Email","FORM_MESSAGE":"Message","FORM_DOMAIN_PLACEHOLDER":"exemple.fr","FORM_DOMAIN_AVAILABLE":"Félicitations, le domaine <span data-selector='domain'></span> est disponible !","FORM_DOMAIN_TAKEN":"Désolé, le domaine <span data-selector='domain'></span> est pris.","SUBSCRIBE":"S'abonner","SUCCESS_CONTACT":"Votre message a bien été envoyé ! Nous vous répondrons dans les plus brefs délais.","SOMETING_WENT_WRONG":"Oops, une erreur s'est produite. Veuillez réessayer ultérieurement.","PERFORMANCE":"Performance","ACCESSIBILITY":"Accessibilité","BEST_PRACTICES":"Bonnes pratiques","SEO":"Référencement","MOBILE":"Mobile","TABLET":"Tablette","DESKTOP":"Ordinateur","VISITORS":"Visiteurs","ENGAGEMENT":"Engagement","CONVERSIONS":"Conversions","JAN":"Janv","FEB":"Févr","MAR":"Mars","APR":"Avr","MAY":"Mai","JUN":"Juin","JUL":"Juil","AUG":"Août","SEP":"Sept","OCT":"Oct","NOV":"Nov","DEC":"Déc","METHOD_PHONE":"Téléphone","METHOD_EMAIL":"Email","FOOTER_TAGLINE":"Nous créons des expériences numériques uniques pour les marques et les entreprises.","LOOP_ACTOR_AGENT":"Agent IA","LOOP_STEPS":"Étapes","LOOP_REPEATED":"répétées","AND":"et"},"subdomains":{"blog":"blog","clients":"references","videos":"videos","services":"services"},"ogSection":"Technologie"},"slugs":["fr","blog"],"component":"paging","articles":[{"id":"content/articles/fr/fallow-codebase-intelligence-typescript.mdx","heroSection":{"heroTitle":"Fallow mesure, l'IA bâtit","heroSubtitle":"Le duo qui forme l'architecte logiciel ultime","heroBadge":"","heroColoredWords":"1,3","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"D'un côté, une architecture verrouillée et mesurable. De l'autre, un agent qui exécute sans relâche."}]},{"type":"p","children":[{"type":"text","text":"Ensemble, ils découpent, nomment et rangent chaque ligne de code."}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/fallow-codebase-intelligence-typescript.png","heroVideoBackground":"","heroStyle":{"heroBg":"","heroMaxWidth":"","heroMs":"","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"fallow codebase intelligence typescript","imageWidth":1376,"imageHeight":768},"seoSection":{"metaTitle":"Fallow et agents IA : retour d'expérience sur la qualité de code","metaDescription":"Retour d'expérience : Fallow, analyseur statique TypeScript écrit en Rust, sert de source de vérité à mes agents IA et les guide pour découper fonctions et fichiers en unités claires, bien nommées et bien rangées.","metaTags":"Fallow, TypeScript, agent IA, qualité de code, complexité cognitive, refactoring, Claude Code, Codex, analyse statique, MCP, vibe coding","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2026-10-18T13:38:48.000Z","localeCode":"fr","slug":"fallow-codebase-intelligence-typescript","url":"/fr/blog/fallow-codebase-intelligence-typescript","ogId":"fallow-codebase-intelligence-typescript-blog-fr","ogImagePath":"/og/fallow-codebase-intelligence-typescript-blog-fr.png","type":"Article","title":"Fallow : la qualité de code au rythme des agents IA","subtitle":"Retour d'expérience sur un contrôle déterministe pour TypeScript","browserUrl":"","textPreview":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Fallow mesure la complexité, le code mort et la duplication d'un projet TypeScript. Branché sur mes agents IA, il fait de chaque commit l'occasion de découper fonctions et fichiers en unités bien nommées et bien rangées."}]}]},"subdomainKey":"blog","subdomain":"blog","draft":false,"logoAlt":"","logoWidth":0,"logoHeight":0,"icon":"code","body":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Les agents IA écrivent désormais une large part du code de mes projets. Ils livrent vite et bien, avec une tendance constante à "},{"type":"text","text":"enrichir l'existant","bold":true},{"type":"text","text":" plutôt qu'à créer un nouveau concept. Au fil des demandes, une fonction de 20 lignes en compte 100, un fichier de 100 lignes en compte 500, et les noms ne décrivent plus qu'une partie de ce qu'ils contiennent."}]},{"type":"p","children":[{"type":"text","text":"Fallow","bold":true},{"type":"text","text":" corrige cette dérive avec une efficacité redoutable. Avant chaque commit, mon agent exécute Fallow pour mesurer les fonctions et les fichiers du projet. Tant que le verdict n'est pas vert, il découpe. Cette procédure garantit un code composé de petites fonctions, rangées dans des fichiers à responsabilité unique, dont le nom dit exactement ce qu'ils font."}]},{"type":"mdxJsxFlowElement","name":"codeTidy","children":[{"type":"text","text":""}],"props":{"before":"Un fichier qui fait tout","after":"Une responsabilité par fichier","caption":"Fallow mesure, l'agent découpe et range chaque responsabilité à sa place."}},{"type":"hr","children":[{"type":"text","text":""}]},{"type":"h2","children":[{"type":"text","text":"Fallow en bref"}]},{"type":"p","children":[{"type":"a","url":"https://fallow.tools","title":"Fallow - Codebase intelligence","children":[{"type":"text","text":"Fallow"}]},{"type":"text","text":" est un analyseur statique "},{"type":"text","text":"open source","italic":true},{"type":"text","text":" pour "},{"type":"text","text":"TypeScript et JavaScript","bold":true},{"type":"text","text":", distribué sous licence MIT sous la forme d'un binaire Rust unique. Il construit un graphe complet du dépôt (modules, exports, dépendances, fonctions) et en tire quatre familles d'analyses :"}]},{"type":"ul","children":[{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Complexité","bold":true},{"type":"text","text":" : Mesure de la complexité cyclomatique et cognitive de chaque fonction, score de maintenabilité de chaque fichier et note de santé du projet sur 100."}]}]},{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Code mort","bold":true},{"type":"text","text":" : Détection des fichiers, exports, types et dépendances que plus rien n'utilise."}]}]},{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Duplication","bold":true},{"type":"text","text":" : Repérage des blocs copiés d'un fichier à l'autre, dans le code TypeScript et JavaScript comme dans les feuilles de style et les composants d'interface."}]}]},{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Architecture","bold":true},{"type":"text","text":" : Contrôle du découpage des imports (interface, métier, données) et détection des dépendances circulaires."}]}]}]},{"type":"p","children":[{"type":"text","text":"L'analyseur n'embarque "},{"type":"text","text":"aucun modèle de langage","bold":true},{"type":"text","text":" : la même entrée produit toujours le même résultat. Il s'exécute seul, sans compilateur TypeScript ni runtime Node.js. Selon les mesures publiées par le projet, il est capable d'analyser un dépôt aussi volumineux que le monorepo de Next.js ("},{"type":"text","text":"20 558 fichiers","bold":true},{"type":"text","text":") en moins de "},{"type":"text","text":"3 secondes","bold":true},{"type":"text","text":"."}]},{"type":"p","children":[{"type":"text","text":"Ce déterminisme en fait le bon partenaire d'un agent IA : l'agent propose, Fallow mesure."}]},{"type":"mdxJsxFlowElement","name":"sourceNote","children":[{"type":"text","text":""}],"props":{"content":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Sources : "},{"type":"a","url":"https://github.com/fallow-rs/fallow/blob/main/BENCHMARKS.md","title":null,"children":[{"type":"text","text":"BENCHMARKS.md"}]},{"type":"text","text":" du projet (mesures de juin 2026) et "},{"type":"a","url":"https://fallow.tools","title":null,"children":[{"type":"text","text":"fallow.tools"}]},{"type":"text","text":", consultés en octobre 2026."}]}]}}},{"type":"hr","children":[{"type":"text","text":""}]},{"type":"h2","children":[{"type":"text","text":"Un arbitre dans la boucle de l'agent"}]},{"type":"p","children":[{"type":"text","text":"Au rythme des agents, je ne relis plus chaque ligne une à une. Demander à un agent « d'écrire du code simple » ne permet pas de s'assurer que la contrainte est respectée."}]},{"type":"p","children":[{"type":"text","text":"Fallow devient le garde-fou de chaque commit. Le schéma ci-dessous montre la boucle que suit l'agent pour chaque tâche :"}]},{"type":"mdxJsxFlowElement","name":"agentLoop","children":[{"type":"text","text":""}],"props":{"steps":[{"actor":"agent","title":"Développement","detail":"Implémentation de la demande, sans contrainte particulière"},{"actor":"fallow","title":"Mesure","detail":"Signalement des fonctions trop complexes, des fichiers à scinder, des exports inutiles et des blocs dupliqués","inLoop":true},{"actor":"agent","title":"Découpage","detail":"Extraction des étapes en fonctions nommées et des responsabilités en fichiers dédiés","inLoop":true},{"actor":"git","title":"Commit","detail":"Accepté seulement sur un verdict « pass »"}],"loopLabel":"jusqu'au vert","caption":"Le verrou bloque le commit tant que Fallow rend un verdict « fail »."}},{"type":"p","children":[{"type":"text","text":"Le découpage s'opère à deux échelles :"}]},{"type":"ul","children":[{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Fonction","bold":true},{"type":"text","text":" : Seuils par défaut de "},{"type":"text","text":"20","bold":true},{"type":"text","text":" en complexité cyclomatique, "},{"type":"text","text":"15","bold":true},{"type":"text","text":" en complexité cognitive et "},{"type":"text","text":"60 lignes","bold":true},{"type":"text","text":" par fonction, que je conserve tels quels."}]}]},{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Fichier","bold":true},{"type":"text","text":" : Score de maintenabilité calculé à partir de la taille, de la densité de complexité, du code mort et des dépendances, et recommandations classées par priorité, comme « scinder un fichier dont trop d'autres dépendent » ou « extraire la fonction "},{"type":"text","text":"parseRow","code":true},{"type":"text","text":" d'un fichier de 520 lignes »."}]}]}]},{"type":"p","children":[{"type":"text","text":"Fallow ne dit pas comment corriger : il désigne ce qui est trop long, trop imbriqué, trop central ou répété, et laisse à l'agent le soin de "},{"type":"text","text":"découper et ranger","bold":true},{"type":"text","text":"."}]},{"type":"mdxJsxFlowElement","name":"sourceNote","children":[{"type":"text","text":""}],"props":{"content":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Source : "},{"type":"a","url":"https://fallow.tools/docs/explanations/health/","title":null,"children":[{"type":"text","text":"Health explained"}]},{"type":"text","text":", documentation de Fallow consultée en octobre 2026."}]}]}}},{"type":"hr","children":[{"type":"text","text":""}]},{"type":"h2","children":[{"type":"text","text":"Retour d'expérience"}]},{"type":"p","children":[{"type":"text","text":"J'ai codé un petit bot en "},{"type":"text","text":"TypeScript","bold":true},{"type":"text","text":" qui réserve automatiquement mes séances de sport, dont les places partent en quelques minutes. Une fois stabilisé, j'ai confié le projet à un agent IA pour qu'il l'intègre à "},{"type":"text","text":"Home Assistant","bold":true},{"type":"text","text":", avec une interface graphique, des réservations pilotables et des notifications sur le téléphone."}]},{"type":"p","children":[{"type":"img","url":"/images/fallow-rpm-lesmills-bot.png","alt":"Interface du bot de réservation de cours de sport dans Home Assistant","caption":"1448x836","children":[{"type":"text","text":""}]}]},{"type":"p","children":[{"type":"text","text":"L'agent a livré rapidement un projet fonctionnel, mais chaque évolution s'était greffée sur le code existant. Une seule fonction contenait la connexion à l'API, la récupération du planning, le choix du créneau puis la réservation, et toute l'interface tenait dans un seul fichier."}]},{"type":"p","children":[{"type":"text","text":"Une fois Fallow branché, l'agent a isolé chaque "},{"type":"text","text":"étape métier","bold":true},{"type":"text","text":" dans une fonction dédiée, avec un nom qui dit ce qu'elle fait. Il a ensuite appliqué "},{"type":"text","text":"le même découpage par responsabilité","bold":true},{"type":"text","text":" à l'échelle des fichiers."}]},{"type":"p","children":[{"type":"text","text":"Le résultat se mesure sur trois parties du projet :"}]},{"type":"ul","children":[{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Réservation","bold":true},{"type":"text","text":" : La fonction principale passe de "},{"type":"text","text":"88 à 28 lignes","bold":true},{"type":"text","text":" et délègue la connexion, le planning, le choix du créneau et la réservation à "},{"type":"text","text":"4 fonctions","bold":true},{"type":"text","text":" nommées d'après leur étape."}]}]},{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Interface","bold":true},{"type":"text","text":" : Le fichier "},{"type":"text","text":"App.tsx","code":true},{"type":"text","text":" passe de "},{"type":"text","text":"501 à 116 lignes","bold":true},{"type":"text","text":", réparti en "},{"type":"text","text":"7 composants","bold":true},{"type":"text","text":" réutilisables, un fichier de types partagés et un "},{"type":"text","text":"hook","italic":true},{"type":"text","text":" dédié."}]}]},{"type":"li","children":[{"type":"lic","children":[{"type":"text","text":"Notifications","bold":true},{"type":"text","text":" : L'envoi des notifications, écrit "},{"type":"text","text":"3 fois","bold":true},{"type":"text","text":", n'existe plus qu'à un seul endroit sous le nom "},{"type":"text","text":"notifyBookingSuccess","code":true},{"type":"text","text":"."}]}]}]},{"type":"hr","children":[{"type":"text","text":""}]},{"type":"h2","children":[{"type":"text","text":"Une source de vérité pour cadrer l'agent"}]},{"type":"p","children":[{"type":"text","text":"Un agent IA intervient sur un projet comme le ferait un développeur. Il cherche le bon fichier, lit ce qui l'entoure et modifie ce qu'il comprend. Un projet généré prompt après prompt, sans jamais être refactoré, accumule dès les premières demandes les traits d'un code "},{"type":"text","text":"spaghetti","italic":true},{"type":"text","text":" : fichiers aux responsabilités mêlées, noms approximatifs, logique dupliquée. Dans ce contexte, trouver le bon fichier oblige l'agent à en lire davantage, et modifier ce qu'il comprend ne suffit plus, car les effets de bord se multiplient."}]},{"type":"p","children":[{"type":"text","text":"Fallow inverse cette pente sans exiger une expertise en architecture logicielle. Les règles de découpage, de nommage et de rangement sont mesurées et le verdict s'impose à l'agent, sans qu'il faille les détailler dans chaque prompt ni les contrôler à la relecture. Le bénéfice se lit sur trois plans :"}]},{"type":"mdxJsxFlowElement","name":"benefitCards","children":[{"type":"text","text":""}],"props":{"items":[{"icon":"shield","tone":"success","title":"Moins de régressions","text":"Des fonctions courtes et des fichiers à responsabilité unique, où chaque modification reste circonscrite à la partie concernée."},{"icon":"coins","tone":"warning","title":"Moins de jetons","text":"Une navigation guidée par des noms explicites, sans relecture de fichiers entiers pour trouver la bonne ligne."},{"icon":"target","tone":"primary","title":"Plus de maîtrise","text":"Un critère objectif et reproductible pour valider le travail de l'agent, là où une consigne en langage naturel reste invérifiable."}]}},{"type":"p","children":[{"type":"text","text":"Confiez Fallow à votre agent. À chaque commit, il découpe, nomme et range le code sans que vous ayez à lui dicter chaque règle. Vous gardez un projet lisible, moins coûteux à faire évoluer, et chaque nouvelle demande part d'une base saine. La qualité ne se décrète plus, elle se vérifie."}]},{"type":"mdxJsxFlowElement","name":"buttons","children":[{"type":"text","text":""}],"props":{"buttons":[{"icon":"gitHub","label":"Fallow sur GitHub","link":"https://github.com/fallow-rs/fallow","style":"primary"},{"icon":"codeFile","label":"Documentation","link":"https://fallow.tools/docs","style":"light"}]}}]},"dateCreate":"2026-10-18T09:00:00.000Z","dateUpdate":"2026-10-18T09:00:00.000Z","author":{"id":"content/authors/fr/nicolas-roehm-bettcher.mdx","heroSection":{"heroTitle":"Nicolas Roehm","heroSubtitle":"Ingénieur logiciel","heroBadge":"","heroColoredWords":"","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Fondateur de French Stack, je conçois des solutions informatiques complètes."}]},{"type":"p","children":[{"type":"text","text":"Développeur full-stack, j'interviens principalement sur des projets frontend avec Angular, React ou Vue."}]},{"type":"p","children":[{"type":"text","text":"Passionné de design, voici quelques-unes de mes "},{"type":"a","url":"https://www.artstation.com/nicolas-roehm","title":"ArtStation - Nicolas Roehm","children":[{"type":"text","text":"conceptions graphiques"}]},{"type":"text","text":"."}]},{"type":"mdxJsxFlowElement","name":"socialLinks","children":[{"type":"text","text":""}],"props":{"links":[{"icon":"gitHub","link":"https://github.com/NicolasRoehm"},{"icon":"stackOverflow","link":"https://stackoverflow.com/users/7462178/nicolas-roehm?tab=profile"},{"icon":"linkedIn","link":"https://fr.linkedin.com/in/nicolas-roehm-bettcher"}]}}]},"heroSubtitleIsInline":true,"heroHasBackground":false,"heroImage":"/images/nicolas-roehm-bettcher.png","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(312deg, #0800ff 0%, #4300ff00 70%)","heroMaxWidth":"","heroMs":"25%","heroTitleMb":"0.5rem","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"#fff0","navbarBorderColor":"","navbarLinkActive":"#6785be","navbarLinkHover":"#6785be"},"imageAlt":"nicolas roehm bettcher","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"Nicolas Roehm, Ingénieur logiciel","metaDescription":"Passionné d'informatique, je conçois des sites web dans leur intégralité : design, developpement, référencement, e-reputation, e-mailling, hébergement","metaTags":"Nicolas Roehm, Ingénieur logiciel, web, mobile, site internet","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2024-12-09T00:38:50.025Z","localeCode":"fr","slug":"nicolas-roehm-bettcher","url":"/fr/nicolas-roehm-bettcher","ogId":"nicolas-roehm-bettcher-fr","ogImagePath":"/og/nicolas-roehm-bettcher-fr.png","type":"Author","title":"Nicolas Roehm-Bettcher","avatar":"/images/nicolas-roehm-avatar.png","lname":"Roehm","fname":"Nicolas","name":"Nicolas Roehm","translations":[{"localeCode":"en","title":"Nicolas Roehm-Bettcher","slug":"nicolas-roehm-bettcher","url":"/en/nicolas-roehm-bettcher"}]},"translations":[{"localeCode":"en","title":"Fallow: code quality at the pace of AI agents","slug":"fallow-codebase-intelligence-typescript","url":"/en/blog/fallow-codebase-intelligence-typescript"}],"tags":[{"id":"content/tags/fr/typescript.mdx","localeCode":"fr","title":"TypeScript","slug":"typescript","url":"/fr/blog/typescript"}]},{"id":"content/articles/fr/angular-validation-formulaire-comparer-plusieurs-champs.mdx","heroSection":{"heroTitle":"Comparer plusieurs champs","heroSubtitle":"","heroBadge":"Validation de formulaire Angular","heroColoredWords":"1","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Comment valider deux champs d'un formulaire en faisant une comparaison ?"}]},{"type":"p","children":[{"type":"text","text":"Vérifions plusieurs champs avec un validateur de haut niveau !"}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/angular-form-validation.png","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(180deg, transparent 0%, #0e256ddb 17%, #ff4444db 120%)","heroMaxWidth":"","heroMs":"","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"angular form validation","imageWidth":1344,"imageHeight":768},"seoSection":{"metaTitle":"Validation de formulaire Angular : Comparer plusieurs champs","metaDescription":"Comment valider deux champs d'un formulaire en faisant une comparaison ? Vérifions plusieurs champs avec un validateur de haut niveau !","metaTags":"formulaire, angular, validation, angular-validation","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2024-12-07T00:09:54.046Z","localeCode":"fr","slug":"angular-validation-formulaire-comparer-plusieurs-champs","url":"/fr/blog/angular-validation-formulaire-comparer-plusieurs-champs","ogId":"angular-validation-formulaire-comparer-plusieurs-champs-blog-fr","ogImagePath":"/og/angular-validation-formulaire-comparer-plusieurs-champs-blog-fr.png","type":"Article","title":"Comparer plusieurs champs avec Angular","subtitle":"","browserUrl":"","textPreview":{"type":"root","children":[]},"subdomainKey":"blog","subdomain":"blog","draft":false,"logoAlt":"","logoWidth":0,"logoHeight":0,"body":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Supposons que notre formulaire ait des champs de date "},{"type":"text","text":"startDate","code":true},{"type":"text","text":" et "},{"type":"text","text":"endDate","code":true},{"type":"text","text":" et nous voulons nous assurer que "},{"type":"text","text":"startDate","code":true},{"type":"text","text":" doit être avant "},{"type":"text","text":"endDate","code":true},{"type":"text","text":"."}]},{"type":"p","children":[{"type":"text","text":"Pour implémenter des validations contenant un ou plusieurs contrôles frères, nous devons définir la fonction de validation à un niveau supérieur à celui des contrôles frères."}]},{"type":"mdxJsxFlowElement","name":"codeHeader","children":[{"type":"text","text":""}],"props":{"filePath":"app / src / pages / form-example / form-example.component.ts","fileName":"form-example.component.ts","svgFile":"typescript"}},{"type":"code_block","lang":"typescript","value":"ngOnInit() : void\n{\n  this.formGroup = this.formBuilder.group(\n  {\n    startDate : new FormControl({\n      value    : null,\n      disabled : false\n    }, [ Validators.required ]),\n    endDate : new FormControl({\n      value    : null,\n      disabled : false\n    }, [ Validators.required ]),\n  },\n  // NOTE Validateur de haut niveau\n  { validator : DateValidator.dateRangeValidator });\n}","children":[{"type":"text","text":""}]},{"type":"p","children":[{"type":"text","text":"Ensuite, nous définissons un validateur personnalisé dans un fichier séparé, par exemple "},{"type":"text","text":"date.validator.ts","code":true},{"type":"text","text":"."}]},{"type":"mdxJsxFlowElement","name":"codeHeader","children":[{"type":"text","text":""}],"props":{"fileName":"date.validator.ts","filePath":"app / src / shared / validators / date.validator.ts","svgFile":"typescript"}},{"type":"code_block","lang":"typescript","value":"// Angular modules\nimport { Injectable }       from '@angular/core';\nimport { AbstractControl }  from '@angular/forms';\nimport { ValidationErrors } from '@angular/forms';\n\n@Injectable({\n  providedIn : 'root'\n})\nexport class DateValidator\n{\n  constructor() {}\n\n  public static dateRangeValidator(control : AbstractControl) : ValidationErrors | null\n  {\n    // NOTE Contrôle de sécurité\n    if (!control.get('startDate').value || !control.get('endDate').value)\n      return null;\n\n    // NOTE Comparaison de champs\n    // const mStart  = moment(control.get('startDate').value);\n    // const mEnd    = moment(control.get('endDate').value);\n    // const isValid = mStart.isBefore(mEnd);\n\n    // NOTE Invalide\n    if (!isValid)\n      return { invalidDateRange : true };\n\n    // NOTE Valide\n    return null;\n  }\n}","children":[{"type":"text","text":""}]},{"type":"p","children":[{"type":"text","text":"Si invalide, retourne un objet d'erreur (n'importe quel nom arbitraire), comme, "},{"type":"text","text":"return { invalidEndDate: true }","code":true},{"type":"text","text":"."}]},{"type":"p","children":[{"type":"text","text":"Assurez-vous qu'il renvoie toujours un "},{"type":"text","text":"null","code":true},{"type":"text","text":" pour les cas valides ou non pertinents, et un objet \"non-null\" dans les cas où une erreur doit être déclenchée sur le "},{"type":"text","text":"formGroup","code":true},{"type":"text","text":"."}]},{"type":"p","children":[{"type":"text","text":"Pour afficher l'erreur au niveau de notre vue, nous utilisons la clé "},{"type":"text","text":"invalidDateRange","code":true},{"type":"text","text":" retournée par notre validateur."}]},{"type":"mdxJsxFlowElement","name":"codeHeader","children":[{"type":"text","text":""}],"props":{"fileName":"form-example.component.html","filePath":"app / src / pages / form-example / form-example.component.html","svgFile":"html"}},{"type":"code_block","lang":"html","value":"<div *ngIf=\"formGroup.hasError('invalidDateRange')\">\n  La date de début n'est pas antérieure à la date de fin\n</div>","children":[{"type":"text","text":""}]}]},"dateCreate":"2021-03-17T10:46:42.000Z","dateUpdate":"2021-09-15T10:57:26.000Z","author":{"id":"content/authors/fr/nicolas-roehm-bettcher.mdx","heroSection":{"heroTitle":"Nicolas Roehm","heroSubtitle":"Ingénieur logiciel","heroBadge":"","heroColoredWords":"","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Fondateur de French Stack, je conçois des solutions informatiques complètes."}]},{"type":"p","children":[{"type":"text","text":"Développeur full-stack, j'interviens principalement sur des projets frontend avec Angular, React ou Vue."}]},{"type":"p","children":[{"type":"text","text":"Passionné de design, voici quelques-unes de mes "},{"type":"a","url":"https://www.artstation.com/nicolas-roehm","title":"ArtStation - Nicolas Roehm","children":[{"type":"text","text":"conceptions graphiques"}]},{"type":"text","text":"."}]},{"type":"mdxJsxFlowElement","name":"socialLinks","children":[{"type":"text","text":""}],"props":{"links":[{"icon":"gitHub","link":"https://github.com/NicolasRoehm"},{"icon":"stackOverflow","link":"https://stackoverflow.com/users/7462178/nicolas-roehm?tab=profile"},{"icon":"linkedIn","link":"https://fr.linkedin.com/in/nicolas-roehm-bettcher"}]}}]},"heroSubtitleIsInline":true,"heroHasBackground":false,"heroImage":"/images/nicolas-roehm-bettcher.png","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(312deg, #0800ff 0%, #4300ff00 70%)","heroMaxWidth":"","heroMs":"25%","heroTitleMb":"0.5rem","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"#fff0","navbarBorderColor":"","navbarLinkActive":"#6785be","navbarLinkHover":"#6785be"},"imageAlt":"nicolas roehm bettcher","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"Nicolas Roehm, Ingénieur logiciel","metaDescription":"Passionné d'informatique, je conçois des sites web dans leur intégralité : design, developpement, référencement, e-reputation, e-mailling, hébergement","metaTags":"Nicolas Roehm, Ingénieur logiciel, web, mobile, site internet","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2024-12-09T00:38:50.025Z","localeCode":"fr","slug":"nicolas-roehm-bettcher","url":"/fr/nicolas-roehm-bettcher","ogId":"nicolas-roehm-bettcher-fr","ogImagePath":"/og/nicolas-roehm-bettcher-fr.png","type":"Author","title":"Nicolas Roehm-Bettcher","avatar":"/images/nicolas-roehm-avatar.png","lname":"Roehm","fname":"Nicolas","name":"Nicolas Roehm","translations":[{"localeCode":"en","title":"Nicolas Roehm-Bettcher","slug":"nicolas-roehm-bettcher","url":"/en/nicolas-roehm-bettcher"}]},"translations":[{"localeCode":"en","title":"Comparing Multiple Fields with Angular","slug":"angular-form-validation-compare-multiple-fields","url":"/en/blog/angular-form-validation-compare-multiple-fields"}],"tags":[{"id":"content/tags/fr/angular.mdx","localeCode":"fr","title":"Angular","slug":"angular","url":"/fr/blog/angular"}]},{"id":"content/articles/fr/javascript-librairies-youtube-like.mdx","heroSection":{"heroTitle":"Javascript librairies #1 : Youtube","heroSubtitle":"","heroBadge":"","heroColoredWords":"5","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Découvrez les meilleurs plugins et scripts « Youtube like » pour votre site web !"}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/js-libs-youtube-1.png","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(180deg, #010093eb 0%, #ffd400 100%)","heroMaxWidth":"","heroMs":"0","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"js libs youtube 1","imageWidth":1344,"imageHeight":768},"seoSection":{"metaTitle":"Youtube : JS plugins & scripts #1","metaDescription":"Cette semaine JS libs vous fait découvrir des plugins Youtube like pour votre site web","metaTags":"youtube js, youtube javascript, youtube libraries, youtube script, youtube plugin, youtube jquery","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2023-08-18T08:52:56.731Z","localeCode":"fr","slug":"javascript-librairies-youtube-like","url":"/fr/blog/javascript-librairies-youtube-like","ogId":"javascript-librairies-youtube-like-blog-fr","ogImagePath":"/og/javascript-librairies-youtube-like-blog-fr.png","type":"Article","title":"JS libs #1 : Youtube","subtitle":"","browserUrl":"","textPreview":{"type":"root","children":[]},"subdomainKey":"blog","subdomain":"blog","draft":false,"logoAlt":"","logoWidth":0,"logoHeight":0,"icon":"play-btn","body":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Découvrez une sélection de "},{"type":"text","text":"ressources web","bold":true},{"type":"text","text":", "},{"type":"text","text":"scripts","bold":true},{"type":"text","text":", "},{"type":"text","text":"plugins","bold":true},{"type":"text","text":" et "},{"type":"text","text":"outils CSS","bold":true},{"type":"text","text":" pour personnaliser votre site ! Le premier épisode de "},{"type":"text","text":"JS libs","bold":true},{"type":"text","text":" est consacré aux "},{"type":"text","text":"plugins Youtube","bold":true},{"type":"text","text":". Bonne customisation !"}]},{"type":"h3","children":[{"type":"text","text":"Youtube Loading Bar"}]},{"type":"p","children":[{"type":"text","text":"Un petit plugin jQuery qui vous permet d'ajouter une barre de chargement « Youtube-like » à tous vos liens ajax."}]},{"type":"h4","children":[{"type":"text","text":"Exemple d'initialisation"}]},{"type":"code_block","lang":"javascript","value":"$('.ajax-link').loadingbar({\n  replaceURL : true, // You can visibly change the URL of the browser to reflect the clicked links by toggling this to true\n  target     : '#loadingbar-frame', // The container's selector where you want the ajax result to appear\n  direction  : 'right', // The direction where the the loading bar will progress\n});","children":[{"type":"text","text":""}]},{"type":"p","children":[{"type":"img","url":"/images/you-tube-loading-bar.png","alt":"Script Web : Youtube Loading Bar","caption":"845x475","children":[{"type":"text","text":""}]}]},{"type":"mdxJsxFlowElement","name":"buttons","children":[{"type":"text","text":""}],"props":{"buttons":[{"icon":"gitHub","label":"GitHub","link":"https://github.com/peachananr/loading-bar","style":"primary"},{"icon":"","label":"Démonstration","link":"http://peachananr.github.io/loading-bar/demo.html","style":"light"}]}},{"type":"h3","children":[{"type":"text","text":"Tubular.js"}]},{"type":"p","children":[{"type":"text","text":"Tubular est un plugin jQuery qui vous permet de définir une vidéo YouTube en tant que fond de page. Pour cela, il vous suffit d'intégrer le plugin à votre site puis de lier le conteneur de votre page à l'ID de votre vidéo Youtube et le tour est joué !"}]},{"type":"h4","children":[{"type":"text","text":"Exemple d'initialisation"}]},{"type":"code_block","lang":"javascript","value":"$('#wrapper').tubular({ videoId : 'aJTGyyRXDh4' }); // where videoId is the YouTube ID","children":[{"type":"text","text":""}]},{"type":"h4","children":[{"type":"text","text":"Options paramétrables"}]},{"type":"code_block","lang":"javascript","value":"ratio            : 16 / 9, // Usually either 4/3 or 16/9 -- tweak as needed\nvideoId          : 'aJTGyyRXDh4',\nmute             : true,\nrepeat           : true,\nwidth            : $(window).width(), // No need to override\nwrapperZIndex    : 99,\nplayButtonClass  : 'tubular-play',\npauseButtonClass : 'tubular-pause',\nmuteButtonClass  : 'tubular-mute',\nvolumeUpClass    : 'tubular-volume-up',\nvolumeDownClass  : 'tubular-volume-down',\nincreaseVolumeBy : 10, // Increment value; volume range is 1-100\nstart            : 0 // Starting position in seconds","children":[{"type":"text","text":""}]},{"type":"p","children":[{"type":"img","url":"/images/you-tube-video-background.png","caption":"845x475","children":[{"type":"text","text":""}],"alt":"You Tube Video Background"}]},{"type":"mdxJsxFlowElement","name":"buttons","children":[{"type":"text","text":""}],"props":{"buttons":[{"icon":"google","label":"Google Code","link":"https://code.google.com/archive/p/jquery-tubular/","style":"primary"}]}},{"type":"h3","children":[{"type":"text","text":"PreViewTube"}]},{"type":"p","children":[{"type":"text","text":"Un petit plugin jQuery pour animer les vignettes de vos vidéos YouTube au survole ou en continue. Il est possible d'ajuster la vitesse d'enchaînement des images pour une meilleur fluidité de l'aperçu."}]},{"type":"h4","children":[{"type":"text","text":"Exemple d'initialisation"}]},{"type":"code_block","lang":"javascript","value":"$('.preViewTube').PreViewTube();","children":[{"type":"text","text":""}]},{"type":"h4","children":[{"type":"text","text":"Options paramétrables"}]},{"type":"code_block","lang":"javascript","value":"interval: 500, // The animation rate in ms (default: 500ms)\nmode     : 'constant' // How the animation should run 'constant' or 'hover' (default : hover)","children":[{"type":"text","text":""}]},{"type":"p","children":[{"type":"img","url":"/images/you-tube-thumbnail-images.png","caption":"845x475","children":[{"type":"text","text":""}],"alt":"You Tube Thumbnail Images"}]},{"type":"mdxJsxFlowElement","name":"buttons","children":[{"type":"text","text":""}],"props":{"buttons":[{"icon":"gitHub","label":"GitHub","link":"https://github.com/vool/PreViewTube.js","style":"primary"},{"icon":"","label":"Démonstration","link":"http://previewtube.vool.ie/","style":"light"}]}},{"type":"h3","children":[{"type":"text","text":"Youtube autoplay playlist"}]},{"type":"p","children":[{"type":"text","text":"Lecteur automatique de playlist Youtube, ce plugin jQuery permet également d'appliquer un effet cinéma à vos vidéos en « éteignant la lumière » de votre site ! De nombreuses options et paramètres sont disponibles pour personnaliser l'apparence et le mode de lecture des vidéos."}]},{"type":"h4","children":[{"type":"text","text":"Exemple d'initialisation"}]},{"type":"code_block","lang":"javascript","value":"$('#youtubevideo').youTubePlaylistResponsive({\n  listtype  : 'custom',\n  listvalue : 'gFftC9O9EZ0,-Fv-iUhLcys,Vv2YXjCWg1A,eIa7YxlHq3A'\n});","children":[{"type":"text","text":""}]},{"type":"h4","children":[{"type":"text","text":"Options paramétrables"}]},{"type":"code_block","lang":"javascript","value":"listtype        : 'search', // Choose between playlist, user_uploads, custom or search (max. 20 video's)\nlistvalue       : 'nature', // Playlist ID, channel name, ID's seperated by comma's (custom) or search for keywords\nautoplay        : false,    // If set to true the player will play onload\nshowrelated     : false,    // Show related movies at the end of the movie\nshowinfo        : true,     // Display thumbnail images for the videos in the playlist\nautohide        : false,    // Indicates whether the video controls will automatically hide after a video begins playing\ntheme           : false,    // Set the color scheme foer the player. true is white ad false is black\nmodestbranding  : true,     // Set to false to show the youtube logo in the player controll bar\niv_load_policy  : false,    // Setting to true will cause video annotations to be shown by default\nallowfullscreen : true,     // Show the fullscreen button\ncontrols        : true,     // This parameter indicates whether the video player controls will display\nhd              : false,    // Play the video's in HD at startup\nmaxwidth        : '',       // Here you can set the maxwidth in % or px\ncenter          : false,    // If maxwidth is set you can optional center the player\nlightsout       : true      // Mouseover the video turns out the light effect (background fading)","children":[{"type":"text","text":""}]},{"type":"p","children":[{"type":"img","url":"/images/you-tube-autoplay-playlist.png","caption":"845x475","children":[{"type":"text","text":""}],"alt":"You Tube Autoplay Playlist"}]},{"type":"mdxJsxFlowElement","name":"buttons","children":[{"type":"text","text":""}],"props":{"buttons":[{"icon":"codeFile","label":"Documentation","link":"https://www.cfcms.nl/youtube-responsive/documentation/index.html#styles","style":"primary"},{"icon":"","label":"Démonstration","link":"https://www.cfcms.nl/youtube-responsive/index.html","style":"light"}]}}]},"dateCreate":"2016-05-23T09:56:46.000Z","dateUpdate":"2021-05-13T01:50:56.000Z","author":{"id":"content/authors/fr/nicolas-roehm-bettcher.mdx","heroSection":{"heroTitle":"Nicolas Roehm","heroSubtitle":"Ingénieur logiciel","heroBadge":"","heroColoredWords":"","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Fondateur de French Stack, je conçois des solutions informatiques complètes."}]},{"type":"p","children":[{"type":"text","text":"Développeur full-stack, j'interviens principalement sur des projets frontend avec Angular, React ou Vue."}]},{"type":"p","children":[{"type":"text","text":"Passionné de design, voici quelques-unes de mes "},{"type":"a","url":"https://www.artstation.com/nicolas-roehm","title":"ArtStation - Nicolas Roehm","children":[{"type":"text","text":"conceptions graphiques"}]},{"type":"text","text":"."}]},{"type":"mdxJsxFlowElement","name":"socialLinks","children":[{"type":"text","text":""}],"props":{"links":[{"icon":"gitHub","link":"https://github.com/NicolasRoehm"},{"icon":"stackOverflow","link":"https://stackoverflow.com/users/7462178/nicolas-roehm?tab=profile"},{"icon":"linkedIn","link":"https://fr.linkedin.com/in/nicolas-roehm-bettcher"}]}}]},"heroSubtitleIsInline":true,"heroHasBackground":false,"heroImage":"/images/nicolas-roehm-bettcher.png","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(312deg, #0800ff 0%, #4300ff00 70%)","heroMaxWidth":"","heroMs":"25%","heroTitleMb":"0.5rem","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"#fff0","navbarBorderColor":"","navbarLinkActive":"#6785be","navbarLinkHover":"#6785be"},"imageAlt":"nicolas roehm bettcher","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"Nicolas Roehm, Ingénieur logiciel","metaDescription":"Passionné d'informatique, je conçois des sites web dans leur intégralité : design, developpement, référencement, e-reputation, e-mailling, hébergement","metaTags":"Nicolas Roehm, Ingénieur logiciel, web, mobile, site internet","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2024-12-09T00:38:50.025Z","localeCode":"fr","slug":"nicolas-roehm-bettcher","url":"/fr/nicolas-roehm-bettcher","ogId":"nicolas-roehm-bettcher-fr","ogImagePath":"/og/nicolas-roehm-bettcher-fr.png","type":"Author","title":"Nicolas Roehm-Bettcher","avatar":"/images/nicolas-roehm-avatar.png","lname":"Roehm","fname":"Nicolas","name":"Nicolas Roehm","translations":[{"localeCode":"en","title":"Nicolas Roehm-Bettcher","slug":"nicolas-roehm-bettcher","url":"/en/nicolas-roehm-bettcher"}]},"translations":[{"localeCode":"en","title":"JS Libs #1: Youtube","slug":"javascript-librairies-youtube-like","url":"/en/blog/javascript-librairies-youtube-like"}],"tags":[{"id":"content/tags/fr/jquery.mdx","localeCode":"fr","title":"jQuery","slug":"jquery","url":"/fr/blog/jquery"}]}],"tags":[{"id":"content/tags/fr/angular.mdx","heroSection":{"heroTitle":"Angular","heroSubtitle":"","heroBadge":"","heroColoredWords":"","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Framework d'application Web open source basé sur TypeScript,"}]},{"type":"p","children":[{"type":"text","text":"dirigé par Google et assisté par la communauté."}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/angular.svg","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(140deg, rgba(0,69,145,0.83) 31%, rgb(221,7,49) 100%)","heroMaxWidth":"","heroMs":"","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"angular","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"Angular","metaDescription":"Framework d'application web open-source basé sur TypeScript, dirigé par Google et assisté par la communauté","metaTags":"Angular, Typescript, Material, Bootstrap, framework, frontend","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2024-12-08T21:25:00.079Z","localeCode":"fr","slug":"angular","url":"/fr/blog/angular","ogId":"angular-blog-fr","ogImagePath":"/og/angular-blog-fr.png","type":"Tag","title":"Angular","subdomainKey":"blog","subdomain":"blog","translations":[{"localeCode":"en","title":"Angular","slug":"angular","url":"/en/blog/angular"}]},{"id":"content/tags/fr/ia.mdx","heroSection":{"heroTitle":"IA","heroSubtitle":"","heroBadge":"","heroColoredWords":"","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Agents, modèles de langage et outils qui les relient,"}]},{"type":"p","children":[{"type":"text","text":"mis à l'épreuve sur de vrais projets."}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/site-internet-web-development-agency.png","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(140deg, #2b1a5e 0%, #7c4dff 100%)","heroMaxWidth":"","heroMs":"","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"site internet web development agency","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"Intelligence artificielle","metaDescription":"Agents IA, modèles de langage et outils qui les relient : retours d'expérience pour coder, automatiser et piloter ses projets avec l'IA.","metaTags":"IA, intelligence artificielle, agent IA, LLM, Claude, Gemini, Codex, API","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2026-10-18T19:00:00.000Z","localeCode":"fr","slug":"ia","url":"/fr/blog/ia","ogId":"ia-blog-fr","ogImagePath":"/og/ia-blog-fr.png","type":"Tag","title":"IA","subdomainKey":"blog","subdomain":"blog","translations":[{"localeCode":"en","title":"AI","slug":"ai","url":"/en/blog/ai"}]},{"id":"content/tags/fr/jquery.mdx","heroSection":{"heroTitle":"jQuery","heroSubtitle":"","heroBadge":"","heroColoredWords":"","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"jQuery est une librairie Javascript open-source conçue pour simplifier la traversée et la manipulation du DOM HTML mais aussi la gestion d'évenements, les animations CSS ainsi que les requêtes Ajax"}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/jquery-logo.svg","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(140deg, rgba(0,69,145,0) 31%, rgba(0,174,255,100) 100%)","heroMaxWidth":"860px","heroMs":"","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"jquery logo","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"jQuery","metaDescription":"jQuery est une librairie Javascript open-source conçue pour simplifier la traversée et la manipulation du DOM HTML, la gestion d'évenements, les animations CSS et les requêtes Ajax","metaTags":"jQuery, Javascript, librairie, DOM HTML","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2024-12-08T19:29:58.745Z","localeCode":"fr","slug":"jquery","url":"/fr/blog/jquery","ogId":"jquery-blog-fr","ogImagePath":"/og/jquery-blog-fr.png","type":"Tag","title":"jQuery","subdomainKey":"blog","subdomain":"blog","translations":[{"localeCode":"en","title":"jQuery","slug":"jquery","url":"/en/blog/jquery"}]},{"id":"content/tags/fr/typescript.mdx","heroSection":{"heroTitle":"TypeScript","heroSubtitle":"","heroBadge":"","heroColoredWords":"","heroBreakTitle":"","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Langage open-source typé superset de JavaScript,"}]},{"type":"p","children":[{"type":"text","text":"garantissant robustesse, maintenabilité et architecture logicielle d'excellence."}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/site-internet-web-development-agency.png","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(140deg, #1b3a6b 0%, #3178c6 100%)","heroMaxWidth":"","heroMs":"","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"site internet web development agency","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"TypeScript","metaDescription":"Langage typé superset de JavaScript conçu pour sécuriser, structurer et faire évoluer les applications web modernes.","metaTags":"TypeScript, JavaScript, typage, codebase intelligence, qualité de code","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2026-08-26T09:00:00.000Z","localeCode":"fr","slug":"typescript","url":"/fr/blog/typescript","ogId":"typescript-blog-fr","ogImagePath":"/og/typescript-blog-fr.png","type":"Tag","title":"TypeScript","subdomainKey":"blog","subdomain":"blog","translations":[{"localeCode":"en","title":"TypeScript","slug":"typescript","url":"/en/blog/typescript"}]}],"pages":[0],"curPage":1,"page":{"id":"content/subdomains/fr/blog.mdx","heroSection":{"heroTitle":"Actualités digitales","heroSubtitle":"","heroBadge":"","heroColoredWords":"2","heroBreakTitle":"","heroShape":"shiny","heroGradient":"business-gradient","heroDescription":{"type":"root","children":[{"type":"p","children":[{"type":"text","text":"Explorez les dernières avancées en "},{"type":"text","text":"design web","bold":true},{"type":"text","text":", "},{"type":"text","text":"SEO","bold":true},{"type":"text","text":", "},{"type":"text","text":"marketing digital","bold":true},{"type":"text","text":", "},{"type":"text","text":"développement web","bold":true},{"type":"text","text":" et bien plus."}]},{"type":"p","children":[{"type":"text","text":"Nos articles décryptent les "},{"type":"text","text":"technologies innovantes","bold":true},{"type":"text","text":" et les "},{"type":"text","text":"standards du web","bold":true},{"type":"text","text":" qui façonnent l'"},{"type":"text","text":"avenir du numérique","bold":true},{"type":"text","text":"."}]},{"type":"p","children":[{"type":"text","text":"Restez connecté, suivez-nous sur les "},{"type":"text","text":"réseaux sociaux","bold":true},{"type":"text","text":"."}]}]},"heroSubtitleIsInline":false,"heroHasBackground":false,"heroImage":"/images/blog-news-web.jpg","heroVideoBackground":"","heroStyle":{"heroBg":"linear-gradient(353deg, rgba(255,129,0,0.64) 0%, #0018ffe0 120%)","heroMaxWidth":"","heroMs":"","heroTitleMb":"","heroTitleColor":"","heroContentBg":"","heroContentAlign":"","heroContentBlur":"","heroBlurImage":"","navbarBg":"","navbarBorderColor":"","navbarLinkActive":"","navbarLinkHover":""},"imageAlt":"blog news web","imageWidth":0,"imageHeight":0},"seoSection":{"metaTitle":"Actualité numérique","metaDescription":"Magazine en ligne pour apprendre le Web, trouver des ressources, parcourir les tendances et déguster un café chaud","metaTags":"inspiration web, tutoriels développement web, tendances web","socialImageWidth":0,"socialImageHeight":0},"heroUpdatedAt":"2024-12-12T18:23:51.381Z","localeCode":"fr","slug":"blog","url":"/fr/blog","ogId":"blog-fr","ogImagePath":"/og/blog-fr.png","type":"Subdomain","title":"Blog","subdomainKey":"blog","subdomain":"blog","translations":[{"localeCode":"en","title":"Blog","slug":"blog","url":"/en/blog"}],"canShare":true,"canComment":true,"hasAuthor":true,"tagsInPanel":true,"cardContainer":"col-md-6","cardTemplate":"default"},"global":{"id":"content/global/fr/settings.json","localeCode":"fr","header":{"nav":[{"href":"index","label":"Accueil","icon":"house"},{"href":"blog","label":"Blog","icon":"journal"},{"href":"videos","label":"Vidéos","icon":"play-btn"},{"href":"services","label":"Prestations","icon":"briefcase"},{"href":"references","label":"Références","icon":"award"},{"href":"a-propos","label":"À propos","icon":"person"},{"href":"contact","label":"Contact","icon":"chat"}]},"footer":{"social":[{"website":"x","account":"RoehmNicolas"},{"website":"instagram","account":"roehm.nicolas"},{"website":"facebook","account":"thefrenchstack"},{"website":"youtube","account":"@frenchstack"}],"hasSocial":true,"nav":[{"title":"L'agence","links":[{"href":"references","label":"Références"},{"href":"a-propos","label":"À propos"},{"href":"contact","label":"Contact"}]},{"title":"Prestations","links":[{"href":"services/creation-graphique","label":"Graphisme"},{"href":"services/developpement-web-mobile","label":"Développement"},{"href":"services/marketing-web","label":"Marketing"},{"href":"services/formation-informatique","label":"Formation"}]},{"title":"Blog","links":[{"href":"blog/angular","label":"Angular"},{"href":"blog/jquery","label":"jQuery"}]},{"title":"Vidéos","links":[{"href":"videos/marketing-audiovisuel","label":"Marketing audiovisuel"}]}]},"bottom":{"dateCreate":"2015-12-27T05:55:00.000Z","nav":[{"href":"mentions-legales","label":"Mentions légales"},{"href":"politique-de-confidentialite","label":"Politique de confidentialité"}],"hasLinks":true},"contactInfo":{"contactMethods":[{"id":"email","icon":"envelope","value":"frenchstack@gmail.com"},{"id":"phone","icon":"phone","value":"0651570751"}]}}},"__N_SSG":true}