[{"data":1,"prerenderedAt":657},["ShallowReactive",2],{"docs-nav:fr":3,"docs:\u002Ffr\u002Fdocs\u002Fexisting-app":189},[4],{"title":5,"path":6,"stem":7,"children":8,"page":52},"Fr","\u002Ffr","fr",[9],{"title":10,"path":11,"stem":12,"children":13,"page":-1},"Qu'est-ce que Fougere","\u002Ffr\u002Fdocs","fr\u002Fdocs\u002Findex",[14,15,19,23,27,31,53,78,123,148],{"title":10,"path":11,"stem":12},{"title":16,"path":17,"stem":18},"Démarrer","\u002Ffr\u002Fdocs\u002Fgetting-started","fr\u002Fdocs\u002F01.getting-started",{"title":20,"path":21,"stem":22},"Une app que vous avez déjà","\u002Ffr\u002Fdocs\u002Fexisting-app","fr\u002Fdocs\u002F02.existing-app",{"title":24,"path":25,"stem":26},"Apportez votre schéma","\u002Ffr\u002Fdocs\u002Fbring-your-schema","fr\u002Fdocs\u002F03.bring-your-schema",{"title":28,"path":29,"stem":30},"La CLI","\u002Ffr\u002Fdocs\u002Fcli","fr\u002Fdocs\u002F04.cli",{"title":32,"path":33,"stem":34,"children":35,"page":52},"Concepts","\u002Ffr\u002Fdocs\u002Fconcepts","fr\u002Fdocs\u002F2.concepts",[36,40,44,48],{"title":37,"path":38,"stem":39},"Philosophie","\u002Ffr\u002Fdocs\u002Fconcepts\u002Fphilosophy","fr\u002Fdocs\u002F2.concepts\u002F1.philosophy",{"title":41,"path":42,"stem":43},"La Frond","\u002Ffr\u002Fdocs\u002Fconcepts\u002Ffrond","fr\u002Fdocs\u002F2.concepts\u002F2.frond",{"title":45,"path":46,"stem":47},"Le chemin le plus court","\u002Ffr\u002Fdocs\u002Fconcepts\u002Fshortest-path","fr\u002Fdocs\u002F2.concepts\u002F3.shortest-path",{"title":49,"path":50,"stem":51},"Le socle","\u002Ffr\u002Fdocs\u002Fconcepts\u002Fthe-base","fr\u002Fdocs\u002F2.concepts\u002F4.the-base",false,{"title":54,"path":55,"stem":56,"children":57,"page":52},"Schéma","\u002Ffr\u002Fdocs\u002Fschema","fr\u002Fdocs\u002F3.schema",[58,62,66,70,74],{"title":59,"path":60,"stem":61},"Entités","\u002Ffr\u002Fdocs\u002Fschema\u002Fentities","fr\u002Fdocs\u002F3.schema\u002F1.entities",{"title":63,"path":64,"stem":65},"Vues","\u002Ffr\u002Fdocs\u002Fschema\u002Fviews","fr\u002Fdocs\u002F3.schema\u002F2.views",{"title":67,"path":68,"stem":69},"La carte d'identité","\u002Ffr\u002Fdocs\u002Fschema\u002Fcard","fr\u002Fdocs\u002F3.schema\u002F3.card",{"title":71,"path":72,"stem":73},"Standard Schema","\u002Ffr\u002Fdocs\u002Fschema\u002Fstandard-schema","fr\u002Fdocs\u002F3.schema\u002F4.standard-schema",{"title":75,"path":76,"stem":77},"Comment un schéma bouge","\u002Ffr\u002Fdocs\u002Fschema\u002Fevolution","fr\u002Fdocs\u002F3.schema\u002F5.evolution",{"title":79,"path":80,"stem":81,"children":82,"page":52},"Métier","\u002Ffr\u002Fdocs\u002Fbusiness","fr\u002Fdocs\u002F4.business",[83,87,91,95,99,103,107,111,115,119],{"title":84,"path":85,"stem":86},"Handlers","\u002Ffr\u002Fdocs\u002Fbusiness\u002Fhandlers","fr\u002Fdocs\u002F4.business\u002F1.handlers",{"title":88,"path":89,"stem":90},"Les ports","\u002Ffr\u002Fdocs\u002Fbusiness\u002Fports","fr\u002Fdocs\u002F4.business\u002F10.ports",{"title":92,"path":93,"stem":94},"Presenters","\u002Ffr\u002Fdocs\u002Fbusiness\u002Fpresenters","fr\u002Fdocs\u002F4.business\u002F2.presenters",{"title":96,"path":97,"stem":98},"Collectors","\u002Ffr\u002Fdocs\u002Fbusiness\u002Fcollectors","fr\u002Fdocs\u002F4.business\u002F3.collectors",{"title":100,"path":101,"stem":102},"Erreurs","\u002Ffr\u002Fdocs\u002Fbusiness\u002Ferrors","fr\u002Fdocs\u002F4.business\u002F4.errors",{"title":104,"path":105,"stem":106},"Seeds","\u002Ffr\u002Fdocs\u002Fbusiness\u002Fseeds","fr\u002Fdocs\u002F4.business\u002F5.seeds",{"title":108,"path":109,"stem":110},"Les faits","\u002Ffr\u002Fdocs\u002Fbusiness\u002Ffacts","fr\u002Fdocs\u002F4.business\u002F6.facts",{"title":112,"path":113,"stem":114},"Le port Storage","\u002Ffr\u002Fdocs\u002Fbusiness\u002Fstorage","fr\u002Fdocs\u002F4.business\u002F7.storage",{"title":116,"path":117,"stem":118},"Des écritures qui tiennent ou tombent ensemble","\u002Ffr\u002Fdocs\u002Fbusiness\u002Ftogether","fr\u002Fdocs\u002F4.business\u002F8.together",{"title":120,"path":121,"stem":122},"Les repositories","\u002Ffr\u002Fdocs\u002Fbusiness\u002Frepositories","fr\u002Fdocs\u002F4.business\u002F9.repositories",{"title":124,"path":125,"stem":126,"children":127,"page":52},"Client","\u002Ffr\u002Fdocs\u002Fclient","fr\u002Fdocs\u002F5.client",[128,132,136,140,144],{"title":129,"path":130,"stem":131},"Queries & commands","\u002Ffr\u002Fdocs\u002Fclient\u002Fqueries-commands","fr\u002Fdocs\u002F5.client\u002F1.queries-commands",{"title":133,"path":134,"stem":135},"Formulaires","\u002Ffr\u002Fdocs\u002Fclient\u002Fforms","fr\u002Fdocs\u002F5.client\u002F2.forms",{"title":137,"path":138,"stem":139},"Session","\u002Ffr\u002Fdocs\u002Fclient\u002Fsession","fr\u002Fdocs\u002F5.client\u002F3.session",{"title":141,"path":142,"stem":143},"invoke","\u002Ffr\u002Fdocs\u002Fclient\u002Finvoke","fr\u002Fdocs\u002F5.client\u002F4.invoke",{"title":145,"path":146,"stem":147},"Back-office","\u002Ffr\u002Fdocs\u002Fclient\u002Fadmin","fr\u002Fdocs\u002F5.client\u002F5.admin",{"title":149,"path":150,"stem":151,"children":152,"page":52},"Infrastructure","\u002Ffr\u002Fdocs\u002Finfra","fr\u002Fdocs\u002F6.infra",[153,157,161,165,169,173,177,181,185],{"title":154,"path":155,"stem":156},"Le gradient","\u002Ffr\u002Fdocs\u002Finfra\u002Fgradient","fr\u002Fdocs\u002F6.infra\u002F1.gradient",{"title":158,"path":159,"stem":160},"Surfaces — REST & GraphQL","\u002Ffr\u002Fdocs\u002Finfra\u002Fsurfaces","fr\u002Fdocs\u002F6.infra\u002F2.surfaces",{"title":162,"path":163,"stem":164},"Déploiement","\u002Ffr\u002Fdocs\u002Finfra\u002Fdeployment","fr\u002Fdocs\u002F6.infra\u002F3.deployment",{"title":166,"path":167,"stem":168},"Hôtes","\u002Ffr\u002Fdocs\u002Finfra\u002Fhosts","fr\u002Fdocs\u002F6.infra\u002F4.hosts",{"title":170,"path":171,"stem":172},"Les sources","\u002Ffr\u002Fdocs\u002Finfra\u002Fsources","fr\u002Fdocs\u002F6.infra\u002F5.sources",{"title":174,"path":175,"stem":176},"Le cycle de vie","\u002Ffr\u002Fdocs\u002Finfra\u002Flifecycle","fr\u002Fdocs\u002F6.infra\u002F6.lifecycle",{"title":178,"path":179,"stem":180},"L'identité entre Fronds","\u002Ffr\u002Fdocs\u002Finfra\u002Fidentity","fr\u002Fdocs\u002F6.infra\u002F7.identity",{"title":182,"path":183,"stem":184},"Observabilité","\u002Ffr\u002Fdocs\u002Finfra\u002Fobservability","fr\u002Fdocs\u002F6.infra\u002F8.observability",{"title":186,"path":187,"stem":188},"Tests","\u002Ffr\u002Fdocs\u002Finfra\u002Ftesting","fr\u002Fdocs\u002F6.infra\u002F9.testing",{"id":190,"title":20,"body":191,"description":652,"extension":653,"meta":654,"navigation":369,"path":21,"seo":655,"stem":22,"__hash__":656},"docs_fr\u002Ffr\u002Fdocs\u002F02.existing-app.md",{"type":192,"value":193,"toc":645},"minimark",[194,199,221,226,237,319,334,431,437,445,469,480,484,487,570,573,577,607,611,623,629,633,641],[195,196,198],"h1",{"id":197},"ajouter-fougere-à-une-app-que-vous-avez-déjà","Ajouter Fougere à une app que vous avez déjà",[200,201,202,203,207,208,211,212,216,217,220],"p",{},"Fougere ajoute sa couche modèle à l'app que vous faites déjà tourner. Le routing, les pages, les composants,\nle style et les routes serveur restent en place. Le module enregistre uniquement ses\npropres chemins : ",[204,205,206],"code",{},"\u002F_fougere\u002Fcall","\n(l'enveloppe), ",[204,209,210],{},"\u002Fapi\u002F{frond}\u002F…"," (",[213,214,215],"a",{"href":159},"surface REST",") et ",[204,218,219],{},"\u002Fauth\u002F**","\nsi vous activez l'auth.",[222,223,225],"h2",{"id":224},"les-trois-pièces","Les trois pièces",[200,227,228,232,233,236],{},[229,230,231],"strong",{},"1. Le module"," — dans votre ",[204,234,235],{},"nuxt.config.ts"," existant :",[238,239,244],"pre",{"className":240,"code":241,"language":242,"meta":243,"style":243},"language-ts shiki shiki-themes material-theme-lighter github-light github-dark","export default defineNuxtConfig({\n  modules: [\u002F* vos modules *\u002F, '@fougere\u002Fnuxt'],\n});\n","ts","",[204,245,246,270,307],{"__ignoreMap":243},[247,248,251,255,258,262,266],"span",{"class":249,"line":250},"line",1,[247,252,254],{"class":253},"sVHd0","export",[247,256,257],{"class":253}," default",[247,259,261],{"class":260},"sGLFI"," defineNuxtConfig",[247,263,265],{"class":264},"su5hD","(",[247,267,269],{"class":268},"sP7_E","{\n",[247,271,273,277,280,283,287,290,294,298,301,304],{"class":249,"line":272},2,[247,274,276],{"class":275},"skxfh","  modules",[247,278,279],{"class":268},":",[247,281,282],{"class":264}," [",[247,284,286],{"class":285},"sutJx","\u002F* vos modules *\u002F",[247,288,289],{"class":268},",",[247,291,293],{"class":292},"sjJ54"," '",[247,295,297],{"class":296},"s_sjI","@fougere\u002Fnuxt",[247,299,300],{"class":292},"'",[247,302,303],{"class":264},"]",[247,305,306],{"class":268},",\n",[247,308,310,313,316],{"class":249,"line":309},3,[247,311,312],{"class":268},"}",[247,314,315],{"class":264},")",[247,317,318],{"class":268},";\n",[200,320,321,324,325,328,329,333],{},[229,322,323],{},"2. La config"," — ",[204,326,327],{},"fougere.config.ts"," à la racine\n(",[213,330,332],{"href":331},"\u002Ffr\u002Fdocs\u002Fgetting-started#fougereconfigts--r%C3%A9f%C3%A9rence","référence complète",") :",[238,335,337],{"className":240,"code":336,"language":242,"meta":243,"style":243},"import { defineFougere } from '@fougere\u002Fcore';\n\nexport default defineFougere({\n  db: { dialect: 'sqlite', path: '.data\u002Fapp.db' },\n});\n",[204,338,339,365,371,383,422],{"__ignoreMap":243},[247,340,341,344,347,350,353,356,358,361,363],{"class":249,"line":250},[247,342,343],{"class":253},"import",[247,345,346],{"class":268}," {",[247,348,349],{"class":264}," defineFougere",[247,351,352],{"class":268}," }",[247,354,355],{"class":253}," from",[247,357,293],{"class":292},[247,359,360],{"class":296},"@fougere\u002Fcore",[247,362,300],{"class":292},[247,364,318],{"class":268},[247,366,367],{"class":249,"line":272},[247,368,370],{"emptyLinePlaceholder":369},true,"\n",[247,372,373,375,377,379,381],{"class":249,"line":309},[247,374,254],{"class":253},[247,376,257],{"class":253},[247,378,349],{"class":260},[247,380,265],{"class":264},[247,382,269],{"class":268},[247,384,386,389,391,393,396,398,400,403,405,407,410,412,414,417,419],{"class":249,"line":385},4,[247,387,388],{"class":275},"  db",[247,390,279],{"class":268},[247,392,346],{"class":268},[247,394,395],{"class":275}," dialect",[247,397,279],{"class":268},[247,399,293],{"class":292},[247,401,402],{"class":296},"sqlite",[247,404,300],{"class":292},[247,406,289],{"class":268},[247,408,409],{"class":275}," path",[247,411,279],{"class":268},[247,413,293],{"class":292},[247,415,416],{"class":296},".data\u002Fapp.db",[247,418,300],{"class":292},[247,420,421],{"class":268}," },\n",[247,423,425,427,429],{"class":249,"line":424},5,[247,426,312],{"class":268},[247,428,315],{"class":264},[247,430,318],{"class":268},[200,432,433,436],{},[229,434,435],{},"3. Une première Frond"," — une entité et un handler, à la racine de l'app que vous avez\ndéjà :",[238,438,443],{"className":439,"code":441,"language":442},[440],"language-text","entities\u002FTodo.ts\nhandlers\u002FTodoHandler.ts\n","text",[204,444,441],{"__ignoreMap":243},[200,446,447,448,452,453,456,457,460,461,464,465,468],{},"Le scanner reconnaît ces deux fichiers grâce à la convention utilisée à la racine du\nprojet (",[213,449,451],{"href":450},"\u002Ffr\u002Fdocs\u002Fgetting-started#un-seul-domaine-pas-de-fronds-du-tout","la forme à plat",").\nUne page écrit\n",[204,454,455],{},"import Todo from '@fronds\u002F\u003Cnom-de-votre-paquet>\u002Fentities\u002FTodo'"," — le module enregistre cet\nalias depuis le scan, donc il n'y a ni ",[204,458,459],{},"package.json"," ni entrée ",[204,462,463],{},"pnpm-workspace.yaml"," à\najouter. Un deuxième domaine ira plus tard dans ",[204,466,467],{},"fronds\u002Fbilling\u002F",", et ces deux fichiers ne\nbougent pas.",[200,470,471,472,475,476,479],{},"Lancez ",[204,473,474],{},"pnpm dev"," et vérifiez le log : ",[204,477,478],{},"scanned 1 frond(s)",".",[222,481,483],{"id":482},"migrer-feature-par-feature","Migrer feature par feature",[200,485,486],{},"Prenez une fonctionnalité à la fois ; les anciennes routes continuent de servir le reste.\nLes éléments suivants ont un équivalent Fougere :",[488,489,490,503],"table",{},[491,492,493],"thead",{},[494,495,496,500],"tr",{},[497,498,499],"th",{},"Ce que vous maintenez aujourd'hui",[497,501,502],{},"Ce que ça devient",[504,505,506,518,526,541,554],"tbody",{},[494,507,508,512],{},[509,510,511],"td",{},"un schéma Zod\u002FYup",[509,513,514,515],{},"les champs de l'entité — ",[213,516,517],{"href":60},"axe shape",[494,519,520,523],{},[509,521,522],{},"une définition de table ou une migration additive",[509,524,525],{},"dérivée — auto-DDL additif depuis les mêmes champs ; les changements destructifs restent explicites",[494,527,528,534],{},[509,529,530,533],{},[204,531,532],{},"server\u002Fapi\u002Ftodos.post.ts"," + appel de validation",[509,535,536,537,540],{},"une opération de ",[213,538,539],{"href":85},"handler",", validée à la façade",[494,542,543,546],{},[509,544,545],{},"l'état du formulaire + règles côté client",[509,547,548,553],{},[213,549,550],{"href":134},[204,551,552],{},"useFormFor(Todo)"," — même validation que le serveur",[494,555,556,562],{},[509,557,558,561],{},[204,559,560],{},"useFetch('\u002Fapi\u002Ftodos')"," + comptabilité de refresh",[509,563,564,569],{},[213,565,566],{"href":130},[204,567,568],{},"useQuery(Todo, 'list')"," — revalidée par les commands",[200,571,572],{},"Supprimez les originaux à chaque feature migrée — le but est d'avoir moins de fichiers à\nsynchroniser, pas une copie parallèle.",[222,574,576],{"id":575},"ce-qui-reste-à-vous","Ce qui reste à vous",[578,579,580,587,593],"ul",{},[581,582,583,586],"li",{},[229,584,585],{},"Pages et composants"," — les primitives sont additives ; pas de layout, pas de widgets.",[581,588,589,592],{},[229,590,591],{},"Les autres routes serveur"," — tout ce qui est hors des chemins revendiqués est intact.",[581,594,595,598,599,602,603,606],{},[229,596,597],{},"L'auth"," — optionnelle. Gardez votre système si vous en avez un ; ",[204,600,601],{},"useCurrentUser"," et\nle flux session→handler demandent l'",[213,604,605],{"href":138},"auth Fougere"," activée.",[222,608,610],{"id":609},"limites-actuelles","Limites actuelles",[578,612,613,620],{},[581,614,615,616,619],{},"Les paquets sont sur npm sous le tag ",[204,617,618],{},"alpha"," — le numéro de version est toute la\npromesse.",[581,621,622],{},"Le storage est SQLite auto-DDL (Kysely dessous). La table d'une entité appartient à\nFougere — migrez une feature quand vous pouvez lui confier son storage, gardez votre\naccès base existant pour le reste.",[200,624,625,626,628],{},"Suite : ",[213,627,24],{"href":25}," — ce que devient un modèle Prisma\nou Drizzle, et la part que vous écrivez pour la première fois.",[222,630,632],{"id":631},"un-autre-hôte","Un autre hôte ?",[200,634,635,636,479],{},"Cette page parle de Nuxt parce que son module fait le montage à votre place. La même Frond\ntourne sous Next, TanStack Start, React Router, SvelteKit et Express — trois d'entre eux\nn'ont besoin d'aucun paquet Fougere. Voir ",[637,638,639],"em",{},[213,640,166],{"href":167},[642,643,644],"style",{},"html pre.shiki code .sVHd0, html code.shiki .sVHd0{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#D73A49;--shiki-default-font-style:inherit;--shiki-dark:#F97583;--shiki-dark-font-style:inherit}html pre.shiki code .sGLFI, html code.shiki .sGLFI{--shiki-light:#6182B8;--shiki-default:#6F42C1;--shiki-dark:#B392F0}html pre.shiki code .su5hD, html code.shiki .su5hD{--shiki-light:#90A4AE;--shiki-default:#24292E;--shiki-dark:#E1E4E8}html pre.shiki code .sP7_E, html code.shiki .sP7_E{--shiki-light:#39ADB5;--shiki-default:#24292E;--shiki-dark:#E1E4E8}html pre.shiki code .skxfh, html code.shiki .skxfh{--shiki-light:#E53935;--shiki-default:#24292E;--shiki-dark:#E1E4E8}html pre.shiki code .sutJx, html code.shiki .sutJx{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#6A737D;--shiki-default-font-style:inherit;--shiki-dark:#6A737D;--shiki-dark-font-style:inherit}html pre.shiki code .sjJ54, html code.shiki .sjJ54{--shiki-light:#39ADB5;--shiki-default:#032F62;--shiki-dark:#9ECBFF}html pre.shiki code .s_sjI, html code.shiki .s_sjI{--shiki-light:#91B859;--shiki-default:#032F62;--shiki-dark:#9ECBFF}html .light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}html.light .shiki span {color: var(--shiki-light);background: var(--shiki-light-bg);font-style: var(--shiki-light-font-style);font-weight: var(--shiki-light-font-weight);text-decoration: var(--shiki-light-text-decoration);}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":243,"searchDepth":272,"depth":272,"links":646},[647,648,649,650,651],{"id":224,"depth":272,"text":225},{"id":482,"depth":272,"text":483},{"id":575,"depth":272,"text":576},{"id":609,"depth":272,"text":610},{"id":631,"depth":272,"text":632},"Ajouter Fougere à une app que vous faites déjà tourner — une feature à la fois, sur n'importe quel hôte.","md",{},{"title":20,"description":652},"PNip8yDIjZFFubcTgRoZDORwZ9R2iS4dSRwuHZsaanM",1788598417581]