Skip to main content

Articles List Configuration

In version 2.0.0, the article list has been removed from the main layout, and became a custom layout due to internal issues. To use the article list, you can follow these steps:

Initial Setup

  1. Create a file named ArticleList.vue inside the /.vitepress/theme/ folder.

  2. The code for the ArticleList.vue file is available inside the package under aplos/custom/ArticleListExample.txt. You can copy the code from there and paste it into the ArticleList.vue file. If you want to copy it from here, you can use the following code:

  <div class="article-list">
      <small>To use the filter you need JavaScript to be enabled.</small>
    <div class="filter-tags">
      <button @click="filterPosts('')" id="all-tags">All</button>
      <button v-for="tag in uniqueTags" :key="tag" @click="filterPosts(tag)">
        <span class="hashtag">#</span>{{ tag }}
    <div class="post-container">
      <article v-for="post in filteredPosts" :key="post.title" class="post">
              .replace(/\s+/g, '-')}.html`"
            >{{ post.title }}</a
        <p class="date">{{ }}</p>
        <p>{{ post.description }}</p>
        <div class="tags">
          <span v-if="typeof post.tags === 'string'" :key="post.tags"
            >#{{ post.tags }}</span
          <span v-else v-for="tag in post.tags" :key="tag">#{{ tag }}</span>

<script setup lang="ts">
import "aplos/custom/ArticleList.scss";
import { data as posts } from "./";
import { computed, ref } from "vue";

const selectedTag = ref(null);

const allTags = computed(() => {
  return posts.reduce((tags, post) => {
    return tags.concat(Array.isArray(post.tags) ? post.tags : [post.tags]);
  }, []);

const uniqueTags = computed(() => {
  const tags = [ Set(allTags.value)];
  return tags.filter((tag) => tag !== "");

const filteredPosts = computed(() => {
  return selectedTag.value === null
    ? posts
    : posts.filter((post) =>
          ? post.tags.includes(selectedTag.value)
          : post.tags === selectedTag.value,

function filterPosts(tag: string) {
  selectedTag.value = tag === "" ? null : tag;
  1. Inside the .vitepress/theme folder, create a file named and paste the following code:
import { createContentLoader } from "vitepress";

interface Post {
  title: string;
  description: string;
  tags: string[];

declare const data: Post[];
export { data };

export default createContentLoader("articles/posts/*.md", { // Change the path to your posts
  excerpt: true,
  transform(raw): Post[] {
    return raw
      .map(({ frontmatter }) => ({
        title: frontmatter.title,
        description: frontmatter.description,
        tags: frontmatter.tags,
        date: formatDate(,
      .sort((a, b) => new Date( - new Date(;

function formatDate(raw: string): string {
  const date = new Date(raw);
  return date.toLocaleDateString("en-GB", {
    year: "numeric",
    month: "long",
    day: "2-digit",

Setting up the Page

Inside the page you want to use the article list, you can use the following example code:

# My Page

This is my page content.

<ArticleList />

This is the rest of my page content.

<script setup lang="ts">
import ArticleList from ".vitepress/theme/ArticleList.vue";

↑ Go to topFile an issue