sveltejs / kit

web development, streamlined
https://svelte.dev/docs/kit
MIT License
18.73k stars 1.94k forks source link

Full layout reset (ignore the root layout) #9455

Closed adiguba closed 1 year ago

adiguba commented 1 year ago

Describe the problem

Currently we can reset to the "root" layout using +page@.svelte or +layout@.svelte. This will use the routes/+layout.svelte as parent layout, ignoring all intermediate layouts.

But there is no way to completely ignore this root layout !

The current solution for this, as stated in the documentation, is to use a (group) : https://kit.svelte.dev/docs/advanced-routing#advanced-layouts-page

It's fine when we build our route tree in advance for that. But it can be painful in an existing app that wouldn't use this structure.

For example, If my app is currently like that :

    src/routes/
    ├ other-routes
    │ ├ path
    │ └ +page@.svelte      // reset to root layer (with header/footer)
    │ ├ ...
    │ └ +layout.svelte 
    ├ item/
    │ ├ [id]/
    │ │ ├ embed/
    │ │ │ └ +page@.svelte  // reset to root layer, but I want an empty layer
    │ │ └ +page.svelte
    │ └ +layout.svelte
    └ +layout.svelte       // root layer, with app header/footer...

Here my /item/[i]/embed route will use the root layer, used by all page of my applications, but I want an empty layout ! I could create a (app) group in order to fix that, like in the documentation's example, but it will have some breaking impacts on my app :

src/routes/
-   ├ other-routes
-   │ ├ path
-   │ └ +page@.svelte      // reset to root layer (with header/footer)
-   │ ├ ...
-   │ └ +layout.svelte 
-   ├ item/
-   │ ├ [id]/
-   │ │ ├ embed/
-   │ │ │ └ +page@.svelte  // reset to root layer (empty)
-   │ │ └ +page.svelte
-   │ └ +layout.svelte
-   └ +layout.svelte       // root layer, with app header/footer...
+   ├  (app)               // New directory
+   │ ├ other-routes
+   │ │ ├ path
+   │ │ └ +page@(app).svelte    // reset to root layer (with header/footer) NEED TO BE RENAMMED !
+   │ │ ├ ...
+   │ │ └ +layout.svelte 
+   │ │ ├ ...
+   │ ├ item/
+   │ │ ├ [id]/
+   │ │ │ ├ embed/
+   │ │ │ │ └ +page@.svelte    // reset to root layer
+   │ │ │ └ +page.svelte
+   │ │ └ +layout.svelte
+   │ └ +layout.svelte        // (app) root layer, with app header/footer...
+   └ +layout.svelte          // root layer, empty

Why we need to revamp the whole app for something so basic ?

Describe the proposed solution

A new special layout reset, by using a specific syntax like +page@@.svelte or +layout@@.svelte (note the double @).

This would consist of using an empty root layout, completely ignoring the +layout.svelte/js/ts files from the routes directory.

=> And now we have a single change on the current page :

    src/routes/
    ├ other-routes
    │ ├ path
    │ └ +page@.svelte
    │ ├ ...
    │ └ +layout.svelte 
    ├ item/
    │ ├ [id]/
    │ │ ├ embed/
-   │ │ │ └ +page@.svelte
+   │ │ │ └ +page@@.svelte  // reset to an EMPTY layer
    │ │ └ +page.svelte
    │ └ +layout.svelte
    └ +layout.svelte       // root layer, with app header/footer...

Alternatives considered

Continue to use (group)

Importance

nice to have

Additional Information

No response

Frank-D commented 1 year ago

+1 (I'm in the exact same situation, and was considering refactoring my entire routes tree exactly like described above, however I'm scratching my head right now wondering if that is really worth it, since I'm afraid I won't need too many pages which require to skip the root layout, so that would be a bummer to introduce a new root group - such as (app) as per the above - and move everything under, only to make room for a couple of those pages (+- static in my case) that require to skip my main/root layout...)

NormandoHall commented 1 year ago

+1 Same, it is crazy to change all the organization paths to use (group) only for reset the layout in some route.

Rich-Harris commented 1 year ago

Closing for the reasons given in https://github.com/sveltejs/kit/pull/9472#issuecomment-1490861458.

Moving lots of files isn't a problem — if you use git mv then you won't even lose git history, and PRs etc will remain mergable. Same goes for renaming existing +page@.svelte files — this doesn't feel like a dealbreaker. route.id code will need to be changed (though I'm curious to know how you're using route.id? I've found it to be quite rare to use it), and this reminds me that it would be nice to add a better type than string to that property.

As an alternative, you can always do this sort of thing:

