[{"data":1,"prerenderedAt":547},["ShallowReactive",2],{"navigation_docs":3,"-advanced-topics-multi-frontend":225,"-advanced-topics-multi-frontend-surround":542},[4,27,77,123,157,211],{"title":5,"icon":6,"path":7,"stem":8,"children":9,"page":26},"Get started","majesticons:rocket-3-start-line","\u002Fget-started","1.get-started",[10,14,18,22],{"title":11,"path":12,"stem":13},"How it works","\u002Fget-started\u002Fhow-it-works","1.get-started\u002F10.how-it-works",{"title":15,"path":16,"stem":17},"Play online","\u002Fget-started\u002Fplay-online","1.get-started\u002F20.play-online",{"title":19,"path":20,"stem":21},"Create a new project","\u002Fget-started\u002Fcreate-new-project","1.get-started\u002F30.create-new-project",{"title":23,"path":24,"stem":25},"First steps","\u002Fget-started\u002Ffirst-steps","1.get-started\u002F40.first-steps",false,{"title":28,"icon":29,"path":30,"stem":31,"children":32,"page":26},"Guide","mdi:book-open-page-variant-outline","\u002Fguide","2.guide",[33,37,41,45,49,53,57,61,65,69,73],{"title":34,"path":35,"stem":36},"Customized API Output","\u002Fguide\u002Fcustomized-api-output","2.guide\u002F05.customized-api-output",{"title":38,"path":39,"stem":40},"Pages & Routing","\u002Fguide\u002Fpages-routing","2.guide\u002F10.pages-routing",{"title":42,"path":43,"stem":44},"Site layout & Menus","\u002Fguide\u002Fsite-layout-menus","2.guide\u002F20.site-layout-menus",{"title":46,"path":47,"stem":48},"Authentication","\u002Fguide\u002Fauthentication","2.guide\u002F40.authentication",{"title":50,"path":51,"stem":52},"Metatags & Local tasks","\u002Fguide\u002Fmetatags-local-tasks","2.guide\u002F50.metatags-local-tasks",{"title":54,"path":55,"stem":56},"Breadcrumbs & Messages","\u002Fguide\u002Fbreadcrumbs-messages","2.guide\u002F60.breadcrumbs-messages",{"title":58,"path":59,"stem":60},"Redirects","\u002Fguide\u002Fredirects","2.guide\u002F65.redirects",{"title":62,"path":63,"stem":64},"Editorial previews","\u002Fguide\u002Feditorial-previews","2.guide\u002F70.editorial-previews",{"title":66,"path":67,"stem":68},"Layout builder","\u002Fguide\u002Flayout-builder","2.guide\u002F80.layout-builder",{"title":70,"path":71,"stem":72},"Drupal Canvas","\u002Fguide\u002Fcanvas","2.guide\u002F90.canvas",{"title":74,"path":75,"stem":76},"Drupal CMS","\u002Fguide\u002Fdrupal-cms","2.guide\u002F95.drupal-cms",{"title":78,"icon":79,"path":80,"stem":81,"children":82,"page":26},"Advanced topics","bi:diagram-3","\u002Fadvanced-topics","3.advanced-topics",[83,87,91,95,99,103,107,111,115,119],{"title":84,"path":85,"stem":86},"Multi-frontend","\u002Fadvanced-topics\u002Fmulti-frontend","3.advanced-topics\u002F05.multi-frontend",{"title":88,"path":89,"stem":90},"Listings, Views","\u002Fadvanced-topics\u002Flistings-views","3.advanced-topics\u002F10.listings-views",{"title":92,"path":93,"stem":94},"Searches","\u002Fadvanced-topics\u002Fsearches","3.advanced-topics\u002F20.searches",{"title":96,"path":97,"stem":98},"JSON-API & GraphQL","\u002Fadvanced-topics\u002Fjsonapi-graphql","3.advanced-topics\u002F30.jsonapi-graphql",{"title":100,"path":101,"stem":102},"Caching","\u002Fadvanced-topics\u002Fcaching","3.advanced-topics\u002F40.caching",{"title":104,"path":105,"stem":106},"Error pages","\u002Fadvanced-topics\u002Ferror-pages","3.advanced-topics\u002F50.error-pages",{"title":108,"path":109,"stem":110},"Drupal forms","\u002Fadvanced-topics\u002Fdrupal-forms","3.advanced-topics\u002F60.drupal-forms",{"title":112,"path":113,"stem":114},"Site Templates","\u002Fadvanced-topics\u002Fsite-templates","3.advanced-topics\u002F65.site-templates",{"title":116,"path":117,"stem":118},"Block layout","\u002Fadvanced-topics\u002Fblock-layout","3.advanced-topics\u002F70.block-layout",{"title":120,"path":121,"stem":122},"Debugging API requests","\u002Fadvanced-topics\u002Fdebugging","3.advanced-topics\u002F80.debugging",{"title":124,"icon":125,"path":126,"stem":127,"children":128,"page":26},"Drupal","simple-icons:drupal","\u002Fdrupal","4.drupal",[129,133,137,141,145,149,153],{"title":130,"path":131,"stem":132},"Key modules","\u002Fdrupal\u002Fkey-modules","4.drupal\u002F10.key-modules",{"title":134,"path":135,"stem":136},"Custom elements","\u002Fdrupal\u002Fcustom-elements","4.drupal\u002F20.custom-elements",{"title":138,"path":139,"stem":140},"Routes","\u002Fdrupal\u002Froutes","4.drupal\u002F30.routes",{"title":142,"path":143,"stem":144},"Providing blocks","\u002Fdrupal\u002Fproviding-blocks","4.drupal\u002F40.providing-blocks",{"title":146,"path":147,"stem":148},"Custom Element Processors","\u002Fdrupal\u002Fcustom-element-processors","4.drupal\u002F50.custom-element-processors",{"title":150,"path":151,"stem":152},"Adding Drupal forms","\u002Fdrupal\u002Fadd-drupal-forms","4.drupal\u002F60.add-drupal-forms",{"title":154,"path":155,"stem":156},"Providing themes","\u002Fdrupal\u002Fthemes","4.drupal\u002F70.themes",{"title":158,"icon":159,"path":160,"stem":161,"children":162,"page":26},"Nuxt","simple-icons:nuxtdotjs","\u002Fnuxt","5.nuxt",[163,167,171,175,179,183,187,191,195,199,203,207],{"title":164,"path":165,"stem":166},"Introduction","\u002Fnuxt\u002Fintroduction","5.nuxt\u002F10.introduction",{"title":168,"path":169,"stem":170},"Setup","\u002Fnuxt\u002Fsetup","5.nuxt\u002F20.setup",{"title":172,"path":173,"stem":174},"Rendering Custom Elements","\u002Fnuxt\u002Frender-custom-elements","5.nuxt\u002F30.render-custom-elements",{"title":176,"path":177,"stem":178},"Default components","\u002Fnuxt\u002Fdefault-components","5.nuxt\u002F32.default-components",{"title":180,"path":181,"stem":182},"Composables","\u002Fnuxt\u002Fcomposables","5.nuxt\u002F35.composables",{"title":184,"path":185,"stem":186},"Custom Routes","\u002Fnuxt\u002Fcustom-routes","5.nuxt\u002F40.custom-routes",{"title":188,"path":189,"stem":190},"Page Layouts","\u002Fnuxt\u002Fpage-layouts","5.nuxt\u002F50.page-layouts",{"title":192,"path":193,"stem":194},"Component Previews","\u002Fnuxt\u002Fcomponent-previews","5.nuxt\u002F55.component-previews",{"title":196,"path":197,"stem":198},"Component Index","\u002Fnuxt\u002Fcanvas-components","5.nuxt\u002F57.canvas-components",{"title":200,"path":201,"stem":202},"Rendering modes","\u002Fnuxt\u002Frendering-modes","5.nuxt\u002F60.rendering-modes",{"title":204,"path":205,"stem":206},"Deployment options","\u002Fnuxt\u002Fdeployment","5.nuxt\u002F70.deployment",{"title":208,"path":209,"stem":210},"Resources","\u002Fnuxt\u002Fresources","5.nuxt\u002F90.resources",{"title":212,"icon":213,"path":214,"stem":215,"children":216,"page":26},"Deployment","solar:server-square-cloud-linear","\u002Fdeployment","6.deployment",[217,221],{"title":218,"path":219,"stem":220},"Deployment Strategies","\u002Fdeployment\u002Fdeployment-strategy","6.deployment\u002F10.deployment-strategy",{"title":222,"path":223,"stem":224},"Unified Hosting","\u002Fdeployment\u002Funified-hosting","6.deployment\u002F20.unified-hosting",{"id":226,"title":84,"body":227,"description":233,"extension":536,"links":537,"meta":538,"navigation":539,"path":85,"seo":540,"stem":86,"__hash__":541},"docs\u002F3.advanced-topics\u002F05.multi-frontend.md",{"type":228,"value":229,"toc":529},"minimark",[230,234,239,242,342,346,377,381,384,526],[231,232,233],"p",{},"Thanks to the component-oriented decoupling of Lupus Decoupled Drupal, it's really easy to connect a frontend of choice!",[235,236,238],"h2",{"id":237},"supported-frontend-frameworks","Supported frontend frameworks",[231,240,241],{},"Lupus Decoupled provides supports for the following frontend frameworks:",[243,244,245,268],"table",{},[246,247,248],"thead",{},[249,250,251,255,258,261,264],"tr",{},[252,253,254],"th",{},"Framework",[252,256,257],{},"Technology",[252,259,260],{},"Status",[252,262,263],{},"Description",[252,265,267],{"align":266},"left","Link",[269,270,271,299,324],"tbody",{},[249,272,273,279,282,285,291],{},[274,275,276],"td",{},[277,278,158],"a",{"href":165},[274,280,281],{},"Vue.js, JavaScript",[274,283,284],{},"Default, Stable & Complete",[274,286,287,290],{},[277,288,289],{"href":169},"Easy setup"," via re-usable connector module.",[274,292,293],{"align":266},[277,294,298],{"href":295,"rel":296},"https:\u002F\u002Fgithub.com\u002Fdrunomics\u002Fnuxtjs-drupal-ce",[297],"nofollow","Connector module",[249,300,301,308,311,314,317],{},[274,302,303],{},[277,304,307],{"href":305,"rel":306},"https:\u002F\u002Fnextjs.org",[297],"Next.js",[274,309,310],{},"React, JavaScript",[274,312,313],{},"Proof-of-concept",[274,315,316],{},"Example implementation, see README for details.",[274,318,319],{"align":266},[277,320,323],{"href":321,"rel":322},"https:\u002F\u002Fgithub.com\u002Fdrunomics\u002Flupus-decoupled-nextjs-example",[297],"Example implementation",[249,325,326,329,336,338,340],{},[274,327,328],{},"Yours?",[274,330,331],{},[277,332,335],{"href":333,"rel":334},"https:\u002F\u002Fgithub.com\u002Fdrunomics\u002Flupus-decoupled-website\u002Fedit\u002Fmain\u002Fcontent\u002F3.advanced-topics\u002F05.multi-frontend.md",[297],"Add it!",[274,337],{},[274,339],{},[274,341],{"align":266},[235,343,345],{"id":344},"example-frontends","Example frontends",[347,348,349,357,364,370],"ul",{},[350,351,352],"li",{},[277,353,356],{"href":354,"rel":355},"https:\u002F\u002Fgithub.com\u002Fdrunomics\u002Flupus-decoupled-nuxt-starter",[297],"Nuxt Naked Starter",[350,358,359],{},[277,360,363],{"href":361,"rel":362},"https:\u002F\u002Fgithub.com\u002Fdrunomics\u002Flupus-decoupled-nuxt-shadcn",[297],"Nuxt Shadcn Example",[350,365,366],{},[277,367,369],{"href":321,"rel":368},[297],"Next.js Example",[350,371,372],{},[277,373,376],{"href":374,"rel":375},"https:\u002F\u002Fgithub.com\u002Fdrunomics\u002Flupus-decoupled-nuxt2-demo",[297],"Nuxt 2 Example (legacy)",[235,378,380],{"id":379},"adding-a-new-frontend-framework","Adding a new frontend framework",[231,382,383],{},"Adding a support for a new framework is quite easy. Here is a short overview of what the frontend needs to take care of:",[347,385,386,406,416,426,440,458,464,475],{},[350,387,388,392,393,397,398,401,402,405],{},[389,390,391],"em",{},"Proxying requests",": The frontend typically proxies requests to the Drupal ",[394,395,396],"code",{},"\u002Fce-api"," endpoint, while preserving the request URI and optionally some request headers.\nThat way, a request to ",[394,399,400],{},"\u002Fnews"," is served by the frontend, which requests the backend API at ",[394,403,404],{},"\u002Fce-api\u002Fnews"," and takes care\nof rendering the response.",[350,407,408,411,412,415],{},[389,409,410],{},"Forwarding headers",": By forwarding the cookie header, the frontend may easily leverage Drupal ",[277,413,414],{"href":47},"authentication handling",".",[350,417,418,421,422,425],{},[389,419,420],{},"Rendering page content",": The ",[394,423,424],{},"content"," section of a response contains a nested tree of custom elements that need to be rendered on the page.",[350,427,428,431,432,436,437,415],{},[389,429,430],{},"Render a page shell",": Request ",[277,433,435],{"href":434},"\u002Fguide\u002Fsite-layout-menus#navigation-menus","navigation menus"," and render them as part of a ",[277,438,439],{"href":43},"site layout",[350,441,442,445,446,450,451,454,455,415],{},[389,443,444],{},"Support page attributes",": Support all page attributes provided by the Drupal ",[277,447,449],{"href":448},"\u002Fget-started\u002Fhow-it-works#custom-elements-page-api","page API",", i.e. render ",[277,452,453],{"href":55},"breadcrumbs and messages",", support ",[277,456,457],{"href":51},"Metatags and Local tasks",[350,459,460,463],{},[389,461,462],{},"Handle errors",": Take care to not add special handling for HTTP 4xx responses, such that Drupal-controlled error pages get rendered as usual. Simply take care of forwarding the status code.",[350,465,466,469,470,474],{},[389,467,468],{},"Handle redirects",": When the page-API generates a ",[277,471,473],{"href":472},"\u002Fguide\u002Fredirects#redirect-api-responses","redirect response"," instead of a page, take care to issue a suitable redirect response with the given status code instead of rendering a page.",[350,476,477,480,481,483,484],{},[389,478,479],{},"Canvas support"," (optional): To support ",[277,482,70],{"href":71},", two additional pieces are needed:\n",[347,485,486,498],{},[350,487,488,491,492,497],{},[389,489,490],{},"Custom Elements preview provider",": Implement a preview provider plugin so the Canvas editor can render live component previews via an iframe. The provider receives a component name and props and renders the component in isolation. See the ",[277,493,496],{"href":494,"rel":495},"https:\u002F\u002Fgit.drupalcode.org\u002Fproject\u002Fcustom_elements\u002F-\u002Fblob\u002F3.x\u002Fsrc\u002FPlugin\u002FCustomElementsPreviewProvider\u002FNuxtPreviewProvider.php?ref_type=heads",[297],"Nuxt preview provider plugin"," as a reference implementation.",[350,499,500,503,504,507,508,513,514,519,520,525],{},[389,501,502],{},"Component index",": Expose a ",[394,505,506],{},"component-index.json"," endpoint listing available components, their props, and metadata. ",[277,509,512],{"href":510,"rel":511},"https:\u002F\u002Fwww.drupal.org\u002Fproject\u002Fcanvas_extjs",[297],"Canvas External JS Components"," (a Canvas extension for integrating external JavaScript components) reads this index to populate the Canvas editor UI. See the ",[277,515,518],{"href":516,"rel":517},"https:\u002F\u002Fgithub.com\u002Fdrunomics\u002Fnuxt-component-preview#component-index",[297],"nuxt-component-preview component index"," and ",[277,521,524],{"href":522,"rel":523},"https:\u002F\u002Fgithub.com\u002Ffullfatthings\u002Fdrupal-canvas-react",[297],"fullfatthings\u002Fdrupal-canvas-react"," for Vue and React reference implementations.",[231,527,528],{},"That's it!",{"title":530,"searchDepth":531,"depth":531,"links":532},"",2,[533,534,535],{"id":237,"depth":531,"text":238},{"id":344,"depth":531,"text":345},{"id":379,"depth":531,"text":380},"md",null,{},true,{"title":84,"description":233},"8LbMX4R457PnmnJT0q44xu5IvUut9RJZpc2fUUdqFH8",[543,545],{"title":74,"path":75,"stem":76,"description":544,"children":-1},"Drupal CMS is Drupal's user-friendly distribution aimed at marketers and content teams. Lupus Decoupled supports it via site templates, providing a fully decoupled setup out of the box.",{"title":88,"path":89,"stem":90,"description":546,"children":-1},"The Lupus Decoupled Views\nsubmodule provides support for Drupal's Views module. The Views module is Drupal's native way and very powerful way of creating listings of content. It provides a UI for configuring complex queries, searches and the rendering of results, including paging.",1779292109775]