Coding 2
**Private Folders**
- In nextjs routing is based on folders so things like grouping and management for code is also done by project so there have to be folders which is not routable or write ui logic rather than routing logic. These folders r called private folders.
- They begin with `_`(underscore). eg: `_lib`.
- If we want underscore to be as part of route then use the prefix `%5F` which is url encoded form of underscore(`_`).
**Route Groups**
- Allows us to logically group our routes and project files without affecting the URL path structure.
- Folder purpose is not for routing only but for grouping of various routes and we may not want to effect the url. Example if project structure
```text
src/app
auth
Login
Register
page.jsx
````
To access we need `localhost:3000/auth/register`. If we want to access via `localhost:3000/register` then we need to tell next that `auth` is route group. surround auth with parenthesis like this `(auth)`.
Now
```text
src/app
(auth)
Login
Register
page.jsx
````
**Layout**
- A page is UI that is unique to a route
- A layout is UI that is shared between multiple pages in the app.
Eg:
In `src/app/layout.jsx`
```jsx
export const metadata = {
title: "Next.js",
description: "Generated by Next.js",
};
export default function RootLayout({ children }) {
return (
{children}
);
}
```
Now every page.jsx content will be under this header and footer. and the routes ie folder inside app and all those nested one will inherit too
**Route Group Layout**
- We may not want the same layout for every nested route so to fix it we can use route groups for layout. Purpose being is to selectively apply layout to certain segments while leaving other unchanged
Structure
```text
src/app
(auth)
forgot-password
(with-auth-layout)
Login
Register
layout.jsx
page.jsx
```
In `src/app/(auth)/(with-auth-layout)/layout.jsx` .
```jsx
export default function AuthLayout({ children }) {
return (
Inner Layout
{children}
);
}
```
Now in `login` and `register` we would have
```text
Head
Inner Layout
Login
Footer
```
This inner layout is added for login and password only and wont work for forgot-password page
**Routing metadata**
- Nextjs have metadata api to define metadata for each page
- Medadata ensures accurate and relevant information is displayed when the page is shared or indexed.
- Configuring metadata
- Export static metadata object
- Export a dynamic generateMetadata function
**MetaData Rules**
- Both layout.jsx and page.jsx files can export metadata. If defined in a layout, it applies to all pages in that layout, but defined in a page, then that page only.
- Metadata is read in order ie from root level to final page level.
- When there's metadata in multiple places for the same route, they get combined, but page metadata will replace layout metadata if they have the same properties
Structure
```text
src/app
about
page.jsx
page.jsx
layout.jsx
```
In `src/app/layout.jsx`
```jsx
// object has to be 'metadata'
export const metadata = {
title: "Next.js",
description: "Generated by Next.js",
};
export default function RootLayout({ children }) {
return (
{children}
);
}
```
In `src/app/about/page.jsx`
```jsx
export const metadata = {
title: "About me",
};
export default function About() {
return About me
;
}
```
all the routes will inherit the metadata of rootlayout page but the metadata inside their own page will take more precedence.
So for `localhost:3000/about` page title is 'About me' and descruption will be inherited by metadata object in `layout.jsx` in app folder.
**Dynamic metadata**
- Depends on dynamic info such as current route parameters, external data or metadata from parent segments
For dynamic routes, metadata may have to dynamic too. instead of exporting the object function is exported which returns the metadata with dynamic information
Structure
```text
src/app
products
[productId]
page.jsx
page.jsx
page.jsx
layout.jsx
````
In `src/app/products/[productId]/page.jsx`
```jsx
// function name has to be 'generateMetadata' case-sensitive
export const generateMetadata = ({ params }) => {
return {
title: `Product ${params.productId}`,
};
};
export default function ProductDetails({ params }) {
console.log("params: ", typeof params.productId);
return Details about Product {params.productId}
;
}
```
As fetch can be used so this function ie generateMetadata can be async too
In `src/app/products/[productId]/page.jsx`
```jsx
// function name has to be 'generateMetadata' case-sensitive
export const generateMetadata = ({ params }) => {
return {
title: `Product ${params.productId}`,
};
};
export default function ProductDetails({ params }) {
console.log("params: ", typeof params.productId);
return Details about Product {params.productId}
;
}
```
**Title metadata**
- Title needed not be a string and it can be a object too. This object has 3 properties ie `absolute`, `default`, `template`.
- Default acts same as the one defined when title is string ie when inherited by other routes as when defined in layout.jsx
Structure
```text
src/app
blog
page.jsx
layout.jsx
```
In `src/app/layout.jsx`
```jsx
export const metadata = {
title: {
default: "Nextjs",
template: "%s | end",
},
description: "Generated by Next.js",
};
```
In `src/app/blog/page.jsx`
```jsx
export const metadata = {
title: {
default: "blog",
},
};
```
metadata of `localhost:3000/blog` is `blog | end`
If
```jsx
export const metadata = {
title: {
absolute: "blog",
},
};
```
then
metadata of `localhost:3000/blog` is `blog` as absolute will counter template too