{#if route.id.includes('/embed/')}
  <slot />
{:else}
  <main>
    <Header/>
    <slot />
    <Footer />
  </main>  
{/if}
adiguba commented 1 year ago

Currently I'm not using route.id with Sveltekit.

But on websites under another techs I used something similar to identify pages for stats/analytics (routes had a unique ID, but localized URIs).

Thanks for your response.

newsve commented 1 year ago

if you use git mv then you won't even lose git history,

This isn't true, you lose it, just google yourself "does git mv preserve history".

As an alternative, you can always do this sort of thing:...

which isn't type-safe and silently breaks on folder changes

Moving lots of files isn't a problem —

I would say, it is, and takes flow and fun out of coding and creates a lot of hassle

Fwiw, I am not into the feature of OP, rather would like to have a more flexible layout API, which allows to break out of parent's or a specific layouts only, and not only root's.

Designing a good composition API is a challenge and not trivial but the layout API at its current state could be improved.

dummdidumm commented 1 year ago

Fwiw, I am not into the feature of OP, rather would like to have a more flexible layout API, which allows to break out of parent's or a specific layouts only, and not only root's.

This is possible. If you have a route like foo/bar/baz/+page.svelte and each segment has a layout, you can skip the baz layout or the baz and bar layout by doing +page@bar.svelte or +page@foo.svelte. Only thing you can't do is skip the root layout or skip a layout in-between, like only skipping the bar layout.

newsve commented 1 year ago

you can skip the baz layout or the baz and bar layout by doing +page@bar.svelte or +page@foo.svelte

Ok, this is very nice, thanks for letting me know! 🙂 In which part of the docs is page@.svelte specced?

dummdidumm commented 1 year ago

https://kit.svelte.dev/docs/advanced-routing#advanced-layouts-breaking-out-of-layouts

rogadev commented 1 year ago

+1 Same, it is crazy to change all the organization paths to use (group) only for reset the layout in some route.

It's really not. Think about a page you may want to print. Do you need a navbar? Footer? No. Just the page, as-is, without any layout.

Why was this closed? This is kind of a big deal that SvelteKit can't do this, IMHO. It's inflexibilities like these that make me pull my hair out when trying to use SvelteKit. It makes me want to reroll back to Nuxt every time. At some point, I'll stop reaching for SK completely and just build everything in Nuxt if these issues don't get fixed.

laneme commented 1 year ago

It makes me want to reroll back to Nuxt every time. At some point, I'll stop reaching for SK completely and just build everything in Nuxt if these issues don't get fixed.

@rogadev Its understandable you (and other users) may want a feature that sveltekit decided not to work on. We should respect that and not act like they owe us a thing and nuxt is their business competitor and they should keep all their customers happy.

If you really believe a feature should be implemented, provide the sveltekit team with convincing use cases. I'm sure they will take a second look.

rogadev commented 1 year ago

@rogadev Its understandable you (and other users) may want a feature that sveltekit decided not to work on. We should respect that and not act like they owe us a thing and nuxt is their business competitor and they should keep all their customers happy.

No expectations were made. I am simply offering candid and straightforward feedback. I am fortunate to be in a position where I can select the framework that best suits each individual project. My comments are intended to elucidate the rationale behind my choices in this context. At no point did I suggest an obligation on their part, but rather, I aimed to articulate the implications their decisions have on my experience as a user.

If you really believe a feature should be implemented, provide the sveltekit team with convincing use cases. I'm sure they will take a second look.

I feel strongly that the original post was sufficiently detailed and I support the sentiments of the original poster, and I fully endorse the points raised by the original author, as evidenced by my participation in this discussion. There are multiple, readily apparent reasons why this feature is important, such as the creation of printable report views that exclude user interface elements like the navigation bar. The current layout system in SvelteKit unnecessarily complicates what should otherwise be a rather straightforward task. If they borrowed from other frameworks that have already learned this lesson it would be a significant improvement.

Lastly, I would like to emphasize the importance of maintaining a professional discourse, especially when addressing the viewpoints of others. The original contributor invested considerable time and effort into presenting a well-argued case. Attempting to discredit or diminish the validity of others concerns by way of gaslighting is poor form and undermines the very purpose of such discussion threads, which are designed to be platforms for constructive debate among developers. Telling people they don't have valid concerns is not in any way constructive.

muthiyalu commented 1 year ago

I agree with @rogadev here , it seems weird that such a basic requirement which is supported in almost every other framework needs such a discussion. IMHO when it comes these matters nothing can compare to the laravel community. Having built apps in many framework and languages (with some of them running in prod for large enterprises) including spring, rails, django, express, vue etc , Sveltekit is a such a breath of fresh air. But the community should listen to why someone may be asking for a feature , especially one that been taken for granted for years in most framework.

lukecarbis commented 10 months ago

I agree that this would be a great addition to SvelteKit. I'm also disappointed it's not easily possible.

My workaround isn't perfect, but suits me, and might suit others:

I just created the route I wanted in the static directory (e.g. /static/privacy-policy/) and put an index.html file there. This will just skip Svelte entirely, which is a bummer if you want to include other components. But it did the trick.

sebmor commented 9 months ago

When it's clearly defined parts of the app, such as admin/app/marketing, using group is perfectly fine. But once an app grows big enough there are always a few exception routes that need an empty or custom layout, not the usual header/footer. And for those to require the whole app to be in a group is just unnecessary directory tree convolution.

I strongly would support a simple solution, perhaps as simple as being able to create named layouts and being able to reference them with +page@layout-name.

Salman2301 commented 6 months ago

Closing for the reasons given in #9472 (comment).

Moving lots of files isn't a problem — if you use git mv then you won't even lose git history, and PRs etc will remain mergable. Same goes for renaming existing +page@.svelte files — this doesn't feel like a dealbreaker. route.id code will need to be changed (though I'm curious to know how you're using route.id? I've found it to be quite rare to use it), and this reminds me that it would be nice to add a better type than string to that property.

As an alternative, you can always do this sort of thing:

{#if route.id.includes('/embed/')}
  <slot />
{:else}
  <main>
    <Header/>
    <slot />
    <Footer />
  </main>  
{/if}

Yeah... but that's what filebased routing suppose to solve?. It will be nice if svelte can support skipping the root layout too. idk why it enforce root layout but you can skip other layouts. Any alternative its feels like a ugly workaround. Please consider supporting it.

Will be nice, if we can read a file and see that file is skipping routes

TheStrongest commented 1 week ago

I just had this issue a while ago. It seemed like a basic feature to have for a frontend framework. I could. I don't understand why this was skipped, and why it hasn't been implemented in the new svelte 5.

Please guys consider this feature, it would be breathe of fresh air. Svelte's selling point is its ease/simplicity.