You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Jekyll单篇文章与列表页共用默认布局的问题解决问询

解决Jekyll单篇文章与列表页共用默认布局的问题

首先得理清你的核心问题:你想让单篇文章使用默认布局(包含站点通用的头部、尾部等结构),但直接把默认布局应用到文章模板后,列表页循环渲染文章时会重复加载整个默认布局,导致页面结构嵌套混乱。

解决思路是拆分布局职责,用布局继承+内容片段复用的方式,让默认布局只负责站点全局结构,单篇文章和列表页分别填充各自的内容,避免重复渲染。

步骤1:定义基础默认布局

先把站点通用的结构放在 _layouts/default.html 里,这是所有页面的基础框架,只渲染一次:

<!DOCTYPE html>
<html lang="{{ site.lang }}">
<head>
  <meta charset="UTF-8">
  <title>{{ page.title }} | {{ site.title }}</title>
  <!-- 站点通用CSS、JS等 -->
  <link rel="stylesheet" href="/css/main.css">
</head>
<body>
  <header class="site-header">
    <!-- 导航栏、站点标题等全局头部 -->
    <h1><a href="/">{{ site.title }}</a></h1>
    <nav>
      <a href="/blog/">博客</a>
      <a href="/about/">关于</a>
    </nav>
  </header>

  <!-- 页面专属内容会插入到这里 -->
  <main class="content">
    {{ content }}
  </main>

  <footer class="site-footer">
    <!-- 全局尾部内容 -->
    <p>&copy; {{ site.time | date: "%Y" }} {{ site.title }}</p>
  </footer>
</body>
</html>

步骤2:创建单篇文章的专用布局

新建 _layouts/post.html,让它继承默认布局,只负责单篇文章的内容结构:

---
layout: default
---
<article class="single-post">
  <h1 class="post-title">{{ page.title }}</h1>
  <div class="post-meta">
    <span class="post-date">{{ page.date | date_to_string }}</span>
    {% if page.tags %}
      <span class="post-tags">标签:{{ page.tags | join: ", " }}</span>
    {% endif %}
  </div>
  <div class="post-content">
    {{ content }}
  </div>
</article>

然后在每篇文章的 front matter 里指定使用这个布局:

---
layout: post
title: "我的第一篇文章"
date: 2024-05-20
tags: [教程, Jekyll]
---
<!-- 文章内容 -->

步骤3:构建列表页(复用默认布局)

列表页(比如 blog/index.html)直接使用默认布局,然后在内容区域循环渲染文章的预览片段,而不是整个文章布局:

---
layout: default
title: 我的博客
---
<h1 class="page-title">最新文章</h1>
<div class="post-list">
  {% for post in site.posts %}
    <div class="post-preview">
      <h2><a href="{{ post.url }}">{{ post.title }}</a></h2>
      <div class="preview-meta">{{ post.date | date_to_string }}</div>
      <p class="preview-excerpt">{{ post.excerpt | strip_html | truncatewords: 30 }}</p>
      <a href="{{ post.url }}" class="read-more">阅读全文 →</a>
    </div>
  {% endfor %}
</div>

进阶:复用文章预览片段

如果多个页面需要展示文章预览(比如首页、分类页),可以把预览代码抽成独立的 include 文件 _includes/post-preview.html:

<div class="post-preview">
  <h2><a href="{{ include.post.url }}">{{ include.post.title }}</a></h2>
  <div class="preview-meta">{{ include.post.date | date_to_string }}</div>
  <p class="preview-excerpt">{{ include.post.excerpt | strip_html | truncatewords: 30 }}</p>
  <a href="{{ include.post.url }}" class="read-more">阅读全文 →</a>
</div>

然后在列表页里这样调用:

{% for post in site.posts %}
  {% include post-preview.html post=post %}
{% endfor %}

关键注意点

  • 绝对不要在列表页的循环里直接引用 _layouts/post.html,这会导致默认布局被嵌套渲染多次,破坏页面结构。
  • 用 post.excerpt 而不是 post.content 来展示预览,避免加载整篇文章的内容,提升列表页加载速度。

这样一来,单篇文章会通过 post 布局继承默认的站点结构,列表页也会使用默认布局,但只渲染一次全局框架,循环展示的是轻量化的文章预览,完美解决你的问题。

内容的提问来源于stack exchange,提问作者gpb14

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 08:00:46