[{"data":1,"prerenderedAt":1331},["ShallowReactive",2],{"fougere:post.list:{}":3,"docs:\u002Fdocs\u002Fadopt\u002Fhosts":6,"docs-uses":1019,"docs-nav":1193},{"items":4,"hasMore":5},[],false,{"id":7,"title":8,"body":9,"description":1007,"extension":1008,"forms":1009,"kind":1010,"meta":1011,"navigation":311,"path":1012,"seo":1013,"stem":1014,"step":1015,"uses":1016,"__hash__":1018},"docs\u002Fdocs\u002F7.adopt\u002F4.hosts.md","Pick a host",{"type":10,"value":11,"toc":998},"minimark",[12,37,44,49,179,213,233,237,252,375,381,387,390,394,401,407,495,511,522,574,581,586,590,593,703,739,757,761,777,798,801,805,820,828,844,893,964,967,973,977,994],[13,14,15,16,20,21,25,26,29,30,32,33,36],"p",{},"Your fronds run under whichever framework serves your pages — the ",[17,18,19],"strong",{},"host",": Nuxt, Next, TanStack\nStart, React Router, SvelteKit, Express, or any engine that speaks ",[22,23,24],"code",{},"Request",". A Frond does not know which one it runs under, and nothing in ",[22,27,28],{},"fronds\u002F"," imports\none — the five demos serving the same blog under Next, TanStack Start, React Router,\nSvelteKit and Express share a ",[22,31,28],{}," directory that is identical byte for byte.\n(",[22,34,35],{},"demos\u002Fnuxt-blog"," is the flagship and carries more: presenters, collectors, a named\nsurface.)",[13,38,39,40,43],{},"What a host does is hand its requests to one function and, if it renders pages, offer the four\nclient primitives. Everything else — the boot, the validator, the REST table, the form contract —\nlives in ",[22,41,42],{},"@fougere\u002Fapp"," and is the same everywhere.",[45,46,48],"h2",{"id":47},"what-each-host-costs","What each host costs",[50,51,52,68],"table",{},[53,54,55],"thead",{},[56,57,58,62,65],"tr",{},[59,60,61],"th",{},"Host",[59,63,64],{},"Package",[59,66,67],{},"What you write",[69,70,71,88,104,118,130,146,160],"tbody",{},[56,72,73,77,82],{},[74,75,76],"td",{},"Nuxt",[74,78,79],{},[22,80,81],{},"@fougere\u002Fnuxt",[74,83,84,85],{},"one line in ",[22,86,87],{},"nuxt.config",[56,89,90,93,98],{},[74,91,92],{},"Next",[74,94,95],{},[22,96,97],{},"@fougere\u002Fnext",[74,99,100,101],{},"two one-line route files + ",[22,102,103],{},"withFougere()",[56,105,106,109,115],{},[74,107,108],{},"TanStack Start",[74,110,111],{},[112,113,114],"em",{},"none",[74,116,117],{},"two route files + the Vite plugin",[56,119,120,123,127],{},[74,121,122],{},"React Router",[74,124,125],{},[112,126,114],{},[74,128,129],{},"three resource routes + the Vite plugin",[56,131,132,135,139],{},[74,133,134],{},"SvelteKit",[74,136,137],{},[112,138,114],{},[74,140,141,142,145],{},"two ",[22,143,144],{},"+server.ts"," + the Vite plugin",[56,147,148,151,155],{},[74,149,150],{},"Express",[74,152,153],{},[112,154,114],{},[74,156,157],{},[22,158,159],{},"app.use(fougere())",[56,161,162,165,169],{},[74,163,164],{},"Hono, a Worker, any engine",[74,166,167],{},[112,168,114],{},[74,170,171,172],{},"one line — ",[173,174,176],"a",{"href":175},"#any-engine",[22,177,178],{},"answer",[13,180,181,184,185,188,189,188,192,195,196,199,200,205,206,208,209,212],{},[22,182,183],{},"fougere new"," writes these lines into the shell the host's own tool made, so a new app starts from\nwhat ",[22,186,187],{},"create-nuxt",", ",[22,190,191],{},"create-next-app",[22,193,194],{},"create-vite"," or ",[22,197,198],{},"sv create"," writes today — see\n",[173,201,203],{"href":202},"\u002Freference\u002Fcli",[22,204,183],{},". A host finds the fronds on its own — the nearest directory, up from the app, that holds\n",[22,207,28],{}," — so ",[22,210,211],{},"root"," is written only when they sit elsewhere, the same option for every host.",[13,214,215,216,218,219,222,223,225,226,229,230,232],{},"Three hosts need no package of their own, and that is not an accident: they serve\nWeb-standard ",[22,217,24],{},"\u002F",[22,220,221],{},"Response",", so the facades go in unchanged. ",[22,224,97],{}," exists\nbecause Next has ",[22,227,228],{},"next\u002Fheaders"," — one import — and Nuxt's module is larger because an h3\nevent is not a ",[22,231,24],{},".",[45,234,236],{"id":235},"what-an-app-publishes","What an app publishes",[13,238,239,240,243,244,247,248,251],{},"Which protocols are served is a fact about the ",[17,241,242],{},"app",", declared once beside ",[22,245,246],{},"sources:"," and\n",[22,249,250],{},"fronds:",":",[253,254,259],"pre",{"className":255,"code":256,"language":257,"meta":258,"style":258},"language-ts shiki shiki-themes material-theme-lighter fougere-pastel material-theme-palenight","\u002F\u002F fougere.config.ts\nimport '@fougere\u002Fadapter-rest';\nimport '@fougere\u002Fadapter-graphql';\n\nexport default defineFougere({\n  protocols: { rest: {}, graphql: {} },\n});\n","ts","",[22,260,261,270,292,306,313,333,364],{"__ignoreMap":258},[262,263,266],"span",{"class":264,"line":265},"line",1,[262,267,269],{"class":268},"skXKP","\u002F\u002F fougere.config.ts\n",[262,271,273,277,281,285,288],{"class":264,"line":272},2,[262,274,276],{"class":275},"sK6XW","import",[262,278,280],{"class":279},"sDDC1"," '",[262,282,284],{"class":283},"sN-8n","@fougere\u002Fadapter-rest",[262,286,287],{"class":279},"'",[262,289,291],{"class":290},"s15xx",";\n",[262,293,295,297,299,302,304],{"class":264,"line":294},3,[262,296,276],{"class":275},[262,298,280],{"class":279},[262,300,301],{"class":283},"@fougere\u002Fadapter-graphql",[262,303,287],{"class":279},[262,305,291],{"class":290},[262,307,309],{"class":264,"line":308},4,[262,310,312],{"emptyLinePlaceholder":311},true,"\n",[262,314,316,319,322,326,330],{"class":264,"line":315},5,[262,317,318],{"class":275},"export",[262,320,321],{"class":275}," default",[262,323,325],{"class":324},"s4mR9"," defineFougere",[262,327,329],{"class":328},"srlTG","(",[262,331,332],{"class":290},"{\n",[262,334,336,340,342,345,348,350,353,356,358,361],{"class":264,"line":335},6,[262,337,339],{"class":338},"sHtqg","  protocols",[262,341,251],{"class":290},[262,343,344],{"class":290}," {",[262,346,347],{"class":338}," rest",[262,349,251],{"class":290},[262,351,352],{"class":290}," {},",[262,354,355],{"class":338}," graphql",[262,357,251],{"class":290},[262,359,360],{"class":290}," {}",[262,362,363],{"class":290}," },\n",[262,365,367,370,373],{"class":264,"line":366},7,[262,368,369],{"class":290},"}",[262,371,372],{"class":328},")",[262,374,291],{"class":290},[13,376,377,380],{},[22,378,379],{},"graphql: {}"," is the whole GraphQL setup: the schema is built from the entities the\napp already scanned, so there is no builder to construct and no types to register. The import\nmakes the protocol available and the key serves it — an app that imports neither carries no\nschema builder, and naming one it did not import refuses the boot, naming the import.",[13,382,383,384,386],{},"Absent means not served. The facade may be mounted — the route file exists, the\nmiddleware is installed — and it will still decline, because the host does not get to\nmake this decision. ",[22,385,178],{}," reads the declaration itself, so every host inherits one answer\ninstead of each spelling it their own way.",[13,388,389],{},"The call envelope is not listed there: it is the wire the client primitives use, not a\nprojection an app chooses to publish.",[45,391,393],{"id":392},"mounting-the-facades","Mounting the facades",[13,395,396,397,400],{},"Mounting a facade is not the same as publishing an adapter: what you write below puts\nthe facade in place, and ",[22,398,399],{},"protocols:"," decides whether it serves anything.",[13,402,403,406],{},[17,404,405],{},"A Web-standard host"," — Next, TanStack Start, React Router, SvelteKit — mounts the\nhandlers directly:",[253,408,410],{"className":255,"code":409,"language":257,"meta":258,"style":258},"\u002F\u002F SvelteKit — src\u002Froutes\u002F_fougere\u002Fcall\u002F+server.ts\nimport { fougere } from '@fougere\u002Fapp\u002Fweb';\nexport const POST = ({ request }: { request: Request }) => fougere(request);\n",[22,411,412,417,442],{"__ignoreMap":258},[262,413,414],{"class":264,"line":265},[262,415,416],{"class":268},"\u002F\u002F SvelteKit — src\u002Froutes\u002F_fougere\u002Fcall\u002F+server.ts\n",[262,418,419,421,423,427,430,433,435,438,440],{"class":264,"line":272},[262,420,276],{"class":275},[262,422,344],{"class":290},[262,424,426],{"class":425},"sPEhv"," fougere",[262,428,429],{"class":290}," }",[262,431,432],{"class":275}," from",[262,434,280],{"class":279},[262,436,437],{"class":283},"@fougere\u002Fapp\u002Fweb",[262,439,287],{"class":279},[262,441,291],{"class":290},[262,443,444,446,450,454,457,460,464,467,469,471,473,477,480,484,486,488,491,493],{"class":264,"line":294},[262,445,318],{"class":275},[262,447,449],{"class":448},"s76I7"," const",[262,451,453],{"class":452},"slP7D"," POST",[262,455,456],{"class":290}," =",[262,458,459],{"class":290}," ({",[262,461,463],{"class":462},"shDUQ"," request",[262,465,466],{"class":290}," }:",[262,468,344],{"class":290},[262,470,463],{"class":338},[262,472,251],{"class":290},[262,474,476],{"class":475},"sBZYL"," Request",[262,478,479],{"class":290}," })",[262,481,483],{"class":482},"scTuO"," =>",[262,485,426],{"class":324},[262,487,329],{"class":328},[262,489,490],{"class":425},"request",[262,492,372],{"class":328},[262,494,291],{"class":290},[13,496,497,500,501,503,504,506,507,510],{},[22,498,499],{},"fougere"," takes a ",[22,502,24],{}," and returns a ",[22,505,221],{},", and reads the door off the path, so every\nroute file hands it the same function. The file you create ",[112,508,509],{},"is"," the consent: no file, no facade.",[13,512,513,515,516,195,519,251],{},[17,514,150],{}," adds them as one middleware, like ",[22,517,518],{},"express.json()",[22,520,521],{},"cors()",[253,523,525],{"className":255,"code":524,"language":257,"meta":258,"style":258},"import { fougere } from '@fougere\u002Fapp\u002Fexpress';\n\napp.use(fougere());   \u002F\u002F every door; what each one serves is `protocols:` in fougere.config.ts\n",[22,526,527,548,552],{"__ignoreMap":258},[262,528,529,531,533,535,537,539,541,544,546],{"class":264,"line":265},[262,530,276],{"class":275},[262,532,344],{"class":290},[262,534,426],{"class":425},[262,536,429],{"class":290},[262,538,432],{"class":275},[262,540,280],{"class":279},[262,542,543],{"class":283},"@fougere\u002Fapp\u002Fexpress",[262,545,287],{"class":279},[262,547,291],{"class":290},[262,549,550],{"class":264,"line":272},[262,551,312],{"emptyLinePlaceholder":311},[262,553,554,556,558,561,563,565,568,571],{"class":264,"line":294},[262,555,242],{"class":425},[262,557,232],{"class":290},[262,559,560],{"class":324},"use",[262,562,329],{"class":328},[262,564,499],{"class":324},[262,566,567],{"class":328},"())",[262,569,570],{"class":290},";",[262,572,573],{"class":268},"   \u002F\u002F every door; what each one serves is `protocols:` in fougere.config.ts\n",[13,575,576,577,580],{},"A path Fougere does not serve calls ",[22,578,579],{},"next()",", so an app's own routes keep answering\nwhether they were registered before or after.",[13,582,583,585],{},[17,584,76],{}," mounts them itself — its module has an API for that, and adds the composables\nat the same time.",[45,587,589],{"id":588},"any-engine","Any engine",[13,591,592],{},"Every host above ends in the same function. When you already hold the app, call it yourself:",[253,594,596],{"className":255,"code":595,"language":257,"meta":258,"style":258},"import { answer } from '@fougere\u002Fapp\u002Fanswer';\n\nhono.all('*', async (c) => (await answer(app, c.req.raw)) ?? c.notFound());\n",[22,597,598,620,624],{"__ignoreMap":258},[262,599,600,602,604,607,609,611,613,616,618],{"class":264,"line":265},[262,601,276],{"class":275},[262,603,344],{"class":290},[262,605,606],{"class":425}," answer",[262,608,429],{"class":290},[262,610,432],{"class":275},[262,612,280],{"class":279},[262,614,615],{"class":283},"@fougere\u002Fapp\u002Fanswer",[262,617,287],{"class":279},[262,619,291],{"class":290},[262,621,622],{"class":264,"line":272},[262,623,312],{"emptyLinePlaceholder":311},[262,625,626,629,631,634,636,638,641,643,646,649,652,655,657,659,661,664,666,668,670,672,675,677,681,683,686,689,692,694,696,699,701],{"class":264,"line":294},[262,627,628],{"class":425},"hono",[262,630,232],{"class":290},[262,632,633],{"class":324},"all",[262,635,329],{"class":328},[262,637,287],{"class":279},[262,639,640],{"class":283},"*",[262,642,287],{"class":279},[262,644,645],{"class":290},",",[262,647,648],{"class":448}," async",[262,650,651],{"class":290}," (",[262,653,654],{"class":462},"c",[262,656,372],{"class":290},[262,658,483],{"class":482},[262,660,651],{"class":328},[262,662,663],{"class":275},"await",[262,665,606],{"class":324},[262,667,329],{"class":328},[262,669,242],{"class":425},[262,671,645],{"class":290},[262,673,674],{"class":425}," c",[262,676,232],{"class":290},[262,678,680],{"class":679},"sy9f4","req",[262,682,232],{"class":290},[262,684,685],{"class":679},"raw",[262,687,688],{"class":328},"))",[262,690,691],{"class":290}," ??",[262,693,674],{"class":425},[262,695,232],{"class":290},[262,697,698],{"class":324},"notFound",[262,700,567],{"class":328},[262,702,291],{"class":290},[13,704,705,708,709,712,713,716,717,720,721,724,725,728,729,731,732,735,736,738],{},[22,706,707],{},"answer(app, request)"," reads the door off the path — ",[22,710,711],{},"\u002F_fougere\u002Fcall",", REST under its prefix,\n",[22,714,715],{},"\u002Fgraphql"," (GraphQL over ",[22,718,719],{},"GET"," too, a mutation refused there) — and answers ",[22,722,723],{},"undefined"," when none\nof them is the request's, so the engine's own routes keep answering. It loads no boot, which is\nwhat lets a Worker import it (",[22,726,727],{},"demos\u002Fcloudflare-d1","). There is no router of ours to adapt: the\nengine is one, and its middleware is how you stand around the app — leaving a route out is a\nmiddleware answering before ",[22,730,178],{}," does. ",[22,733,734],{},"fougere(request)"," from ",[22,737,437],{}," is the same\nfunction for a host that has only the request: it boots the app at the first one.",[13,740,741,744,745,748,749,753,754,756],{},[22,742,743],{},"fougere serve"," answers this way too, beside the envelope it serves its peers, and ",[22,746,747],{},"server: { use }","\nin the config stands around that half (",[173,750,752],{"href":751},"\u002Fdocs\u002Fconcepts\u002Fconfiguration#what-stands-around-fougere-serve","config",").\nThe envelope is read off the Node stream rather than through a ",[22,755,24],{},": it is the wire between two\nprocesses, and the same call answered 29 % less the other way.",[45,758,760],{"id":759},"the-client-primitives","The client primitives",[13,762,763,188,766,188,769,772,773,776],{},[22,764,765],{},"useQuery",[22,767,768],{},"useCommand",[22,770,771],{},"useFormFor"," and ",[22,774,775],{},"useCurrentUser"," exist per UI framework, not\nper host:",[778,779,780,787,793],"ul",{},[781,782,783,786],"li",{},[22,784,785],{},"@fougere\u002Freact"," — React, whatever renders it",[781,788,789,792],{},[22,790,791],{},"@fougere\u002Fsvelte"," — Svelte, as stores",[781,794,795,797],{},[22,796,81],{}," — Vue, through Nuxt's own data layer",[13,799,800],{},"The rules they obey are shared: a call names a facade and an operation, and a command on a\nfacade revalidates every mounted query on that facade. Only the state model differs.",[45,802,804],{"id":803},"the-one-thing-every-bundler-must-be-told","The one thing every bundler must be told",[13,806,807,808,811,812,815,816,819],{},"A call through a facade names its address as a literal (",[22,809,810],{},"{ address: 'post' }","), so nothing a\nminifier renames reaches it. What still reads a class name is the form — ",[22,813,814],{},"useFormFor(Post)","\nsubmits to the address named after the entity — and ",[22,817,818],{},"invoke(Post, 'list')"," on the server. A\nminifier renames classes, so a production build would designate an entity nobody hosts:",[253,821,826],{"className":822,"code":824,"language":825},[823],"language-text","Entity 'j' is not hosted here. Hosted here: post.\n","text",[22,827,824],{"__ignoreMap":258},[13,829,830,831,772,833,836,837,840,841,843],{},"You do not have to declare anything for this. ",[22,832,81],{},[22,834,835],{},"@fougere\u002Fvite"," reserve\nthe entity names for you — the first from the scan it just ran, the second by reading\n",[22,838,839],{},"fronds\u002F\u003Cfrond>\u002Fentities\u002F",". On Next, ",[22,842,103],{}," does the same through webpack:",[253,845,847],{"className":255,"code":846,"language":257,"meta":258,"style":258},"\u002F\u002F next.config.ts\nimport { withFougere } from '@fougere\u002Fnext\u002Fconfig';\nexport default withFougere(nextConfig);\n",[22,848,849,854,876],{"__ignoreMap":258},[262,850,851],{"class":264,"line":265},[262,852,853],{"class":268},"\u002F\u002F next.config.ts\n",[262,855,856,858,860,863,865,867,869,872,874],{"class":264,"line":272},[262,857,276],{"class":275},[262,859,344],{"class":290},[262,861,862],{"class":425}," withFougere",[262,864,429],{"class":290},[262,866,432],{"class":275},[262,868,280],{"class":279},[262,870,871],{"class":283},"@fougere\u002Fnext\u002Fconfig",[262,873,287],{"class":279},[262,875,291],{"class":290},[262,877,878,880,882,884,886,889,891],{"class":264,"line":294},[262,879,318],{"class":275},[262,881,321],{"class":275},[262,883,862],{"class":324},[262,885,329],{"class":328},[262,887,888],{"class":425},"nextConfig",[262,890,372],{"class":328},[262,892,291],{"class":290},[253,894,896],{"className":255,"code":895,"language":257,"meta":258,"style":258},"\u002F\u002F vite.config.ts — TanStack Start, React Router, SvelteKit\nimport { fougere } from '@fougere\u002Fvite';\nexport default defineConfig({ plugins: [fougere(), sveltekit()] });\n",[22,897,898,903,923],{"__ignoreMap":258},[262,899,900],{"class":264,"line":265},[262,901,902],{"class":268},"\u002F\u002F vite.config.ts — TanStack Start, React Router, SvelteKit\n",[262,904,905,907,909,911,913,915,917,919,921],{"class":264,"line":272},[262,906,276],{"class":275},[262,908,344],{"class":290},[262,910,426],{"class":425},[262,912,429],{"class":290},[262,914,432],{"class":275},[262,916,280],{"class":279},[262,918,835],{"class":283},[262,920,287],{"class":279},[262,922,291],{"class":290},[262,924,925,927,929,932,934,937,940,942,945,947,950,952,955,958,960,962],{"class":264,"line":294},[262,926,318],{"class":275},[262,928,321],{"class":275},[262,930,931],{"class":324}," defineConfig",[262,933,329],{"class":328},[262,935,936],{"class":290},"{",[262,938,939],{"class":338}," plugins",[262,941,251],{"class":290},[262,943,944],{"class":328}," [",[262,946,499],{"class":324},[262,948,949],{"class":328},"()",[262,951,645],{"class":290},[262,953,954],{"class":324}," sveltekit",[262,956,957],{"class":328},"()]",[262,959,429],{"class":290},[262,961,372],{"class":328},[262,963,291],{"class":290},[13,965,966],{},"Express needs none of this: it runs your sources, nothing is minified.",[968,969,970],"callout",{},[13,971,972],{},"An app that minifies without one of these will build cleanly and fail on the first call.\nThe failure is loud — the server says which entity it does host — but it happens in\nproduction, not at build time.",[45,974,976],{"id":975},"two-hosts-at-once","Two hosts at once",[13,978,979,980,983,984,986,987,993],{},"Nothing stops a frond from being served by more than one host: run it in its own process\nwith ",[22,981,982],{},"serve()"," and let the others reach it through ",[22,985,250],{},". That is the\n",[112,988,989],{},[173,990,992],{"href":991},"\u002Fdocs\u002Fconcepts\u002Fconfiguration","gradient",", and the host is not part of the decision.",[995,996,997],"style",{},"html pre.shiki code .skXKP, html code.shiki .skXKP{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#7D8C80;--shiki-default-font-style:inherit;--shiki-dark:#676E95;--shiki-dark-font-style:italic}html pre.shiki code .sK6XW, html code.shiki .sK6XW{--shiki-light:#39ADB5;--shiki-light-font-style:italic;--shiki-default:#8FCF86;--shiki-default-font-style:inherit;--shiki-dark:#89DDFF;--shiki-dark-font-style:italic}html pre.shiki code .sDDC1, html code.shiki .sDDC1{--shiki-light:#39ADB5;--shiki-default:#EE9F6B;--shiki-dark:#89DDFF}html pre.shiki code .sN-8n, html code.shiki .sN-8n{--shiki-light:#91B859;--shiki-default:#EE9F6B;--shiki-dark:#C3E88D}html pre.shiki code .s15xx, html code.shiki .s15xx{--shiki-light:#39ADB5;--shiki-default:#A3B0A5;--shiki-dark:#89DDFF}html pre.shiki code .s4mR9, html code.shiki .s4mR9{--shiki-light:#6182B8;--shiki-default:#C9B6EA;--shiki-dark:#82AAFF}html pre.shiki code .srlTG, html code.shiki .srlTG{--shiki-light:#90A4AE;--shiki-default:#A3B0A5;--shiki-dark:#BABED8}html pre.shiki code .sHtqg, html code.shiki .sHtqg{--shiki-light:#E53935;--shiki-default:#93CFC0;--shiki-dark:#F07178}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);}html pre.shiki code .sPEhv, html code.shiki .sPEhv{--shiki-light:#90A4AE;--shiki-default:#DDE5DA;--shiki-dark:#BABED8}html pre.shiki code .s76I7, html code.shiki .s76I7{--shiki-light:#9C3EDA;--shiki-default:#8FCF86;--shiki-dark:#C792EA}html pre.shiki code .slP7D, html code.shiki .slP7D{--shiki-light:#90A4AE;--shiki-default:#C9B6EA;--shiki-dark:#BABED8}html pre.shiki code .shDUQ, html code.shiki .shDUQ{--shiki-light:#90A4AE;--shiki-light-font-style:italic;--shiki-default:#DDE5DA;--shiki-default-font-style:inherit;--shiki-dark:#BABED8;--shiki-dark-font-style:italic}html pre.shiki code .sBZYL, html code.shiki .sBZYL{--shiki-light:#E2931D;--shiki-default:#EFCD8F;--shiki-dark:#FFCB6B}html pre.shiki code .scTuO, html code.shiki .scTuO{--shiki-light:#9C3EDA;--shiki-default:#A3B0A5;--shiki-dark:#C792EA}html pre.shiki code .sy9f4, html code.shiki .sy9f4{--shiki-light:#90A4AE;--shiki-default:#93CFC0;--shiki-dark:#BABED8}",{"title":258,"searchDepth":272,"depth":272,"links":999},[1000,1001,1002,1003,1004,1005,1006],{"id":47,"depth":272,"text":48},{"id":235,"depth":272,"text":236},{"id":392,"depth":272,"text":393},{"id":588,"depth":272,"text":589},{"id":759,"depth":272,"text":760},{"id":803,"depth":272,"text":804},{"id":975,"depth":272,"text":976},"The same fronds under Nuxt, Next, SvelteKit, React Router or Express.","md",[707],"task",{},"\u002Fdocs\u002Fadopt\u002Fhosts",{"title":8,"description":1007},"docs\u002F7.adopt\u002F4.hosts",null,[1017],"configuration","tsWbivLQQLuLtquLELXn8o8CTpFRtJ2WS70eYZhrS0w",[1020,1023,1026,1029,1032,1035,1038,1041,1043,1049,1054,1059,1063,1067,1071,1075,1079,1084,1088,1092,1097,1101,1106,1110,1114,1118,1122,1126,1130,1134,1138,1142,1146,1150,1152,1156,1160,1163,1166,1169,1172,1175,1178,1181,1184,1187,1190],{"path":1021,"title":1022,"uses":1015},"\u002Fdocs\u002Fconcepts\u002Fentity","Entity",{"path":1024,"title":1025,"uses":1015},"\u002Fdocs\u002Fconcepts\u002Fhandler","Handler",{"path":1027,"title":1028,"uses":1015},"\u002Fdocs\u002Fconcepts\u002Frepository","Repository",{"path":1030,"title":1031,"uses":1015},"\u002Fdocs\u002Fconcepts\u002Ffrond","Frond",{"path":1033,"title":1034,"uses":1015},"\u002Fdocs\u002Fconcepts\u002Ffacade","Facade",{"path":1036,"title":1037,"uses":1015},"\u002Fdocs\u002Fconcepts\u002Ffact","Fact",{"path":1039,"title":1040,"uses":1015},"\u002Fdocs\u002Fconcepts\u002Fport","Port",{"path":991,"title":1042,"uses":1015},"Configuration",{"path":1044,"title":1045,"uses":1046},"\u002Fdocs\u002Faccess\u002Fauthentication","Authentication",[1047,1048],"port","frond",{"path":1050,"title":1051,"uses":1052},"\u002Fdocs\u002Faccess\u002Fstate","Keep a caller's state",[1017,1053],"handler",{"path":1055,"title":1056,"uses":1057},"\u002Fdocs\u002Fdata\u002Fsql","SQLite or Postgres",[1058,1017],"entity",{"path":1060,"title":1061,"uses":1062},"\u002Fdocs\u002Fdata\u002Fseveral-databases","Several databases",[1017,1058],{"path":1064,"title":1065,"uses":1066},"\u002Fdocs\u002Fdata\u002Fcomputed-field","A computed field",[1058,1047],{"path":1068,"title":1069,"uses":1070},"\u002Fdocs\u002Fdata\u002Fevolve","Evolve a schema",[1058],{"path":1072,"title":1073,"uses":1074},"\u002Fdocs\u002Fdata\u002Fseeds","Seed data",[1058],{"path":1076,"title":1077,"uses":1078},"\u002Fdocs\u002Fdata\u002Fvalues","Read settings and secrets",[1058,1017],{"path":1080,"title":1081,"uses":1082},"\u002Fdocs\u002Fdata\u002Fmirror","Mirror a source you cannot query",[1083],"repository",{"path":1085,"title":1086,"uses":1087},"\u002Fdocs\u002Fdata\u002Ftogether","Two writes as one",[1083],{"path":1089,"title":1090,"uses":1091},"\u002Fdocs\u002Fbehaviour\u002Faround-every-call","Around every call",[1047,1048],{"path":1093,"title":1094,"uses":1095},"\u002Fdocs\u002Fbehaviour\u002Ffinish-a-fact","Finish a fact",[1096],"fact",{"path":1098,"title":1099,"uses":1100},"\u002Fdocs\u002Fserve\u002Frest-graphql","REST, OpenAPI, GraphQL",[1053,1017],{"path":1102,"title":1103,"uses":1104},"\u002Fdocs\u002Fserve\u002Fpages","Pages: queries and commands",[1053,1105],"facade",{"path":1107,"title":1108,"uses":1109},"\u002Fdocs\u002Fserve\u002Fforms","A form",[1058],{"path":1111,"title":1112,"uses":1113},"\u002Fdocs\u002Fserve\u002Fadmin","An admin panel",[1053],{"path":1115,"title":1116,"uses":1117},"\u002Fdocs\u002Frun\u002Fdeploy","Deploy a split",[1017,1048],{"path":1119,"title":1120,"uses":1121},"\u002Fdocs\u002Frun\u002Fsecure","Secure calls between processes",[1017,1048],{"path":1123,"title":1124,"uses":1125},"\u002Fdocs\u002Frun\u002Flifecycle","Reload and shut down",[1017],{"path":1127,"title":1128,"uses":1129},"\u002Fdocs\u002Frun\u002Fobserve","Observe",[1017,1053],{"path":1131,"title":1132,"uses":1133},"\u002Fdocs\u002Frun\u002Fdev-panel","The dev panel",[1053],{"path":1135,"title":1136,"uses":1137},"\u002Fdocs\u002Frun\u002Ftest","Test",[1058,1047],{"path":1139,"title":1140,"uses":1141},"\u002Fdocs\u002Fadopt\u002Fnew-project","Start a project",[1048,1017],{"path":1143,"title":1144,"uses":1145},"\u002Fdocs\u002Fadopt\u002Fexisting-app","Add Fougere to an existing app",[1048,1017],{"path":1147,"title":1148,"uses":1149},"\u002Fdocs\u002Fadopt\u002Fbring-your-schema","Bring your schema",[1058],{"path":1012,"title":8,"uses":1151},[1017],{"path":1153,"title":1154,"uses":1155},"\u002Fdocs\u002Fadopt\u002Fanother-repository","A frond from another repository",[1105,1048],{"path":1157,"title":1158,"uses":1159},"\u002Fdocs\u002Fadopt\u002Fdemos","Demos",[],{"path":1161,"title":1162,"uses":1015},"\u002Fdocs\u002Fextending\u002Fscan","How the scan reads a project",{"path":1164,"title":1165,"uses":1015},"\u002Fdocs\u002Fextending\u002Fwithout-compiler","Boot without the compiler",{"path":1167,"title":1168,"uses":1015},"\u002Fdocs\u002Fextending\u002Fboot","The boot, step by step",{"path":1170,"title":1171,"uses":1015},"\u002Fdocs\u002Fextending\u002Fcard-and-wire","The card and the wire",{"path":1173,"title":1174,"uses":1015},"\u002Fdocs\u002Fextending\u002Fextension-points","Registries and extension points",{"path":1176,"title":1177,"uses":1015},"\u002Fdocs\u002Fextending\u002Fvocabulary","Teach a word",{"path":1179,"title":1180,"uses":1015},"\u002Fdocs\u002Fextending\u002Fextensions","Run code at boot and shutdown",{"path":1182,"title":1183,"uses":1015},"\u002Fdocs\u002Fextending\u002Fsource-adapter","Write a source adapter",{"path":1185,"title":1186,"uses":1015},"\u002Fdocs\u002Fextending\u002Fsurface","Write a surface",{"path":1188,"title":1189,"uses":1015},"\u002Fdocs\u002Fextending\u002Fforeign-frond","A frond in another language",{"path":1191,"title":1192,"uses":1015},"\u002Fdocs","What is Fougere",[1194],{"title":1195,"path":1191,"stem":1196,"children":1197,"page":-1},"Docs","docs",[1198,1200,1221,1230,1251,1260,1273,1290,1306],{"title":1192,"path":1191,"stem":1199},"docs\u002Findex",{"title":1201,"path":1202,"stem":1203,"children":1204,"page":5},"Concepts","\u002Fdocs\u002Fconcepts","docs\u002F1.concepts",[1205,1207,1209,1211,1213,1215,1217,1219],{"title":1022,"path":1021,"stem":1206},"docs\u002F1.concepts\u002F1.entity",{"title":1025,"path":1024,"stem":1208},"docs\u002F1.concepts\u002F2.handler",{"title":1028,"path":1027,"stem":1210},"docs\u002F1.concepts\u002F3.repository",{"title":1031,"path":1030,"stem":1212},"docs\u002F1.concepts\u002F4.frond",{"title":1034,"path":1033,"stem":1214},"docs\u002F1.concepts\u002F5.facade",{"title":1037,"path":1036,"stem":1216},"docs\u002F1.concepts\u002F6.fact",{"title":1040,"path":1039,"stem":1218},"docs\u002F1.concepts\u002F7.port",{"title":1042,"path":991,"stem":1220},"docs\u002F1.concepts\u002F8.configuration",{"title":1222,"path":1223,"stem":1224,"children":1225,"page":5},"Access","\u002Fdocs\u002Faccess","docs\u002F2.access",[1226,1228],{"title":1045,"path":1044,"stem":1227},"docs\u002F2.access\u002F1.authentication",{"title":1051,"path":1050,"stem":1229},"docs\u002F2.access\u002F2.state",{"title":1231,"path":1232,"stem":1233,"children":1234,"page":5},"Data","\u002Fdocs\u002Fdata","docs\u002F3.data",[1235,1237,1239,1241,1243,1245,1247,1249],{"title":1056,"path":1055,"stem":1236},"docs\u002F3.data\u002F1.sql",{"title":1061,"path":1060,"stem":1238},"docs\u002F3.data\u002F2.several-databases",{"title":1065,"path":1064,"stem":1240},"docs\u002F3.data\u002F3.computed-field",{"title":1069,"path":1068,"stem":1242},"docs\u002F3.data\u002F4.evolve",{"title":1073,"path":1072,"stem":1244},"docs\u002F3.data\u002F5.seeds",{"title":1077,"path":1076,"stem":1246},"docs\u002F3.data\u002F6.values",{"title":1081,"path":1080,"stem":1248},"docs\u002F3.data\u002F7.mirror",{"title":1086,"path":1085,"stem":1250},"docs\u002F3.data\u002F8.together",{"title":1252,"path":1253,"stem":1254,"children":1255,"page":5},"Behaviour","\u002Fdocs\u002Fbehaviour","docs\u002F4.behaviour",[1256,1258],{"title":1090,"path":1089,"stem":1257},"docs\u002F4.behaviour\u002F1.around-every-call",{"title":1094,"path":1093,"stem":1259},"docs\u002F4.behaviour\u002F2.finish-a-fact",{"title":1261,"path":1262,"stem":1263,"children":1264,"page":5},"Serve","\u002Fdocs\u002Fserve","docs\u002F5.serve",[1265,1267,1269,1271],{"title":1099,"path":1098,"stem":1266},"docs\u002F5.serve\u002F1.rest-graphql",{"title":1103,"path":1102,"stem":1268},"docs\u002F5.serve\u002F2.pages",{"title":1108,"path":1107,"stem":1270},"docs\u002F5.serve\u002F3.forms",{"title":1112,"path":1111,"stem":1272},"docs\u002F5.serve\u002F4.admin",{"title":1274,"path":1275,"stem":1276,"children":1277,"page":5},"Run","\u002Fdocs\u002Frun","docs\u002F6.run",[1278,1280,1282,1284,1286,1288],{"title":1116,"path":1115,"stem":1279},"docs\u002F6.run\u002F1.deploy",{"title":1120,"path":1119,"stem":1281},"docs\u002F6.run\u002F2.secure",{"title":1124,"path":1123,"stem":1283},"docs\u002F6.run\u002F3.lifecycle",{"title":1128,"path":1127,"stem":1285},"docs\u002F6.run\u002F4.observe",{"title":1132,"path":1131,"stem":1287},"docs\u002F6.run\u002F5.dev-panel",{"title":1136,"path":1135,"stem":1289},"docs\u002F6.run\u002F6.test",{"title":1291,"path":1292,"stem":1293,"children":1294,"page":5},"Adopt","\u002Fdocs\u002Fadopt","docs\u002F7.adopt",[1295,1297,1299,1301,1302,1304],{"title":1140,"path":1139,"stem":1296},"docs\u002F7.adopt\u002F1.new-project",{"title":1144,"path":1143,"stem":1298},"docs\u002F7.adopt\u002F2.existing-app",{"title":1148,"path":1147,"stem":1300},"docs\u002F7.adopt\u002F3.bring-your-schema",{"title":8,"path":1012,"stem":1014},{"title":1154,"path":1153,"stem":1303},"docs\u002F7.adopt\u002F5.another-repository",{"title":1158,"path":1157,"stem":1305},"docs\u002F7.adopt\u002F6.demos",{"title":1307,"path":1308,"stem":1309,"children":1310,"page":5},"Extending","\u002Fdocs\u002Fextending","docs\u002F8.extending",[1311,1313,1315,1317,1319,1321,1323,1325,1327,1329],{"title":1162,"path":1161,"stem":1312},"docs\u002F8.extending\u002F1.scan",{"title":1165,"path":1164,"stem":1314},"docs\u002F8.extending\u002F10.without-compiler",{"title":1168,"path":1167,"stem":1316},"docs\u002F8.extending\u002F2.boot",{"title":1171,"path":1170,"stem":1318},"docs\u002F8.extending\u002F3.card-and-wire",{"title":1174,"path":1173,"stem":1320},"docs\u002F8.extending\u002F4.extension-points",{"title":1177,"path":1176,"stem":1322},"docs\u002F8.extending\u002F5.vocabulary",{"title":1180,"path":1179,"stem":1324},"docs\u002F8.extending\u002F6.extensions",{"title":1183,"path":1182,"stem":1326},"docs\u002F8.extending\u002F7.source-adapter",{"title":1186,"path":1185,"stem":1328},"docs\u002F8.extending\u002F8.surface",{"title":1189,"path":1188,"stem":1330},"docs\u002F8.extending\u002F9.foreign-frond",1794396615053]