Jehlani Luciano Logo

Layouts

Guidelines for creating and using Astro layout components.

astro
          
            ## Astro Layouts Guidelines

1.  Purpose: Layouts are reusable Astro components (`.astro` files) designed to provide a consistent structure for pages, such as defining the overall HTML shell (`<html>`, `<head>`, `<body>`), headers, footers, and navigation.

2.  Core Concept: Layouts are just standard Astro components. They can accept props, import other components (including other layouts), and use slots.

3.  Location: Conventionally placed in the `src/layouts/` directory, but this is not mandatory. They can reside anywhere in `src/`. If placed directly within `src/pages/`, prefix the filename with an underscore (`_`) to prevent it from becoming a route (e.g., `src/pages/_MyLayout.astro`).

4.  Basic Structure: A typical layout component defines the common page elements and uses a `<slot />` component to designate where the unique content of each page should be injected.

    ```astro
    <!-- src/layouts/BaseLayout.astro -->
    ---
    const { pageTitle = 'Default Title' } = Astro.props;
    ---
    <html lang="en">
    <head>
      <meta charset="utf-8" />
      <meta name="viewport" content="width=device-width" />
      <title>{pageTitle}</title>
      <link rel="stylesheet" href="/global.css">
    </head>
    <body>
      <header>My Site Header</header>
      <main>
        <slot /> <!-- Page content goes here -->
      </main>
      <footer>My Site Footer</footer>
    </body>
    </html>
    ```

5.  Using Layouts in `.astro` Pages: Import the layout component and wrap the page-specific content within its tags. Pass any required data as props.

    ```astro
    <!-- src/pages/index.astro -->
    ---
    import BaseLayout from '../layouts/BaseLayout.astro';
    ---
    <BaseLayout pageTitle="Home Page">
      <h1>Welcome!</h1>
      <p>This is the home page content.</p>
    </BaseLayout>
    ```

6.  Layouts for Markdown Pages (`.md` files in `src/pages/`):

    - Use the special `layout` frontmatter property within the Markdown file to specify the path to the `.astro` layout component.

      ```markdown
      ---
      layout: ../layouts/BlogPostLayout.astro
      title: "My First Blog Post"
      author: "Jane Doe"
      ---

      This is the content of my post.
      ```

    - The specified layout component automatically receives props derived from the Markdown file:
      - `frontmatter`: An object containing all the YAML frontmatter data.
      - `file`: Absolute path of the Markdown file.
      - `url`: URL pathname of the page.
      - `headings`: An array of heading objects (`{ depth, slug, text }`).
      - `rawContent()`: Function returning the raw Markdown string.
      - `compiledContent()`: Async function returning the compiled HTML string.
    - Use the `MarkdownLayoutProps` type helper from `astro` for TypeScript support in these layouts.

7.  Layouts for MDX Pages (`.mdx` files):

    - You can use the `layout` frontmatter property just like in `.md` files, with the same automatic prop injection.
    - Alternatively, you can import the layout component within the MDX file and wrap the content manually. If you do this, you must pass props explicitly; automatic prop injection does not occur in this case. Remember to include `<meta charset="utf-8">` in your layout when using MDX.

8.  Nesting Layouts: Layouts can import and use other layouts. This is useful for creating variations (e.g., a blog post layout that uses a base site layout). Pass props and slots down through the layers as needed.
    ```astro
    <!-- src/layouts/BlogPostLayout.astro -->
    ---
    import BaseLayout from './BaseLayout.astro';
    const { frontmatter } = Astro.props; // Received from Markdown page
    ---
    <BaseLayout pageTitle={frontmatter.title}>
      <article>
        <h1>{frontmatter.title}</h1>
        <p>By {frontmatter.author}</p>
        <slot /> <!-- Markdown content goes here -->
      </article>
    </BaseLayout>
    ```

Reference: [Astro Layouts Docs](https://docs.astro.build/en/basics/layouts/)